mlesniew / PicoMQTT

ESP MQTT client and broker library
GNU Lesser General Public License v3.0
256 stars 29 forks source link

long timeouts #48

Open jjirasek opened 1 week ago

jjirasek commented 1 week ago

hi, I am connecting to mosquitto server like this: PicoMQTT::Client mqtt("x.x.x.x"); and then I am sending messages every 60 seconds with mqtt.publish. It works great, but there is problem if communication is interrupted (for example internet is down). Then there is aprox 14s long freezing and after then regular 4s freezings. Freezing is when executing mqtt.loop Is there any way to reduce this freezings?

Thanks

justbendev commented 1 week ago

Hi there! :wave:

This issue is unlikely to be related to the library itself. I recommend conducting some research before submitting a bug report.

The behavior you're observing can depend on several factors, including how your sketch is designed, whether your routines are blocking or non-blocking, whether you're using a single-core or multi-core microcontroller, and much more.

Expecting a specific routine to trigger precisely at the right moment without accounting for these variables can be challenging. It’s important to have a good understanding of these variables to achieve what you need.

Don't forget that the WiFi routine itself does use CPU Cycles especially on single core microcontrollers, that could lead to timeouts requiring a reconnect.

I would be more than happy to help if you can give us a bit more details about the sketch, the issue, how can we reproduce this issue, hardware used and anything that could be relevant.

Have a great day :+1:

jjirasek commented 1 day ago

After some research, I think these timeouts are normal. Their duration can be set when defining the picomqtt client (according to client.h).

By the way, I need to define the brooker address in "void setup()" (because I want to let users of my project to define the brooker address), I don't know how to do it. Thank you for your advice.

mlesniew commented 18 hours ago

Hey guys,

Unfortunately, calling mqtt.loop() can sometimes block for a few seconds. This is caused by the library's synchronous nature.

When the TCP connection with the broker is interrupted, the ESP often is not aware of that right away. It can only detect that the connection is not working if it times out waiting for some expected data on the connection.

The time out time is set to 10 seconds by default. That's actually a lot, especially if you're communicating with a broker within the local network (e.g. at your home) and when there's good wifi reception.

Besides that, the mqtt.loop() call can block if the connection with the broker has been lost already and PicoMQTT tries to reestablish it. In such cases mqtt.loop() will also wait for the connection to be established. If that doesn't succeed within the time out time, it gives up.

Now the bad news is that you can't eliminate the blocking completely. It's just the price we're paying for the library's simple synchronous API.

The good news is that you can significantly reduce the observed freezing by adjusting the two timeouts specified when constucting the client object (see https://github.com/mlesniew/PicoMQTT/blob/master/src/PicoMQTT/client.h#L66):

To answer your other question -- the borker address can be changed at any time by setting the host instance variable. There are more public instance variables that you can change too, here's an example:

PicoMQTT::Client mqtt;

void setup() {
    mqtt.host = "mqtt.example.com";
    mqtt.port = 1883;
    ...
    mqtt.begin();
}