首页 » 技术分享 » MQTT协议_服务质量

MQTT协议_服务质量

 
文章目录

服务质量

MQTT按照这里定义的服务质量 (QoS) 等级分发应用消息。分发协议是对称的,客户端和服务端既可以是发送者也可以是接收者。分发协议关注的是从单个发送者到单个接收者的应用消息。服务端分发应用消息给多个客户端时,每个客户端独立处理。分发给客户端的出站应用消息和入站应用消息的QoS等级可能是不同的。

MQTT定义了三个层次的服务质量:

l  QoS 0:最多分发一次;

l  QoS 1: 至少分发一次;

l  QoS 2: 仅分发一次

接下来,我们分别对这三个服务质量做特别的说明。

2.2.3.1 QoS 0,最多分发一次

消息的分发依赖于底层网络的能力。接收者不会发送响应,发送者也不会重试。消息可能送达一次也可能根本没送达。这个服务质量常用在鸡肋的消息传递中,即消息丢了也没有关系。

发送者:

必须发送QoS等于0,DUP等于0的PUBLISH报文。

接收者:

接受PUBLISH报文时同时接受消息的所有权。

使用场景:

尽力而为。

常用于广播。

交互方式:


断开重连

对于QoS 0的消息,在消息交互的过程中,如果出现断开重连的情况,丢失的消息报文也无需做特别的处理。

2.2.3.2 QoS 1,至少分发一次

服务质量确保消息至少送达一次,有可能存在多次发送的情况。

QoS 1的PUBLISH报文的可变报头中包含一个报文标识符,需要PUBACK报文确认。即需要接收者发送PUBACK回包,但是PUBACK回包只是用来重用相同的报文标识符,不影响后续非重复的报文标识符的发送。

发送者:

ü  每次发送新的应用消息都必须分配一个未使用的报文标识符。一旦发送者收到PUBACK报文,这个报文标识符就可以重用。

ü  发送的PUBLISH报文必须包含报文标识符且QoS等于1,DUP等于0。

ü  必须将这个PUBLISH报文看作是未确认的,直到从接收者那收到对应的PUBACK报文。

ü  允许发送者在等待确认时使用不同的报文标识符发送后续的PUBLISH报文。也就是说可以是异步的情况。

接收者:

ü  响应的PUBACK报文必须包含一个报文标识符,这个标识符来自接收到的、已经接受所有权的PUBLISH报文。

ü  发送了PUBACK报文之后,接收者必须将任何包含相同报文标识符的入站PUBLISH报文当作一个新的消息,并忽略它的DUP标志的值。简单的理解是,在发送PUBACK报文之后,如果还是接收到了一个相同的报文标识符,接收方应当认为这是一个新的报文,同时不关注DUP标志位的数值。

使用场景:

保证送达,可能重复

交互方式:

Client[Qos=1,DUP=0/*重复次数*/,MessageId=x]--->PUBLISH--> Server收到后,存储Message,发布,删除,向Client回发PUBACK。

Client收到PUBACK后,删除Message;如果未收到PUBACK,设置DUP++,重新发送,Server端重新发布,所以有可能重复发送消息。

断开重连

如果在消息分发的过程中出现了断开重连的情况,且客户端设置清理会话(CleanSession)标志为0重连时,客户端和服务端必须使用原始的报文标识符重发任何未确认的PUBLISH报文(如果QoS>0)和PUBREL报文。

且发送端重发任何之前的PUBLISH报文时,必须按原始PUBLISH报文的发送顺序重发。

接收端必须按照对应的PUBLISH报文的顺序发送PUBACK报文。

2.2.3.3 QoS 2,仅分发一次

这是最高等级的服务质量,消息丢失和重复都是不可接受的。使用这个服务质量等级会有额外的开销。

QoS 2的消息可变报头中有报文标识符。QoS 2的PUBLISH报文的接收者使用一个两步确认过程来确认收到。

发送者:

ü  必须给要发送的新应用消息分配一个未使用的报文标识符。一旦发送者收到PUBCOMP报文,这个报文标识符就可以重用。

ü  发送的PUBLISH报文必须包含报文标识符且报文的QoS等于2,DUP等于0。

ü  必须将这个PUBLISH报文看作是未确认的 ,直到从接收者那收到对应的PUBREC报文。

ü  收到PUBREC报文后必须发送一个PUBREL报文。PUBREL报文必须包含与原始PUBLISH报文相同的报文标识符。

ü  必须将这个PUBREL报文看作是未确认的 ,直到从接收者那收到对应的PUBCOMP报文。

ü  一旦发送了对应的PUBREL报文就不能重发这个PUBLISH报文。

接收者:

ü  响应的PUBREC报文必须包含报文标识符,这个标识符来自接收到的、已经接受所有权的PUBLISH报文。

ü  在收到对应的PUBREL报文之前,接收者必须发送PUBREC报文确认任何后续的具有相同标识符的PUBLISH报文。 在这种情况下,它不能重复分发消息给任何后续的接收者。

ü  响应PUBREL报文的PUBCOMP报文必须包含与PUBREL报文相同的标识符。

ü  发送PUBCOMP报文之后,接收者必须将包含相同报文标识符的任何后续PUBLISH报文当作一个新的发布。

使用场景:

不重复不丢失,是最理想的网络收发状态。

交互方式:


断开重连

如果在消息分发的过程中出现了断开重连的情况,且客户端设置清理会话(CleanSession)标志为0重连时,客户端和服务端必须使用原始的报文标识符重发任何未确认的PUBLISH报文(如果QoS>0)和PUBREL报文。

且发送端重发任何之前的PUBLISH报文时,必须按原始PUBLISH报文的发送顺序重发。

接收端必须按照对应的PUBLISH报文的顺序发送PUBREC报文。

发送端必须按照对应的PUBREC报文的顺序发送PUBREL报文。

2.2.3.4 几种QoS之间的关系

在MQTT3.1.1协议的设计过程中,涉及到QoS的报文信息包括以下几个类型:订阅,订阅确认,消息发布,消息分发。

1)订阅和订阅确认中的QoS

订阅是客户端向服务器端申请主题的行为,在每一个订阅报文中,为每一个订阅的主题指定了最大的QoS等级。而服务器端收到订阅请求之后,可以决定给每一个订阅主题的开放何种等级的QoS,并通过SUBACK告知客户端。

即订阅QoS >= 订阅确认QoS

2)消息发布和消息分发

消息发布通过PUBLISH报文实现,可能是服务器端到客户端,也可能是客户端到服务器端。如果是第二种情况的话,那就还需要服务器端根据订阅主题列表,还确认是否将该报文分发,于是就产生了消息分发的动作,在消息分发的报文中,也是包含有QoS的。

于是就涉及到发布消息的QoS,客户端收到订阅确认的QoS等级,以及分发消息(客户端收到消息)的QoS。那这三个之间的关系是如何呢?

一个简单的原则就是:第三个QoS是前两个QoS中的最小者。

列表如下:

发布消息的QoS

Topic订阅确认的QoS

分发消息(接收消息)的QoS

0

0

0

1

0

0

2

0

0

0

1

0

1

1

1

2

1

1

0

2

0

1

2

1

2

2

2



版权所有,转载请注明出处:http://www.junsion.icoc.bz/ by 小丑

转载自原文链接, 如需删除请联系管理员。

原文链接:MQTT协议_服务质量,转载请注明来源!

0