放:1W 台设备的话可能就有 1~3 万个 topic 在 broker 运行,一般 4H16G 的 linux 服务器撑不撑得住?
不放:只设两个 topic ,down 和 up, 设备 id 放在载荷里,但是每次单点发布时,其实会给所有设备都发送一遍,pps 撑不撑得住,通讯模块是否会接受到很多无用信息,影响处理性能?
还有一个群发的应用场景,请问如何实现最好。(无网关,目前采用的是遍历发送)

有必要,设备上行的消息可以发给同一个或多个 topic ,但是设备最好自己订阅自己特有的 topic

没有设备 ID 在 topic 中,server 可能会保存 topic 数据,严重影响性能。所以使用设备 ID 做为 topic 好。群发的话,看 QOS 和 cleanSession 如何设置的,和前面的问题一样,导致 server 要保存 topic 的数据的话,最好使用设备相差的 topic ,程序遍历发送,如果不用 server 保存 topic 数据的话,可以使用设备无关的同一 topic 。

"每次单点发布时,其实会给所有设备都发送一遍"----设备的网络流量抗得住吗?

撑得住,现在流量费很便宜

broker 运行 2W 个 topic 会有性能问题吗

mqtt 在线和离线,不是统一监听系统级别 Topic ,message 里面有设备 id 吗, 另外我们开锁, 也是根据设备 id 建 topic

啥意思,为什么既说 message 里设备 is ,又说根据 id 建 topic

小项目,只有几百个设备。设备上传主题,包含分组和设备 id 。主要是测试时方便,可以只订阅一类(/指定)的设备,以便分析数据。如:{前缀}/{车间}/{机型}/#消息都是非驻留的,服务只能通过超时未收到消息,来判断设备离线。下发给设备的主题,都是统一的,最多包含分类,因为用到的频次低。如校时和计数清零,设备 id 只在消息里面。反正也不用测试,只要后续的数据变化了,就表示命令生效了。

个人觉得是有必要的,另外顺便问一下楼主 MQTT 服务器是用什么搭建的。持久化这块处理吗?

你用的是哪个 mqtt ,我们之前用的 emqx ,topic 的数量多少只是内存占用多少的问题,并且一个 topic 内存占用很少,反而 topic 的层级对性能影响较大

MQTT 协议是发布订阅模式,你要向指定设备发送下行消息,那就只能让每个设备都订阅各自的主题。群发压根没啥特殊的,让一个群下的设备,订阅一个主题即可。别搞什么大聪明技巧,在协议框架下,支持海量 topic ,是很简单的事。MQTT 的 topic 其实就是一个 tcp 通道地址列表或者映射图,跟消息中间件的 topic 概念上相同但性能上完全是两码事。

有必要。每台设备只订阅带自己设备 ID 的 topic ,能够很方便做访问控制,保证安全。举个例子,如果你设备 ID 都泄露了,如果此时 hacker 只需拿到它当前设备里面的 mqtt 账号信息,就可以模拟给其他设备发生消息了。如果设备只订阅带自己设备 ID 的 topic ,服务器侧可以很容易设置 ACL 规则,只允许每台设备只能访问和发送消息到它自己的 topic ,hacker 就很难攻击了

。。。。

mqtt 本来就支持路径的泛订阅,像#8 那样用就好,机型/设备 id

如果你想做到点对点发消息,client 订阅的 topicFilter 路径带 id 也不是不行;但你即使不这样做,很多 mqtt broker 也都是支持点对点发消息的

为什么要将设备 id 放在 topic 里面? 特别好奇你这里的需求是什么样的。 放在消息载荷里面肯定是对的。

你服务器下发给 A 终端的操作,所有的终端也都会接收到。有些设备处于省电状态,不希望频繁的唤醒,

2W 个 topic 很轻松的。

看自己需求吧,都可。比如想方便以后一对一下发指令,那就要考虑加到 topic 里了。

可以不放,但是 mqtt 的服务你的做调整吧,如果 mqtt 是自己定制的,可以做。因为每个 client 有自己的 session ,如果你能用 payload 的 id 关联到 sessionid 上,那就可以让 mqtt 给特定 session 的设备推消息。