eventRT/deploy/deploy.md

20 KiB
Raw Blame History

项目部署指南

本项目依赖 MongoDB(事件持久化存储)与 RabbitMQmTLS 消息队列),并通过 OpenTelemetry + Jaeger 完成链路追踪。

前提条件

  1. 已安装 Dockerkubectl
  2. Minikube 集群已启动并可访问
  3. 确保以下端口在宿主机上未被占用:27017MongoDB5671RabbitMQ AMQP

1. 部署 MongoDB 数据库

EventRT 支持两种 MongoDB 部署方式,根据场景二选一:Docker(本地开发 / Ubuntu 宿主机直跑)或 K8sMinikube 环境)。

1.1 Docker 部署(本地开发)

使用官方 mongo:7.0 镜像,在 Ubuntu 宿主机(192.168.1.101)上以 Docker 容器运行。

1.1.1 部署命令
docker run --name mongodb \
  -e MONGO_INITDB_ROOT_USERNAME=coslight \
  -e MONGO_INITDB_ROOT_PASSWORD=coslight@tj \
  -p 27017:27017 \
  -d mongo:7.0
1.1.2 连接信息
参数 说明
容器名称 mongodb 容器名
镜像版本 mongo:7.0 MongoDB 7.0
主机端口 27017 外部应用连接端口
用户名 coslight Root 管理员
密码 coslight@tj 启动时通过 MONGO_INITDB_ROOT_PASSWORD 设置
鉴权数据库 admin auth_db
业务数据库 eventdb EventRT 事件存储库
1.1.3 状态检查
# 检查容器启动状态
docker ps -a | grep mongodb
# 检查启动日志
docker logs mongodb

注意: 密码当前以明文形式写在 docker run 命令中,生产环境应通过 Docker Secret 或环境变量文件(--env-file)传入,避免在 Shell 历史记录中留存明文密码。

1.1.4 连接验证
# 快速检查 MongoDB 是否接受连接
docker exec -it mongodb mongosh \
  -u coslight -p "coslight@tj" --authenticationDatabase admin \
  --eval "db.adminCommand({ ping: 1 })"

# 列出所有数据库(确认服务正常)
docker exec -it mongodb mongosh \
  -u coslight -p "coslight@tj" --authenticationDatabase admin \
  --eval "show dbs"
1.1.5 初始化 eventdb 数据库

MongoDB 启动后进入容器,为 eventdb 库授权:

docker exec -it mongodb mongosh \
  -u coslight -p "coslight@tj" --authenticationDatabase admin

mongosh 中执行:

// 切换到 eventdb若不存在则自动创建
use eventdb

// 授予 coslight 用户对 eventdb 的读写权限(根用户已有全库权限,此步可选)
db.createUser({
  user: "coslight",
  pwd:  "coslight@tj",
  roles: [{ role: "readWrite", db: "eventdb" }]
})

1.2 K8s 部署Minikube

YAML 文件位于 deploy/k8s/(从 modelrt 仓库迁移而来,需确认文件已拷贝至本项目)。

kubectl apply -f deploy/k8s/mongodb-secret.yaml
kubectl apply -f deploy/k8s/mongodb-pvc.yaml
kubectl apply -f deploy/k8s/mongodb-statefulset.yaml
kubectl apply -f deploy/k8s/mongodb-service.yaml
参数 说明
镜像 mongo:7.0 MongoDB 7.0
NodePort 30017 集群外访问端口
用户名 admin Root 管理员Secret mongodb-secret
密码 coslight Secret mongodb-secret 中配置,生产环境请替换强密码
存储 2Gi PVC mongodb-data
CPU 100m 请求 / 500m 上限 StatefulSet resources 字段
内存 256Mi 请求 / 512Mi 上限 StatefulSet resources 字段

注意: 密码存储在 mongodb-secret.yamlstringData 中,生产环境应替换为强密码,并避免将明文密码提交至版本库。

1.2.1 等待 Pod 就绪
kubectl wait --for=condition=ready pod -l app=mongodb --timeout=120s
1.2.2 连接验证
kubectl exec -it $(kubectl get pod -l app=mongodb -o jsonpath='{.items[0].metadata.name}') \
  -- mongosh -u admin -p coslight --authenticationDatabase admin \
  --eval "db.adminCommand({ ping: 1 })"
1.2.3 初始化 eventdb 数据库
kubectl exec -it $(kubectl get pod -l app=mongodb -o jsonpath='{.items[0].metadata.name}') \
  -- mongosh -u admin -p coslight --authenticationDatabase admin

mongosh 中执行:

use eventdb

db.createUser({
  user: "coslight",
  pwd:  "coslight@tj",
  roles: [{ role: "readWrite", db: "eventdb" }]
})
1.2.4 状态检查
kubectl get pods -l app=mongodb
kubectl logs -l app=mongodb --tail=30

2. 部署 RabbitMQKubernetes

RabbitMQ 配置为仅允许 TLS 连接(listeners.tcp = none),所有客户端须持有由同一 CA 签发的证书。YAML 文件位于 deploy/mq/

2.1 TLS 证书生成

2.1.1 生成根 CA
git clone https://github.com/rabbitmq/tls-gen.git
cd tls-gen/basic

# 生成根 CA结果输出至 result/
make CN=rabbitmq-server
# ca_certificate.pem 与 ca_key.pem即 cakey.pem生成于 result/
2.1.2 生成服务端证书

服务端证书需包含 SAN使其同时匹配集群内 DNS 和 Minikube IP。使用 deploy/mq/server.conf(已预置正确配置):

# 将 ca_certificate.pem 和 cakey.pem 放在当前目录
openssl genrsa -out server_key.pem 2048

openssl req -new -key server_key.pem \
    -out server_cert.csr -config deploy/mq/server.conf

openssl x509 -req -in server_cert.csr \
    -CA ca_certificate.pem -CAkey cakey.pem -CAcreateserial \
    -out server_certificate.pem -days 730 -sha256 \
    -extfile deploy/mq/server.conf -extensions v3_server

rm server_cert.csr
2.1.3 生成 EventRT 客户端证书

CN 必须与 RabbitMQ 中注册的用户名一致(eventrt-client)。使用 deploy/mq/eventrt.conf

openssl genrsa -out eventrt_client_key.pem 2048

openssl req -new -key eventrt_client_key.pem \
    -out eventrt_client.csr -config deploy/mq/eventrt.conf

openssl x509 -req -in eventrt_client.csr \
    -CA ca_certificate.pem -CAkey cakey.pem -CAcreateserial \
    -out eventrt_client_cert.pem -days 365 \
    -extensions v3_client -extfile deploy/mq/eventrt.conf

rm eventrt_client.csr
2.1.4 生成 ModelRT 客户端证书

使用 deploy/mq/modelrt.confCN 为 modelrt-client

openssl genrsa -out modelrt_client_key.pem 2048

openssl req -new -key modelrt_client_key.pem \
    -out modelrt_client.csr -config deploy/mq/modelrt.conf

openssl x509 -req -in modelrt_client.csr \
    -CA ca_certificate.pem -CAkey cakey.pem -CAcreateserial \
    -out modelrt_client_cert.pem -days 365 \
    -extensions v3_client -extfile deploy/mq/modelrt.conf

rm modelrt_client.csr
2.1.5 验证证书
# 验证服务端证书
openssl verify -CAfile ca_certificate.pem server_certificate.pem

# 验证客户端证书
openssl verify -CAfile ca_certificate.pem eventrt_client_cert.pem
openssl verify -CAfile ca_certificate.pem modelrt_client_cert.pem

# 确认 CN 和扩展clientAuth / serverAuth
openssl x509 -in server_certificate.pem -noout -subject -ext subjectAltName
openssl x509 -in eventrt_client_cert.pem -noout -subject -text | grep -A1 "Extended Key Usage"
openssl x509 -in modelrt_client_cert.pem -noout -subject

2.2 部署 RabbitMQ

2.2.1 创建证书 Secret

在证书文件所在目录执行:

sh deploy/mq/secert.sh

该脚本等价于:

kubectl create secret generic rabbitmq-certs \
  --from-file=ca_certificate.pem=./certs/ca_certificate.pem \
  --from-file=server_certificate.pem=./certs/server_certificate.pem \
  --from-file=server_key.pem=./certs/server_key.pem
2.2.2 部署
kubectl apply -f deploy/mq/rabbitmq-secret.yaml
kubectl apply -f deploy/mq/rabbitmq-users-config.yaml
kubectl apply -f deploy/mq/rabbitmq-config.yaml
kubectl apply -f deploy/mq/rabbitmq-deployment.yaml
kubectl apply -f deploy/mq/rabbitmq-service.yaml
2.2.3 端口汇总
端口 NodePort 说明
5671 30671 AMQP over TLS客户端连接
5672 30672 AMQP 明文(内部备用,生产禁用)
15671 31671 Management UI over TLS
15672 31672 Management UI 明文(内部备用)
2.2.4 用户与权限说明

