Hi,
With TCP you can expect that your packets arrive exactly in the order that you sent them, or not at all. If the packets ultimately do not arrive then the connection is considered to have dropped, and a new connection is required. There is no scenario with TCP where some packets go missing but the connection has not restarted.
In MQTT v3.1.1 retrying message delivery during a session was allowed, however it is a fundamentally bad idea to implement this. The reason is this - if you have a reliable network connection, the only way that a client/broker will not respond to a PUBLISH by sending a PUBACK is if it is unable to do so. This may mean that the client/broker is overloaded. In this case, retrying the message will make the situation worse. If the client/broker is not overloaded but has not replied for another reason, perhaps waiting on the message to be processed in some way the same is true. Sending a message retry will just add further load to the system.
The other scenario is that the network connection is unreliable. This gives two situations - either the unreliable situation is short lived and the connection is recovered without loss, or the connection completely drops. In the first case, when the connection recovers the TCP stack of the sender must ensure that the outgoing packets remain in the exact order they were given to it by the application. As far as the client is concerned, there was just some extra latency in the connection. Sending a message retry in this case achieves nothing except for wasting bandwidth and adding extra load. Where the network connection drops completely, the case is clear - we need to make a new TCP connection and start a new MQTT session, which means sending first a CONNECT - and then we must retry our outgoing messages.
I hope this makes it clear that doing in-session retries is actually counterproductive.
Regards,
Roger