Docker 部署
本文说明 ovra-zero 使用纯 Docker 的部署方式,不依赖 k3d、Kubernetes 或 Helm。适合单机服务器、开发测试环境,以及希望先用容器把后端服务跑起来的场景。
当前仓库中的 deploy/docker/docker-compose.yaml 仍是占位文件,本文以 docker network、docker run 和服务镜像构建为主。需要 Kubernetes 本地集群部署时,请参考 k3d 部署。
准备工作
环境要求
| 环境 | 说明 |
|---|---|
| Docker | 运行 MySQL、Redis、etcd 和后端服务 |
Go 1.24+ | 构建 Linux 服务二进制 |
MySQL 8.0+ | 业务数据库 |
Redis 7+ | 缓存、验证码、幂等控制 |
etcd 3.5+ | go-zero RPC 服务发现 |
服务端口
| 服务 | 容器名 | 容器端口 | 宿主机端口 |
|---|---|---|---|
| MySQL | ovra-zero-mysql | 3306 | 3306 |
| Redis | ovra-zero-redis | 6379 | 6379 |
| etcd | ovra-zero-etcd | 2379 | 2379 |
| auth | ovra-zero-auth | 8091 | 8091 |
| system | ovra-zero-system | 8092 / 9092 | 8092 / 9092 |
| demo | ovra-zero-demo | 8099 / 9099 | 8099 / 9099 |
创建 Docker 网络
创建统一网络,后续容器通过服务名互相访问:
docker network create ovra-zero
如果网络已存在,Docker 会提示重复创建,可以忽略。
启动基础组件
MySQL
docker run -d --name ovra-zero-mysql --network ovra-zero \
-p 3306:3306 \
-e MYSQL_ROOT_PASSWORD='Pl@1221view' \
-e MYSQL_DATABASE=ovra_zero \
-v "$PWD/bin/sql/ovra_zero.sql:/docker-entrypoint-initdb.d/ovra_zero.sql:ro" \
mysql:8.4
查看初始化日志:
docker logs ovra-zero-mysql --tail=100
Redis
docker run -d --name ovra-zero-redis --network ovra-zero \
-p 6379:6379 \
redis:7-alpine redis-server --requirepass 'Pl@1221view'
验证:
docker exec ovra-zero-redis redis-cli -a 'Pl@1221view' ping
etcd
docker run -d --name ovra-zero-etcd --network ovra-zero \
-p 2379:2379 \
-p 2380:2380 \
quay.io/coreos/etcd:v3.5.13 \
etcd \
--name ovra-zero-etcd \
--listen-client-urls http://0.0.0.0:2379 \
--advertise-client-urls http://ovra-zero-etcd:2379 \
--listen-peer-urls http://0.0.0.0:2380 \
--initial-advertise-peer-urls http://ovra-zero-etcd:2380 \
--initial-cluster ovra-zero-etcd=http://ovra-zero-etcd:2380 \
--initial-cluster-state new \
--initial-cluster-token ovra-zero-etcd
验证:
docker exec ovra-zero-etcd etcdctl --endpoints=http://127.0.0.1:2379 endpoint health
准备 Docker 配置
服务在容器中需要访问 Docker 网络内的服务名,不能继续使用 127.0.0.1。建议创建一套 Docker 环境配置:
mkdir -p etc/docker
cp etc/dev/common.yaml etc/docker/common.yaml
cp etc/dev/auth.yaml etc/docker/auth.yaml
cp etc/dev/system.yaml etc/docker/system.yaml
cp etc/dev/demo.yaml etc/docker/demo.yaml
编辑 etc/docker/common.yaml,把地址改为容器名:
RpcConf:
Etcd:
Hosts:
- ovra-zero-etcd:2379
SystemRpc:
Etcd:
Hosts:
- ovra-zero-etcd:2379
Data:
Database:
Username: root
Password: Pl@1221view
Host: ovra-zero-mysql
Port: 3306
Database: ovra_zero
Redis:
Pass: Pl@1221view
Host: ovra-zero-redis:6379
Type: node
Tls: false
程序默认按 ENV 读取 etc/<ENV>/<service>.yaml。容器启动时设置 ENV=docker 后,会读取 etc/docker/auth.yaml、etc/docker/system.yaml、etc/docker/demo.yaml,并自动合并同目录的 common.yaml。
构建服务镜像
先编译 Linux 二进制到项目根目录。ARM64:
GOOS=linux GOARCH=arm64 CGO_ENABLED=0 go build -ldflags='-s -w' -tags no_k8s -o app-auth app/auth/auth.go
GOOS=linux GOARCH=arm64 CGO_ENABLED=0 go build -ldflags='-s -w' -tags no_k8s -o app-system app/system/system.go
GOOS=linux GOARCH=arm64 CGO_ENABLED=0 go build -ldflags='-s -w' -tags no_k8s -o app-demo app/demo/demo.go
x86_64 环境将 GOARCH=arm64 改为:
GOARCH=amd64
构建镜像:
docker build -t ovra-zero-auth:local -f deploy/docker/auth/Dockerfile .
docker build -t ovra-zero-system:local -f deploy/docker/system/Dockerfile .
docker build -t ovra-zero-demo:local -f deploy/docker/demo/Dockerfile .
启动后端服务
建议先启动 system,再启动 auth 和 demo。
system
docker run -d --name ovra-zero-system --network ovra-zero \
-e ENV=docker \
-p 8092:8092 \
-p 9092:9092 \
ovra-zero-system:local
auth
docker run -d --name ovra-zero-auth --network ovra-zero \
-e ENV=docker \
-p 8091:8091 \
ovra-zero-auth:local
demo
docker run -d --name ovra-zero-demo --network ovra-zero \
-e ENV=docker \
-p 8099:8099 \
-p 9099:9099 \
ovra-zero-demo:local
查看日志:
docker logs ovra-zero-system --tail=100
docker logs ovra-zero-auth --tail=100
docker logs ovra-zero-demo --tail=100
验证系统
查看容器:
docker ps --format 'table {{.Names}}\t{{.Status}}\t{{.Ports}}'
验证 etcd 注册:
docker exec ovra-zero-etcd etcdctl --endpoints=http://127.0.0.1:2379 get system.rpc --prefix
验证接口:
curl -sS http://127.0.0.1:8091/auth/code
curl -sS http://127.0.0.1:8092/system/user/getInfo
/system/user/getInfo 需要认证时返回未登录或鉴权错误也属于服务已正常响应。
可选:使用 Traefik
如果希望统一入口,可以把 bin/traefik 配置挂载到 Traefik 容器,并让 Traefik 加入同一个 Docker 网络。需要确保动态配置中的服务地址指向:
ovra-zero-auth:8091
ovra-zero-system:8092
ovra-zero-demo:8099
示例:
docker run -d --name ovra-zero-traefik --network ovra-zero \
-p 28080:28080 \
-v "$PWD/bin/traefik:/etc/traefik:ro" \
traefik:v3.0 \
--configfile=/etc/traefik/traefik.yaml
停止与清理
停止服务:
docker stop ovra-zero-auth ovra-zero-system ovra-zero-demo
docker stop ovra-zero-etcd ovra-zero-redis ovra-zero-mysql
删除容器:
docker rm ovra-zero-auth ovra-zero-system ovra-zero-demo
docker rm ovra-zero-etcd ovra-zero-redis ovra-zero-mysql
删除网络:
docker network rm ovra-zero
常见问题
服务连接不上 MySQL、Redis 或 etcd
确认容器处于同一个 Docker 网络:
docker network inspect ovra-zero
确认 etc/docker/common.yaml 中使用的是容器名,不是 127.0.0.1。
auth 调用 system 失败
先确认 system 已启动并完成 RPC 注册:
docker logs ovra-zero-system --tail=100
docker exec ovra-zero-etcd etcdctl --endpoints=http://127.0.0.1:2379 get system.rpc --prefix
exec format error
说明二进制架构和镜像运行架构不一致。ARM64 使用 GOARCH=arm64,x86_64 使用 GOARCH=amd64,重新构建二进制和镜像。
数据没有初始化
MySQL 只会在首次创建空数据目录时执行 /docker-entrypoint-initdb.d 中的 SQL。若容器已初始化过,需要删除容器和数据卷后重建,或手动导入:
docker exec -i ovra-zero-mysql mysql -uroot -p'Pl@1221view' ovra_zero < bin/sql/ovra_zero.sql