用户定义在 rabbitmq-users-config.yamldefinitions.json 中,启动时通过 load_definitions 自动加载:

用户 认证方式 权限 说明
coslight 密码 administrator 管理员,密码在 rabbitmq-secret.yaml
eventrt-client X.509 证书CN configure/read/write EventRT 服务专用
modelrt-client X.509 证书CN configure/read/write ModelRT 服务专用
web-client X.509 证书CN read/write Web 客户端

注意: 证书认证用户的 password_hash 留空RabbitMQ 通过 ssl_cert_login_from = common_name 将证书 CN 映射为用户名。


3. 部署 EventRTKubernetes

所有资源部署在 default 命名空间YAML 文件位于 deploy/k8s/

3.1 构建并推送镜像

镜像采用三阶段构建,最终基于 scratch

阶段 基础镜像 作用
builder golang:1.26-alpine 编译 Go 二进制(CGO_ENABLED=0-trimpath -ldflags="-s -w"
certs alpine:3.21 提取 CA 证书、时区数据及非 root 用户定义UID 默认 1000
runtime scratch 仅含可执行文件与运行时依赖,无 shell、无包管理器

方式一:从源码构建并加载

# 在项目根目录执行(默认运行用户 UID=1000
docker build -f deploy/dockerfile/eventrt.Dockerfile -t coslight/eventrt:latest .

# 自定义运行用户 UID
docker build -f deploy/dockerfile/eventrt.Dockerfile \
  --build-arg USER_ID=2000 \
  -t coslight/eventrt:latest .

# 加载到 Minikube无需私有仓库
minikube image load coslight/eventrt:latest

方式二:直接加载已有本地镜像

Ubuntu 宿主机上已存在构建好的镜像(如 eventrt:v1)时,无需重新构建,直接导入 Minikube

# 确认本地镜像存在
docker images eventrt:v1

# 加载到 Minikube
minikube image load eventrt:v1

# 验证镜像已进入 Minikube 缓存
minikube image ls | grep eventrt

注意: deploy/k8s/eventrt-deployment.yaml 中的 image 字段需与加载的镜像名称一致,并将 imagePullPolicy 设为 Never,防止 Minikube 尝试从远端拉取。

3.1.1 镜像冒烟测试

# 查看镜像大小scratch 镜像预期 ≤ 25 MB
docker images coslight/eventrt:latest

# 检查镜像元信息(确认 User、Cmd、架构
docker inspect coslight/eventrt:latest

# 验证二进制可执行(无 config 时程序报错退出属预期行为,说明镜像构建正常)
docker run --rm coslight/eventrt:latest

# 挂载示例配置做完整启动验证Ctrl+C 退出)
docker run --rm \
  -v "$(pwd)/configs/config.example.yaml:/app/configs/config.yaml" \
  -p 8081:8081 \
  coslight/eventrt:latest

注意: scratch 镜像不含 shell无法使用 docker exec 进入容器调试;如需排查问题,可临时将最终阶段改为 alpine 进行本地调试,确认后再切回 scratch

3.2 创建客户端证书 Secret

在 RabbitMQ TLS 证书生成完成后(见 2.1),进入证书文件所在目录执行:

sh deploy/k8s/eventrt-certs-secret.sh

该脚本等价于:

kubectl create secret generic eventrt-certs \
  --from-file=ca_certificate.pem=./ca_certificate.pem \
  --from-file=eventrt_client_cert.pem=./eventrt_client_cert.pem \
  --from-file=eventrt_client_key.pem=./eventrt_client_key.pem

3.3 部署

kubectl apply -f deploy/k8s/eventrt-secret.yaml
kubectl apply -f deploy/k8s/eventrt-configmap.yaml
kubectl apply -f deploy/k8s/eventrt-deployment.yaml
kubectl apply -f deploy/k8s/eventrt-service.yaml

等待 Pod 就绪:

kubectl wait --for=condition=ready pod -l app=eventrt --timeout=120s

3.4 配置说明

配置项 方式 说明
mongodb.password Secret eventrt-secret 不写入 ConfigMap通过环境变量 MONGODB_PASSWORD 注入
service.secret_key Secret eventrt-secret 不写入 ConfigMap通过环境变量 SERVICE_SECRET_KEY 注入
RabbitMQ 客户端证书 Secret eventrt-certs 挂载至 /app/configs/certs/
config.yaml 其余配置 ConfigMap eventrt-config rabbitmq.host 已设为 K8s Service 名 rabbitmq-service
K8S_NAMESPACE / K8S_NODE_NAME Downward API 注入至日志全局字段

3.5 状态检查

# 查看 Pod 状态
kubectl get pods -l app=eventrt

# 查看启动日志
kubectl logs -l app=eventrt --tail=50

# 查看 Service
kubectl get svc eventrt-service

3.6 端口汇总

NodePort 说明
30081 EventRT HTTP API

3.7 清理

kubectl delete -f deploy/k8s/eventrt-service.yaml \
               -f deploy/k8s/eventrt-deployment.yaml \
               -f deploy/k8s/eventrt-configmap.yaml \
               -f deploy/k8s/eventrt-secret.yaml
kubectl delete secret eventrt-certs

4. Mac 本地访问SSH 隧道)

