【问题标题】:Weird behavior of Paho-MQTT python library on Ubuntu 20.04Ubuntu 20.04 上 Paho-MQTT python 库的奇怪行为
【发布时间】:2021-05-04 17:29:37
【问题描述】:

我正在使用 paho-mqtt python 库开发一个项目。我有两台机器 Raspberry pi 3 和一台带有 ubuntu 20.04 的桌面。安装在 Raspberry pi 上的 Mosquitto 代理和我在 Ubuntu 上运行的 python 代码。

两台机器通过局域网连接。当我在 Ubuntu 上使用 Mosquitto 客户端 CLI 发布到代理(在 Raspberry pi 上运行的代理)时,它工作正常,但是当我使用 python 代码时,当我多次运行代码时,它只连接一次。当我在 Raspberry pi 上运行 python 代码时,它运行良好,没有任何问题。

我在 Ubuntu 上安装了 Mosquitto 代理也遇到了同样的问题,python 代码不能正常工作。

我使用了 python 3.8 和 3.5 解释器并尝试了所有 paho-mqtt 库版本,但仍然是同样的问题。它也不会触发异常或显示日志。它仅在连接时显示日志。我认为问题出在 Ubuntu 20.04 中。我的python代码如下: mqtthandeler.py

import paho.mqtt.client as mqtt
from configmanager import ConfigManager


# Retrieve the commands and configurations from the server via MQTT
class Subscriber:

    def __init__(self):
        self.cfg = ConfigManager()
        self.cfg.get_config()
        # Network connection status LEDs indicators
        # MQTT connection flag
        self.connected = False

    def test(self, x, y, z):

        print('new command = ' + str(z))

    def mqtt_connect(self):
        global client


        # Creat instance for MQTT client
        client = mqtt.Client(client_id=self.cfg.config_data['MQTT']['server id'], 
                 clean_session=False, userdata=None,
                             protocol=mqtt.MQTTv311, transport='tcp')

        # Set the username and password to connect to the MQTT Broker
        client.username_pw_set(username=self.cfg.config_data['MQTT']['authentication']['username'],
                               password=self.cfg.config_data['MQTT']['authentication']['password'])

        # callbacks for on connect and disconnect
        client.on_connect = self.on_connect
        client.on_disconnect = self.on_disconnect
        client.on_message = self.on_message
        client.on_log = self.on_log

        # Connect to the MQTT broker
        try:
            client.connect_async(host=self.cfg.config_data['MQTT']['hostname'],
                                 port=self.cfg.config_data['MQTT']['port'],
                                 keepalive=60, bind_address="")
            client.loop_start()
            print('try to connect')

    

        except Exception as e:
            #  If debug true print error message
            print('Unable to connect to MQTT broker \n Error message: ' + e)
            if self.cfg.config_data['DEBUG']:
                print('Unable to connect to MQTT broker \n Error message: ' + e)

            else:
                print('Unable to connect to MQTT broker')

    def on_log(self, client, userdata, level, buff):
        print('log= ' + buff)

    # If connected to the MQTT broker print the results of the connection
    def on_connect(self, client, userdata, flags, rc):

        self.connected = True
        # Subscribe to the commands topic to receive commands from the server
        client.subscribe(topic=self.cfg.config_data['MQTT']['topics']['commands'],
                         qos=self.cfg.config_data['MQTT']['qos'])
        if self.cfg.config_data['DEBUG']:
            print("Connection returned result: " + mqtt.connack_string(rc))

    # If disconnected from MQTT broker print the message and try to reconnect again
    def on_disconnect(self, _client, userdata, rc):
        self.connected = False
        if rc != 0 & self.cfg.config_data['DEBUG']:
            print("Unexpected disconnection.")

    # When Message received from MQTT
    def on_message(self, client, userdata, message):
        print("Received message '" + str(message.payload) + "' on topic '"
              + message.topic + "' with QoS " + str(message.qos))


'''#================================================================================================================#'''


# Publish data to the MQTT
class Publisher(Subscriber):

    def __init__(self):
        qos_cfg = ConfigManager()
        qos_cfg.get_config()
        self._qos = qos_cfg.config_data['MQTT']['qos']

    # ================================================================================================================#
    def publish(self, _topic, msg):
        client.publish(topic=_topic, payload=msg, qos=self._qos)
        print('Sent')

main.py

from mqtthandler import Subscriber, Publisher



# Press the green button in the gutter to run the script.
if __name__ == '__main__':
    print("MDL Server Started")
    # Establish connection to the MQTT broker
    mqtt = Subscriber()
    mqtt.mqtt_connect()
    pub = Publisher()
    for i in range(10):
        pub.publish('prox\\', '2222\\')

Mosquitto -v 输出(代码连接时)

1612077624: No will message specified.
1612077624: Sending CONNACK to 2222 (1, 0)
1612077624: Received SUBSCRIBE from 2222
1612077624:     command\ (QoS 1)
1612077624: 2222 1 command\
1612077624: Sending SUBACK to 2222
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m2, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m2, rc0)
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m3, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m3, rc0)
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m4, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m4, rc0)
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m5, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m5, rc0)
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m6, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m6, rc0)
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m7, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m7, rc0)
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m8, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m8, rc0)
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m9, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m9, rc0)
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m10, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m10, rc0)
1612077624: Received PUBLISH from 2222 (d0, q1, r0, m11, 'prox\', ... (5 bytes))
1612077624: Sending PUBACK to 2222 (m11, rc0)
1612077624: Socket error on client 2222, disconnecting.

有时 Mosquitto -v 在多次尝试后会显示此输出

1612078246: Socket error on client <unknown>, disconnecting.
1612079414: New connection from 192.168.10.2 on port 1883.

有时在 Mosquitto -v 上什么也没有 另外,我在 virtualenv (Pycharm virtualenv) 之外运行了代码,但行为相同 我希望有一个人可以帮助我。提前谢谢你

【问题讨论】:

    标签: python-3.x ubuntu mqtt paho


    【解决方案1】:

    我只是发布我找到的解决方案,以防有人遇到同样的问题。

    解决方案是在 main.py 中调用“mqtt_connect”函数后添加 0.1 秒的延迟,让 MQTT 代码有足够的时间连接到代理。我认为这个问题的发生是因为我的机器速度很快,所以程序在 MQTT 客户端获得足够的时间连接之前执行并完成。

    最终的 main.py 代码:

    import time
    from mqtthandler import Subscriber, Publisher
    
    # Stop
    # def exit():
    #     print('MDL Server stopped')
    
    
    # Press the green button in the gutter to run the script.
    if __name__ == '__main__':
        print("MDL Server Started")
        # Establish connection to the MQTT broker
        mqtt = Subscriber()
        mqtt.mqtt_connect()
        time.sleep(0.1)
        pub = Publisher()
        for i in range(10):
            pub.publish('prox\\', '2222' + '\\')
    

    【讨论】:

      猜你喜欢
      • 2023-02-16
      • 2022-01-03
      • 1970-01-01
      • 1970-01-01
      • 2020-08-09
      • 1970-01-01
      • 2021-03-03
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多