You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

调用msg.topic致MQTT客户端on_message方法失效,求问题原因及解决

问题分析与解决

嘿,我一眼就揪出问题所在了——你在on_message回调里不小心覆盖了原始的MQTT消息对象!

问题根源

看这段出问题的代码:

def on_message(client, userdata, msg):
    msg = msg.payload.decode()  # 这里把原始msg对象直接覆盖成字符串了!
    print("topic:", msg.topic)  # 现在msg是字符串,根本没有topic属性!
    print("Received Message: {}".format(msg))

原始的msg是paho-mqtt库提供的消息对象,它自带.topic(消息主题)和.payload(字节流形式的消息内容)两个核心属性。但你第一行代码把msg重新赋值成了解码后的字符串,后面再尝试访问msg.topic时,本质是在调用字符串的topic属性——这肯定会触发AttributeError!

那为啥程序没报错?因为paho-mqtt的客户端循环(比如你用的loop_forever())会自动捕获回调里的异常,不会让整个程序崩溃,但会直接终止当前回调的执行,这就是你看到“后续打印语句不再执行”的原因。

修复方案

只需要换个变量名,别覆盖原始的msg对象就行:

import paho.mqtt.client as client
hostname = 'iot.eclipse.org'
topic = 'Mein/Topic'

def on_message(client, userdata, msg):
    payload = msg.payload.decode()  # 用新变量存解码后的内容
    print("topic:", msg.topic)      # 现在能正常访问原始msg的topic属性了
    print("Received Message: {}".format(payload))

def on_connect(client, userdata, flags, rc):
    print("Connection returned result: " + str(rc) + "\n")
    if rc == 0:
        print("Listening now.\n")
        client.subscribe(topic)

client = client.Client()
client.on_message = on_message
client.on_connect = on_connect
client.connect(hostname)
client.loop_forever()

小提醒

在回调函数里操作传入的参数时,尽量别直接覆盖原始对象,尤其是这种库提供的带多属性的对象,很容易因为变量名重复踩这种隐性坑。

内容的提问来源于stack exchange,提问作者Philipp

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.11 09:05:57