modify: 消息模块
tests / ubuntu-latest / py3.13 (push) Has been cancelled
tests / windows-latest / py3.13 (push) Has been cancelled
tests / ubuntu-latest / py3.13 (pull_request) Has been cancelled
tests / windows-latest / py3.13 (pull_request) Has been cancelled

This commit is contained in:
2026-09-17 11:23:34 +08:00
parent e0d5bad7b2
commit 9dc2dde59f
6 changed files with 852 additions and 0 deletions
+3
View File
@@ -0,0 +1,3 @@
# 密码文件与证书都是本机生成的,不进仓库
config/passwd
config/certs/
+50
View File
@@ -0,0 +1,50 @@
# svfs 消息模块的 ACL 示例(最小权限)。默认**未启用**——要用就在
# mosquitto.conf 里解开 allow_anonymous false / password_file / acl_file 三行,
# 否则这份文件不会生效。
#
# 规则先记两条,踩坑都出在这儿:
#
# * 这里的 <用户名> 是 **MQTT 连接的 username**。客户端默认用 svfs 登录名
# (settings.mqtt_config:mqtt_username 留空 = 登录名),所以通常两者一致;
# 在设置里覆盖过 broker 账号时,以覆盖后的为准。
# * 组织标识(下面的 default)要**换成你的 SVFS_ORG**,且不能写成通配——
# 多租户隔离靠的就是这一段。用户名里有特殊字符时按百分号编码填
# (拿 svfs_client.topics.topic_segment 算一下,例如「张三」→ %E5%BC%A0%E4%B8%89)。
# ---- 匿名段:第一个 user 之前的规则属于匿名连接 ----------------------
#
# 开了 allow_anonymous false 后这一段就没用了(示例服务端届时要用下面的
# svfs-server 账号发布)。留着是为了「允许匿名发布、但读取仍受控」的折中场景。
topic write svfs/default/user/+/message
topic write svfs/default/user/+/plugin/+
topic write svfs/default/broadcast/#
# ---- 服务端发布账号 --------------------------------------------------
#
# 服务端要能给任意用户写消息;它只需要写,不需要读。
user svfs-server
topic write svfs/default/user/+/message
topic write svfs/default/user/+/plugin/+
topic write svfs/default/broadcast/#
topic write svfs/default/broadcast/plugin/+
# ---- 客户端:每人只读自己那两条订阅主题 ------------------------------
#
# 客户端登录后订阅的是 svfs/<org>/user/<自己>/# 与 svfs/<org>/broadcast/#,
# 所以只给这些就够(读不到别人的消息、也没有写权限)。
user alice
topic read svfs/default/user/alice/#
topic read svfs/default/broadcast/#
user bob
topic read svfs/default/user/bob/#
topic read svfs/default/broadcast/#
# ---- 等价的通配写法(可选) ------------------------------------------
#
# 用户多了不想一个个写,可以用 pattern:%u 会被替换成连接用的用户名。
# 前提是 %u 独占一个主题层级(不能写成 svfs/default/user/%u-2/# 这种)。
# 注意 pattern 对所有用户生效(包括匿名与 svfs-server),所以这里只给读。
#
# pattern read svfs/default/user/%u/#
# pattern read svfs/default/broadcast/#
+62
View File
@@ -0,0 +1,62 @@
# svfs 消息模块用的 mosquitto 配置(挂到容器的 /mosquitto/config/mosquitto.conf)。
#
# 默认这份是「内网匿名」:能立刻跑起来,但任何能连到 1883 的人都能收发消息,
# 只适合内网/开发。下面另有「认证 + ACL」与「TLS」两个注释段,要用时解开,
# 完整说明(含客户端怎么配)见 docs/mqtt-guide.md 的「二、Docker 部署 broker」。
# ---- 监听与放行 ------------------------------------------------------
#
# mosquitto 2.x 的规矩:一旦定义了 listener,allow_anonymous 的默认值就是
# false——不显式写这一行,客户端会被直接拒连("能连上端口却连不上 broker"
# 的典型来源)。同理,不定义 listener 时只接受 loopback 连接。
listener 1883
allow_anonymous true
# ---- 数据与日志 ------------------------------------------------------
#
# 本模块实际用的是 QoS 0 + clean session(见 docs/mqtt-guide.md),持久化本身
# 帮不上什么忙;留着它只是为了以后调 QoS、用 retained 消息时不用回头改配置。
persistence true
persistence_location /mosquitto/data/
# 同时往 stdout 和文件写:compose logs 看实时,./log 留档。
log_dest stdout
log_dest file /mosquitto/log/mosquitto.log
log_type all
# ---- 认证 + ACL(可选,生产该开) ------------------------------------
#
# 要开认证,按顺序做三件事:
# 1) 造密码文件(用户名就用 svfs 的登录名,客户端默认拿它当 broker 用户名):
# docker compose exec mqtt mosquitto_passwd -c -b /mosquitto/config/passwd alice 密码
# docker compose exec mqtt mosquitto_passwd -b /mosquitto/config/passwd svfs-server 服务端密码
# (-c 会覆盖已有文件,之后加用户不要再带 -c;Linux 上宿主的 config/ 目录
# 属主不是 uid 1883 时会写不进去,先 sudo chown -R 1883:1883 config)
# 2) 客户端侧准备 broker 密码:它的默认值是**登录 token**,和这里的静态密码
# 对不上,连接会被拒(CONNACK code=4/5)。两条路:
# * 在客户端 settings.json 里写 mqtt_password(见 docs/mqtt-guide.md 三);
# * 或由服务端在登录响应里下发 mqtt.password(推荐,用户端零配置)。
# 3) 解开下面三行,重启容器。
#
# allow_anonymous false
# password_file /mosquitto/config/passwd
# acl_file /mosquitto/config/acl
#
# 注意:开了认证之后示例服务端(examples/plugin_server.py)也会连不上——
# 它的 _mqtt_publish 不带 broker 账号,得给它加 SVFS_MQTT_USER/SVFS_MQTT_PASS
# 的几行补丁,或让它用独立的发布账号(docs/mqtt-guide.md 有现成代码)。
# ---- TLS(可选) -----------------------------------------------------
#
# 解开这段起 8883,同时把 compose 里的 8883 端口映射打开。
# 证书放进 config/certs/(.gitignore 已挡住),容器内路径就是 /mosquitto/config/certs/…。
#
# 重要:客户端只做「系统信任库 + CERT_REQUIRED」校验,没有单独的 CA 配置项
# (设置里的 ca_bundle 只作用于 HTTP)。所以自签证书必须把 CA 装进**每台
# 客户端的系统信任库**,否则握手一定失败——内网先用明文 1883 往往更省事。
#
# listener 8883
# allow_anonymous false
# cafile /mosquitto/config/certs/ca.crt
# certfile /mosquitto/config/certs/server.crt
# keyfile /mosquitto/config/certs/server.key
+31
View File
@@ -0,0 +1,31 @@
# MQTT broker(mosquitto 2.x):svfs 消息模块的实时推送通道。
#
# docker compose up -d # 起
# docker compose logs -f mqtt # 看日志(配置里 log_dest stdout)
# docker compose down # 停
#
# 默认配置是「内网匿名」——能跑起来,但任何能连到 1883 的人都收发得到消息,
# 只适合内网/开发。上认证、ACL、TLS 见 config/mosquitto.conf 里的三个注释段,
# 完整说明见 docs/mqtt-guide.md 的「二、Docker 部署 broker」。
services:
mqtt:
image: eclipse-mosquitto:2
container_name: svfs-mqtt
restart: unless-stopped
ports:
- "1883:1883" # 明文:内网/开发(默认只开这个)
# - "8883:8883" # TLS:解 config/mosquitto.conf 的 TLS 段、放好证书再开这个
volumes:
# 配置目录整份挂进去(conf / acl / passwd / certs 都在这里)。
# 挂目录而不是单个文件:mosquitto_passwd 要往这里写密码文件,
# 只挂文件的话写进去的东西会落在容器层,重启就没了。
- ./config:/mosquitto/config
# 数据与日志用具名卷:容器里的 mosquitto 用户是 uid 1883,用宿主目录
# 在 Linux 上常撞权限错误;具名卷由 Docker 按镜像里的属主创建,开箱即用。
- mqtt-data:/mosquitto/data
- mqtt-log:/mosquitto/log
volumes:
mqtt-data:
mqtt-log: