-1

Do i need to subscribe to all topics i am interested in before i execute the loop_forever() function? E.g. to somehow dynamically add more subscriptions during the life time of the MQTT client.

Joysn
  • 987
  • 1
  • 16
  • 30
  • 1
    You shouldn't really subscribe to any topics before starting the client loop. How you choose to start that loop very much depends on what your code will be doing. As it is we can't answer this question without a LOT more context – hardillb Oct 30 '21 at 22:25
  • @hardillb i played a little bit with my setup and it works. See the code snipped below. – Joysn Oct 31 '21 at 22:45

1 Answers1

0

I found out that it is possible. I implemented a class which hides the mqtt stuff. In the constructor i connect to the broker and start the loop_forever() with a seperate thread. And afterwards that class subscribes to some topics and register a callback for each topic, which are called from on_message.

c = comm("localhost")
c.register_handler("topic1", first_handler)
c.register_handler("topic2", second_handler)

class comm:
    def __init__(self, broker_address):
        self.client = mqtt.Client("")
        self.client.on_message = self.on_message
        self.callbacks = dict()
        self.client.connect(broker_address)
        threading.Thread(target=self.__run, daemon=True).start()
        
    def __run(self):
        self.client.loop_forever()

    def on_message(self, client, userdata, msg):
        self.callbacks[msg.topic](jsonpickle.decode(msg.payload))

    def on_connect(self, client, userdata, flags, rc):
        for topic in self.callbacks:
           self.client.subscribe(topic)    

    def register_handler(self, topic: str, handler: Callable[[Dict], None]):
        self.callbacks[topic] = handler
        self.client.subscribe(topic)
Joysn
  • 987
  • 1
  • 16
  • 30
  • 1
    Note that you can simplify this a bit using [`loop_start`](https://github.com/eclipse/paho.mqtt.python#loop-startstop-example) and its best to subscribe in the `on_connect` callback (for a number of reasons including [loss of subscription](https://github.com/eclipse/paho.mqtt.python/issues/398) following automatic reconnect with default options). – Brits Nov 01 '21 at 01:17
  • @Brits In the on_connect callback i have implemented a reconnect handling of the subscribed topics. I collect those topics in register_handler and then simply use the dict keys to get them all and subscribe to them again. With the simplification you mean: i can call loop.start() instead of the threading part and loop_forever()? And then somehow call loop_stop() when i dont need the mqtt client anymore? – Joysn Nov 01 '21 at 08:52
  • 1
    "i can call loop.start() instead..." - yes. It's a pretty minor change (and far from essential). – Brits Nov 01 '21 at 19:05
  • @Brits ok, super. I will consider this in my implementation. Thanks a lot! – Joysn Nov 01 '21 at 19:12