dotnet / MQTTnet

MQTTnet is a high performance .NET library for MQTT based communication. It provides a MQTT client and a MQTT server (broker). The implementation is based on the documentation from http://mqtt.org/.
MIT License
4.49k stars 1.07k forks source link

Not receiving messages sent while disconnected with MqttProtocolVersion.V500 #1827

Open altwohill opened 1 year ago

altwohill commented 1 year ago

Describe the bug

Apologies if this is me misunderstanding something, or if this is actually a bug.

When testing behaviour of .WithCleanSession(false) I'm finding the client is not picking up messages that were sent while the client was previously offline. However if I change the protocol to V3.11 it works as expected.

Which component is your bug related to?

To Reproduce

Steps to reproduce the behavior:

  1. Start client and connect with MqttProtocolVersion.V500
  2. Send a test message, verify it shows on client
  3. Disconnect client, send more messages
  4. Reconnect client

Expected behavior

Messages sent during step 3 above should display immediately upon reconnecting.

Not working

public async Task Connect(CancellationToken cancellationToken)
    {
        _cancellationToken = cancellationToken;

        var optionsBuilder = new MqttClientOptionsBuilder()
            .WithTcpServer(_traceOptions.Server, _traceOptions.Port)
            .WithProtocolVersion(MQTTnet.Formatter.MqttProtocolVersion.V500)
            .WithCleanSession(false)
            .WithClientId(Dns.GetHostName());
        if (_traceOptions.UseTls)
        {
            optionsBuilder = optionsBuilder.WithTls();
        }

        var options = optionsBuilder.Build();

        await _client.ConnectAsync(options, _cancellationToken);
        _logger.LogInformation("Connected to server {server}", _traceOptions.Server);
        await Subscribe();
    }

Working

public async Task Connect(CancellationToken cancellationToken)
    {
        _cancellationToken = cancellationToken;

        var optionsBuilder = new MqttClientOptionsBuilder()
            .WithTcpServer(_traceOptions.Server, _traceOptions.Port)
            .WithProtocolVersion(MQTTnet.Formatter.MqttProtocolVersion.V311)
            .WithCleanSession(false)
            .WithClientId(Dns.GetHostName());
        if (_traceOptions.UseTls)
        {
            optionsBuilder = optionsBuilder.WithTls();
        }

        var options = optionsBuilder.Build();

        await _client.ConnectAsync(options, _cancellationToken);
        _logger.LogInformation("Connected to server {server}", _traceOptions.Server);
        await Subscribe();
    }

Again, not sure if I'm missing something but it does almost seem like the client unsubscribes when it shuts down - but I don't want it to do this!

xMarkos commented 1 year ago

I had experienced similar problem and the solution was to add .WithSessionExpiryInterval(uint.MaxValue). Apparently, the session length is by default 0 seconds, which is not very useful. FWIW we are using self-hosted HiveMQ.

amitsahu-work commented 1 year ago

Any update on this?