5.3 CoAP工作模式
CoAP虽然参考了HTTP的设计思路,但也根据受资源限制设备的具体情况改良了诸多设计细节,同时增加了很多实用功能。本节分为三部分内容——逻辑分层结构、报文类型和请求/响应模式。
5.3.1 逻辑分层结构
CoAP的数据交互方式和HTTP的请求/响应工作方式非常相似。CoAP请求一般由客户端发起,服务器根据客户端请求中的URI定位资源在服务器中的具体位置,通过客户端请求中的请求方法确定如何操作该资源,如读取资源、创建资源、修改资源或者删除资源等。CoAP服务器处理请求之后将返回一个CoAP响应,CoAP响应中包含响应码,也有可能包含响应负载。
与HTTP采用TCP作为传输层不同,CoAP使用UDP作为传输层协议。UDP并不是一个面向连接的传输层协议,所以CoAP定义4种不同的报文类型:CON(Confirmable)、NON(NonConfirmable)、ACK(Acknowledgement)和RST(Reset)。本质来说,CoAP采用了双层结构——消息层和请求/响应层。消息层处理端点之间的数据交换,并为CON、NON、ACK和RST报文类型提供重传机制,CoAP通过增加消息层的方式弥补UDP传输的不可靠性。CoAP的逻辑分层结构如图5-4所示。
5.3.2 报文类型
CoAP定义了四种不同的报文类型,通过这四种不同的报文类型至少可以组合成可靠传输和非可靠传输两种工作方式。
1.4种报文类型
·Confirmable Message(CON):在请求/响应交互过程中,CON报文需要被接收者确认。每一个CON报文必须要对应一个准确的ACK报文或RST报文,如果在规定的时间内客户端未接收到ACK报文或RST报文,那么客户端将会触发一次“重传”。
·Non-Confirmable Message(NON):相比于CON报文,NON报文的约束条件要宽松许多。单个NON报文不需要对应一个准确的ACK或RST报文。在一些传感器数据上传应用场景中NON报文较为常用,服务器对NON报文的处理也较为灵活。若服务器收到一个来自客户端的NON报文类型的CoAP请求,服务器可选择不返回响应;同时客户端也不会因为一定时间内没有收到来自服务器的ACK类型报文而触发重传机制。
·Acknowledgement Message(ACK):ACK报文用于确认CON报文。ACK报文的报文序号(Message ID)需要和CON报文的报文序号保持严格一致,ACK报文可以在一定程度上保证CoAP传输的可靠性。ACK报文中可以不包括响应负载,可能为空。CoAP请求/响应过程定义了携带模式和分离模式,ACK报文负载为空的情况一般出现在分离模式中。
·Reset Message(RST):若服务器接收到一个CON报文,但由于报文中上下文缺失导致服务器无法处理该报文,那么服务器将会返回一个RST报文。RST报文的报文序号需要与CON报文的报文序号保持严格一致,而且RST报文的负载一定为空。
2.可靠传输
由于CoAP使用UDP作为传输层协议,UDP并不是一种面向连接的传输层协议,所以对于一些要求可靠传输的场合,CoAP需要另外增加某种机制保证传输的可靠性。
CON报文和ACK报文可保证CoAP请求/响应交互过程的可靠性。当客户端发送一个CON报文时,报文的接收者必须返回一条ACK报文来确认其已经正确收到了该CON报文。需要特别指出,CON报文中的Message ID必须与ACK报文中的Message ID完全一致。在图5-5中,CoAP客户端发送一个CON报文,报文的Message ID为0x7d34,接收者收到该CON报文之后返回一个ACK报文,ACK报文的Message ID同为0x7d34。
图5-5 CoAP可靠传输示例
若客户端在一定的时间内没有收到ACK报文,那么客户端将重新发送CON报文。CoAP重传机制也可提高CoAP的可靠性,CoAP重传机制通过两个主要的参数进行控制——超时时间和重传计数器,CoAP重传机制将在5.4节详细分析。
3.非可靠传输
在物联网应用领域并不是所有的发送者报文都需要被确认。NON报文是一种非常轻量级的替换方案。如图5-6所示便是一个非可靠传输示例,CoAP客户端发送一条NON报文,NON报文的Message ID为0x01a0,而服务器什么都没有返回。