EventRT 在 Mac 本地运行时RabbitMQ 部署在 Ubuntu 宿主机(192.168.1.101)的 Minikube 中MongoDB 直接运行在宿主机上。需通过 SSH 本地端口转发建立访问隧道。

4.1 网络拓扑

Mac 本地端口  ──SSH隧道──▶  Ubuntu 宿主机 (192.168.1.101)  ──▶  Minikube NodePort (192.168.49.2)
                                       └──▶  MongoDB Docker (宿主机 27017)

4.2 建立隧道

ssh -L 27017:127.0.0.1:27017 \
    -L 5671:192.168.49.2:30671 \
    -L 15671:192.168.49.2:31671 \
    -L 4318:192.168.49.2:31318 \
    -L 16686:192.168.49.2:31686 \
    douxu@192.168.1.101

如需后台静默运行(不占用终端):

ssh -fN \
    -L 27017:127.0.0.1:27017 \
    -L 5671:192.168.49.2:30671 \
    -L 15671:192.168.49.2:31671 \
    -L 4318:192.168.49.2:31318 \
    -L 16686:192.168.49.2:31686 \
    douxu@192.168.1.101

4.3 端口映射说明

Mac 本地端口 目标 服务 说明
27017 宿主机 127.0.0.1:27017 MongoDB EventRT 事件数据库
5671 Minikube 192.168.49.2:30671 RabbitMQ AMQP 消息队列 mTLS 连接
15671 Minikube 192.168.49.2:31671 RabbitMQ Management 管理界面 http://localhost:15671
4318 Minikube 192.168.49.2:31318 OTLP HTTP OTel Trace 上报Jaeger Collector
16686 Minikube 192.168.49.2:31686 Jaeger UI 链路追踪查询 http://localhost:16686

注意: 隧道建立后,本地 config.yaml 中所有服务地址填 localhost:<本地端口> 即可直接运行服务。

4.4 关闭隧道

前台运行时直接 Ctrl+C;后台运行时查找并终止进程:

# 找到 ssh 隧道进程
ps aux | grep "ssh -fN"
# 终止(替换为实际 PID
kill <PID>

5. 本地运行go run / 二进制)

5.1 配置服务配置文件

configs/config.example.yaml 复制为 configs/config.yaml 并按以下说明调整:

