第二章:环境准备与基础搭建
好,咱们正式开始动手了。这一章我把它叫做「地基工程」。你想想看,边缘设备的环境跟云端不一样,资源有限、网络复杂、安全要求还高。如果地基没打好,后面消息队列跑起来,三天两头出问题,那可就头疼了。
我个人习惯,在搭建任何分布式系统之前,先把容器化环境理清楚。Docker 和 Docker Compose 是标配,但怎么配、配多少、怎么限制资源,这里面门道不少。我带大家一步步走。
2.1 Docker 基础:不只是装个软件
Docker 大家都熟,但在边缘计算场景下,我建议你多留个心眼。边缘设备的操作系统五花八门,有的还是 ARM 架构。我曾经在一个工业网关项目上,就因为镜像没选对架构,折腾了一整天。
先确认你的 Docker 版本:
docker --version
# 我建议至少 20.10 以上版本
安装其实很简单,但要注意一点:千万别用系统自带的旧版本。我习惯用官方脚本安装:
curl -fsSL https://get.docker.com -o get-docker.sh
sudo sh get-docker.sh
sudo usermod -aG docker $USER,然后重新登录。不然每次都要 sudo,很烦。
装好之后,跑个 hello-world 验证一下:
docker run hello-world
看到那个 "Hello from Docker!" 了吗?嗯,基础环境通了。
2.2 Docker Compose 编排:让多容器协作
单容器好办,但我们的消息队列方案里,至少需要几个组件:消息代理(比如 RabbitMQ 或 EMQX)、数据持久化服务、可能还有监控代理。手动一个个启动?不现实。
Docker Compose 就是干这个的。我建议你安装最新稳定版:
sudo curl -L "https://github.com/docker/compose/releases/latest/download/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose
验证一下:
docker-compose --version
这里有个小坑:边缘设备上可能没有 curl,或者网络受限。我曾经在某个工厂内网环境,只能手动下载二进制包传上去。所以,提前准备好离线安装包,是个好习惯。
2.3 网络规划:别让消息走错路
边缘设备的网络环境,说白了就是「乱」。有的设备在 192.168.1.x 段,有的在 10.0.0.x 段,还有的可能通过 4G 模块上网。消息队列要跨设备通信,网络规划必须提前想好。
我一般用 Docker 的 overlay 网络,或者干脆用 host 网络模式。但 host 模式有安全隐患,你想想看,容器直接暴露在宿主机网络上,端口冲突是小事,被扫描到就麻烦了。
我的建议方案:
- 同一台设备上的容器:用 bridge 网络,端口映射到宿主机
- 跨设备通信:用 overlay 网络 + 服务发现(比如 Consul 或 etcd)
- 安全要求高的场景:用 macvlan 网络,给容器分配独立 MAC 地址
举个例子,一个典型的 docker-compose 网络配置:
networks:
edge-mq-net:
driver: bridge
ipam:
config:
- subnet: 172.20.0.0/16
gateway: 172.20.0.1
2.4 资源限制策略:别让消息队列吃掉所有内存
边缘设备的内存通常只有 512MB 到 2GB。消息队列如果没限制,一旦流量突增,直接 OOM 把设备搞死。我见过不止一次这样的惨案。
Docker 提供了很精细的资源限制能力。我建议你至少设置以下参数:
| 参数 | 说明 | 推荐值(边缘设备) |
|---|---|---|
| --memory | 最大内存 | 256MB ~ 512MB |
| --memory-reservation | 软限制(内存压力时保证) | 128MB |
| --cpus | CPU 核心数 | 0.5 ~ 1.0 |
| --pids-limit | 最大进程数 | 100 |
在 docker-compose 里这样写:
services:
message-broker:
image: rabbitmq:3-management
deploy:
resources:
limits:
cpus: '0.5'
memory: 256M
reservations:
memory: 128M
2.5 安全基线配置:别裸奔
边缘设备往往部署在无人值守的现场,物理安全都难保证,更别说网络安全了。但正因为这样,安全基线才更重要。我的原则是:默认拒绝,按需开放。
几个必须做的安全配置:
- 不要用 root 运行容器。创建专用用户,比如 uid 1000。
- 只暴露必要端口。管理端口(比如 15672)只在内网开放。
- 启用 TLS。消息队列的通信必须加密,哪怕是在内网。
- 设置文件系统只读。除非必要,否则把容器的根文件系统设为只读。
一个安全加固的 docker-compose 示例:
services:
message-broker:
image: rabbitmq:3-management
user: "1000:1000"
read_only: true
tmpfs:
- /var/lib/rabbitmq
security_opt:
- no-new-privileges:true
cap_drop:
- ALL
cap_add:
- NET_BIND_SERVICE
核心思路: 给容器最小的权限,只给它能干活的那部分。比如消息队列需要绑定端口,那就只给 NET_BIND_SERVICE 权限,其他全部丢掉。
嗯,说到这里,环境准备这块基本就齐了。你可能会问:「这么多配置,每次都要手写吗?」别急,下一章我会带大家做一个自动化脚本,把这些配置一键搞定。但今天,先把这些概念吃透。
记住一句话:边缘计算的环境准备,不是「能跑就行」,而是「跑得稳、跑得久、跑得安全」。我在项目里吃过太多亏,希望你别重蹈覆辙。
我的习惯: 每配置完一个环境,我都会写一个 README 文档,把网络拓扑、端口映射、资源限制都记下来。半年后回来维护,你会感谢当时的自己。