5.1.1 配置参数说明
类别 参数名 作用描述 示例值
MongoDB host MongoDB 服务器地址 "localhost"
port MongoDB 端口 27017
user 连接用户名 "coslight"
password 连接密码 "coslight@tj"
database 业务数据库名 "eventdb"
auth_db 鉴权数据库 "admin"
timeout 连接超时(秒) 10
RabbitMQ host RabbitMQ 服务器地址 "localhost"
port AMQP over TLS 端口 5671
server_name TLS SNI / 证书 CN "rabbitmq-server"
ca_cert_path CA 证书路径 "./configs/certs/ca_certificate.pem"
client_cert_path 客户端证书路径 "./configs/certs/eventrt_client_cert.pem"
client_key_path 客户端私钥路径 "./configs/certs/eventrt_client_key.pem"
insecure_skip_verify 是否跳过证书校验(开发临时用) false
Logger (Zap) mode 日志模式 development / production "development"
level 最低日志级别 "debug"
filepath 日志文件路径(空字符串输出到 stdout ""
maxsize 单文件最大大小MB 1
maxbackups 保留旧文件最大个数 5
maxage 保留旧文件最大天数 30
compress 是否压缩备份文件 false
Service service_addr HTTP 监听地址 ":8081"
service_name 服务名(日志/监控标识) "eventRT"
secret_key 内部签名密钥 "eventrt_key"
deploy_env 部署环境 development / production "development"
OTel endpoint OTLP HTTP 上报地址(不含协议前缀) "localhost:4318"
insecure 是否不启用 TLS true

5.2 编译 EventRT 服务

go build -o eventrt main.go

5.3 启动服务

./eventrt

5.4 检测服务启动日志

控制台输出 starting EventRT server 后即代表服务启动成功。


6. 排查手册

6.1 证书权限检查

确认客户端证书包含 TLS Web Client Authentication

openssl x509 -in configs/certs/eventrt_client_cert.pem -noout -text \
  | grep -A1 "Extended Key Usage"

预期输出包含 TLS Web Client Authentication

6.2 握手连通性验证

openssl s_client -connect localhost:5671 \
    -cert configs/certs/eventrt_client_cert.pem \
    -key  configs/certs/eventrt_client_key.pem \
    -CAfile configs/certs/ca_certificate.pem

预期结果:看到 Verify return code: 0 (ok)

6.3 RabbitMQ 日志检查

连接成功后RabbitMQ 日志应出现:

connection <xxx>: user 'eventrt-client' authenticated and granted access to vhost '/'

查看 Pod 日志:

kubectl logs -l app=rabbitmq --tail=50 | grep eventrt-client

6.4 MongoDB 连通性验证

mongosh "mongodb://coslight:coslight@tj@localhost:27017/eventdb?authSource=admin"

预期进入 mongosh 提示符,执行 show collections 无报错。


7. 后续操作(停止与清理)

7.1 本地 Docker 部署清理

适用于第 1 节使用 docker run 启动的 MongoDB 容器。

# 停止容器
docker stop mongodb

# 删除容器(容器内数据将同步丢失)
docker rm mongodb

7.2 本地 go run 运行清理

适用于第 5 节以 go run 或编译后二进制方式在本地启动的 EventRT 服务。

前台运行时直接 Ctrl+C 终止;后台运行时查找并终止进程:

# 终止 go run 启动的进程
pkill -f "go run main.go"

# 或终止编译后的二进制进程
pkill eventrt

7.3 K8s(Minikube) 部署清理

适用于第 1.2、2、3 节在 Minikube 中部署的所有资源。

7.3.1 分服务清理

仅停止(缩容至 0PVC 数据与 Secret 保留)

将所有 Deployment 和 StatefulSet 缩容至 0 副本Pod 停止运行但持久卷数据不删除,之后可直接缩容回 1 恢复服务。

# 停止所有 DeploymentEventRT / RabbitMQ
kubectl scale deployment eventrt rabbitmq --replicas=0

# 停止 MongoDB StatefulSetPVC 数据保留)
kubectl scale statefulset mongodb --replicas=0

恢复时:

kubectl scale deployment eventrt rabbitmq --replicas=1
kubectl scale statefulset mongodb --replicas=1

永久清理(删除所有资源,数据不可恢复)

按部署顺序反向删除各服务资源:

# EventRT 应用
kubectl delete -f deploy/k8s/eventrt-service.yaml \
               -f deploy/k8s/eventrt-deployment.yaml \
               -f deploy/k8s/eventrt-configmap.yaml \
               -f deploy/k8s/eventrt-secret.yaml
kubectl delete secret eventrt-certs

# MongoDB
kubectl delete -f deploy/k8s/mongodb-service.yaml \
               -f deploy/k8s/mongodb-statefulset.yaml \
               -f deploy/k8s/mongodb-pvc.yaml \
               -f deploy/k8s/mongodb-secret.yaml

# RabbitMQ
kubectl delete -f deploy/mq/rabbitmq-service.yaml \
               -f deploy/mq/rabbitmq-deployment.yaml \
               -f deploy/mq/rabbitmq-users-config.yaml \
               -f deploy/mq/rabbitmq-config.yaml \
               -f deploy/mq/rabbitmq-secret.yaml
kubectl delete secret rabbitmq-certs
7.3.2 一键清理

注意: 此操作会删除 deploy/k8s/deploy/mq/ 下所有 YAML 对应的 K8s 资源,请确认后执行。

kubectl delete -f deploy/k8s/ -f deploy/mq/
kubectl delete secret eventrt-certs rabbitmq-certs