当前位置: 首页 > 编程日记 > 正文

CoAP 协议解析说明(转)


CoAP 协议全面分析

HTTP与COAP 请求与响应示例

HTTP请求(文本格式)

POST https://getman.cn/echo HTTP/1.1
User-Agent: Fiddler
Host: getman.cn
Content-Length: 9{temp:22}

HTTP响应(文本格式)

HTTP/1.1 200 OK
Server: NWSs
Date: Thu, 07 Dec 2017 14:38:25 GMT
Content-Type: text/html; charset=UTF-8
Connection: keep-alive
Cache-Control: private, no-cache
Vary: Accept-Encoding
X-Powered-By: PHP/7.1.7
Access-Control-Allow-Origin: *
X-NWS-LOG-UUID: 6bac6a30-99fb-4441-8c04-fe0f6556e5b7
X-Daa-Tunnel: hop_count=2
Content-Length: 298POST /echo HTTP/1.1
X-DAA-TUNNEL: hop_count=2
X-TENCENT-UA: Qcloud
QVIA: 7f0000016285484627467c8660a39b6bbf1af144
X-NWS-LOG-UUID: 6bac6a30-99fb-4441-8c04-fe0f6556e5b7
X-FORWARDED-PROTO: https
X-FORWARDED-FOR: 223.73.213.93
USER-AGENT: Fiddler
CONTENT-LENGTH: 9
HOST: getman.cn{temp:22}

COAP请求与响应

  • COAP SPEC里面例子(二进制格式) 
    get

  • COAP firebox copper插件log(已把二进制解析为文本,可以直观的了解该协议所包含内容)

get

COAP请求与响应都会放在COAP Message里面。

HTTP 与 COAP协议都是通过4个请求方法(GET, PUT, POST, DELETE)对服务器端资源进行操作。 两者之间明显的区别在于HTTP是通过文本描述方式描述协议包内容,协议包里面会包含一些空格符,换行符等,协议包可读性很强。而COAP是通过定义 二进制各位段功能来描述协议包内容。 因此COAP协议包大小更小,更紧凑。COAP协议最小的协议包只有4B。 协议包需要经过解析后才能知道里面具体内容,另还有一个明显的区别是传统的HTTP协议是主机与web服务器之间是单向通信的(用websocket除外)。而CoAP系统中CoAP Client与CoAP server是可以双向通信,双方都可以主动向对方发送请求。

COAP协议背景

在物联网应用里面, 设备与设备之间都存在网络里面,它们需要互相进行网络通信。 但由于通常物联网设备都是资源限制型的,有限的CPU能力,有限RAM,有限的flash,有限的网络带宽, 针对此类特殊场景,COAP协议借鉴了HTTP协议机制并简化了协议包格式。简洁地实现了物联网设备之间M2M通信。

COAP协议特点

  1. 基于消息模型,定义了4个消息类型,以消息为数据通信载体,通过交换网络消息来实现设备间数据通信
  2. 对CoAP Server云端设备资源操作都是通过请求与响应机制来完成,类似HTTP,设备端可通过4个请求方法(GET, PUT, POST, DELETE)对服务器端资源进行操作。 请求与响应的数据包都是放在CoAP消息里面进行传输的
  3. 基于消息的双向通信(M2M),CoAP Client与CoAP server双方都可以独立向对方发送请求.双方可当client或者server角色。
  4. 协议包轻量级,最小长度仅为4B。
  5. 支持可靠传输,数据重传,块传输。 确保数据可靠到达。
  6. 支持IP多播, 即可以同时向多个设备发送请求(比如CoAP client搜索CoAP Server)
  7. 非长连接通信,适用于低功耗物联网场景

COAP具体协议介绍

协议框架

CoAP默认运行在UDP上,但它也支持运行在SMS,TCP等数据传输层上。本文主要是基于UDP上的CoAP协议介绍

1.消息模型 Messages


COAP协议通信是通过在UDP上传输消息类完成。UDP比作公路话,消息就是公路上汽车。

COAP定义了4种类型消息,来实现设备端与云端之间双向通信

1. 需要确认消息   CON
2. 不需要确认消息  NON (适用于消息会重复频繁的发送,丢掉消息不对业务产生影响)
3. 确认应答消息   ACK
4. 复位消息  RST

基于4种消息类型,可以实现2种传输质量。即可靠消息传输 与 不可靠消息传输。

怎么是可靠消息传输?

主要是通过确认及重传机制来实现的,客户端发送消息后,需要等待服务器收到通知, 如果在规定时间内,没有收到需要重新发送数据。 可靠传输是基于CON消息传输的,服务器端收到CON类型的消息后,需要返回ACK消息,客户端到在指定时间ACK_TIMEOUT内收到ACK消息后,才代表这个消息以可靠到服务器端。

怎么是不可靠消息传输?

客户端只管发送消息, 不管服务器端有没有收到,因此可能存在丢包。不可靠传输是基于NON消息传输的。服务器端收到NON类型的消息后,不用回复ACK消息。

2.资源请求/响应模型 Requests/Responses


对于物联网,服务器上的资源可以简单的认为是物联网设备的实时运行影子, 通过访问服务器上资源就可以实现与设备间数据的交互。 上面谈到的消息模型比如汽车话, 资源请求及响应好比汽车上货物。 资源请求及响应内容最终会被放在CoAP消息包里面。CoAP请求与响应,类似HTTP,且根据RESTful架构设计的。 CoAP客户端发出请求,CoAP服务端进行请求处理然后发送响应。

COAP 请求Request方法: 请求方法与HTTP协议类似,有4个。 GET, PUT, POST, DELETE, 所有的请求方法都会放在CoAP CON/NON消息里面进行传输。

COAP 请求响应Response代码: 响应内容也与HTTP协议类似。 主要有如下3类:

  • Success 2.xx 代表客户端请求被成功接收并被成功处理
  • Client Error 4.xx 代表客户端请求有错误,比如参数错误等
  • Server Error 5.xx 代表服务器在执行客户端请求时出错。

所有的请求服务器响应可以放在CoAP CON/NON/ACK消息里面进行传输。针对CoAP 带CON消息请求,响应如果快速处理完(有些请求的处理需要耗时多,服务器无法立即响应),则可直接放在ACK消息包里面返回。对于无法立即响应的,服务器带资源ready后,会单独发一个响应消息包给客户端

服务器上可访问资源统一用URL来定位(比如/deviceID/temp 访问某个设备的温度信息)。客户端通过某个资源的URL来访问服务器具体资源,通过4个请求方法(GET,PUT,POST,DELETE)完成对服务器上资源增删改查操作。

举个例子: 比如某个设备需要从服务器端查询当前温度信息。

  • 请求消息(CON): GET /temperature , 请求内容会被包在CON消息里面
  • 响应消息 (ACK): 2.05 Content "22.5 C" ,响应内容会被放在ACK消息里面

3.消息报文定义 Messages Define


Header(必须):固定4个byte

  • Ver : 2bit, 代表版本信息,当前是1
  • T: 2bit, 代表该消息类型, CON, NON. ACK, RST
  • TKL: 4bit,token长度, 当前支持0~8B长度,其他长度保留将来扩展用
  • Code:8bit,分成前3bit(0~7)和后5bit(0~31),前3bit代表类型。 0代表空消息或者请求码, 2开头代表响应码,取值如下:
0.00 Indicates an Empty message
0.01-0.31 Indicates a request.
1.00-1.31 Reserved
2.00-5.31 Indicates a response.
6.00-7.31 Reserved
  • Message ID:16bit, 代表消息MID,每个消息都有一个ID ,重发的消息MID不变。

token(可选)

也叫做请求ID。把响应与之前的请求关联起来。有时候客户端发送出请求带上token,服务器端有时不能立即响应, 当服务器端准备好数据后,会单独发送一个消息给客户端, 这时候客户端需要判断这个消息是针对之前的哪个请求回复的,token用途就在这里,通过token,客户端收到响应后,取出TOKEN,就可以知道该响应是针对之前哪个请求回复的。

option(可选,0个或者多个)

请求消息 与回应消息都可以0~多个options。 主要用于描述请求或者响应对应的各个属性,类似参数或者特征描述。

payload(可选)

实际携带数据内容, 若有, 前面加payload 标志 OxFF.

option 介绍

格式

当一个消息报文里面有多个option时,每个option需要按照该option在协议里面对应的编号顺序排列下来。并且每个option索引是通过增量来计算的。option Delta 代表相对于前面一个option编号的增量。

举个例子 
假设前面一个option编号为20, 当前option编号为25,则当前option的增量Delta就设置为5 
增量最大可占用2个byte, 计算方式如下
当option Delta = 0~12时,只占4bit。
当option Delta =13 则占1B, 实际数字是option Delta【extended】 - 13 
当option Delta =14 则占2B , 实际数字是option Delta【extended】 - 269

COAP 支持OPTION编号列表, 是HTTP协议 options 子集。

举例 Uri-Host:服务器主机名称,如californium.eclipse.org 
Uri-Port:服务器端口号,默认为5683 
Uri-Path:资源路路径,如\temperature 
Uri-Query:访问资源参数,例如?v=1&t=2

4.块传输


需要传输大量数据时,比如一个大文件,需要采用分块传输,把文件拆解成多个块进行传输。扩展的块传输协议在COAP基础协议上增加了3个options, 2个response codes 用于块传输大小协商及控制。

 

block option结构

有三部分组成:
SZX: Block Size,占用2bit,取值范围0~6,对应每个block 大小为2xx(SZX+4),即范围(16 ~ 1024),以Byte为单位
M: More Flag,占用1bit, 代表是否还有剩下数据块未传输。如果设置为0,代表数据块都已传输出去
NUM: Block Number, 占用0~3Byte,代表当前块编号,以0开始, 如我们要传10个数据块,则数据块的编号为0~9

option block1: 主要用于客户端发出请求时,分块传输,比如需要上传一个大的数据包到服务器上。
option block2: 主要用于服务器端响应时,分块传输, 比如设备端发起资源发现式,由于服务器上资源较多,就要启动分块传输。

Size option

主要用于向对方说明,这次块传输需要传送的数据总数量。
Size1 option: 代表客户度发出请求里面资源总的大小。
Size2 option: 代表服务器端响应资源总的大小。

如何启动块传输?

当请求消息或者响应消息里面有出息 block1/block2 option时,代表这是块传输通信。需要根据option block 里面M标识,决定是否继续进行块传输。

示例
第一个消息,客户端发起发现资源请求信息CON并设置Block2:0(NUM)/0(M)/64(SZX)告诉服务器端,能接受最大block size为64.
第二个消息。服务器端回复确认消息ACK,并设置Block2:0/1/64,告诉客户端,block size已接受为64, 且后面还有数据,当前传输块编号是0. size2:1094, 告诉客户端,接下来总的数据大小是1094B。
第三个消息,客户端发起请求获取下一个block。设置Block2:1/0/64.告诉服务器端下一个要获取的block编号是1.

5.订阅与发布


MQTT协议是基于订阅与发布模型的,coap通过扩展协议方式也简单的实现了订阅与发布模型。

当一个客户端需要定期去查询服务器端某个资源的最新状态时,订阅与发布模型就非常有用,不用这个模型,客户端就要周期的不断发送请求到服务器端。

模型框架

关键概念 主题Subject: 代表CoAP服务器上的某个资源resource,该资源状态随时可能发生变化 观察者Observer:代表对某个coap资源最新状态感兴趣的客户端CoAP Client 登记Registration: 观察者需要向服务器CoAP server登记感兴趣的主题Subject。 
通知Notification:当CoAP观察到某个主题发生状态变化时,CoAP服务器会主动向该主题下的已登记的观察者列表里面的每个观察者发送其订阅的主题最新状态数据。 备注:如果已订阅某个主题的CoAP client对CoAP server Notification无法确认,则会从主题订阅列表里面移除掉。

订阅与发布协议在COAP基础协议上增加了1个Observe option, 其值为整数,通过该options来实现订阅与发布模型管理

在get请求消息里面
oberser value 为 0: 代表向CoAP服务器端订阅一个主题。 
oberser value 为 1: 代表向CoAP服务器端移除一个已订阅主题。

在notification消息里面
oberser value 代表 主题发生变化时,检测到顺序,以便客户端可以知道状态变化的先后。

举个例子

1. 客户端向服务器端登记感兴趣的主题 /temperature 
2. 当temperature发生状态改变时,服务器端主动通知到客户端。 
3. 客户端根据token,就可以与之前订阅主题关联起来,以此确定是哪个主题订阅的。

一个CoAP Client可以分次向CoAP server订阅多个资源主题。 一个CoAP server上的主题可以被多个观察者(CoAP Client)订阅。 这样就通过了CoAP server实现了CoAP Client之间直接数据转发通信。

可以通过灵活设计服务器上的资源链接,来实现对某个主题的条件订阅(类似触发器或者阀值等)。 比如订阅主题是: <coap://server/temperature/critical?above=42>, 当温度超过42,CoAP Server需要发送通知。

6.安全


COAP使用DTLS来做安全传输层,该层运行于UDP之上.
 
当前考虑使用DTLS时,需要考虑设备终端资源受限情况, 有些资源有限设备无法运行DTLS安全加密算法。

做安全加密,需要根据应用场景需要,对应只上报数据,且数据敏感度不高场景,可以不考虑加入安全层。

相关文章:

孔雀翎----《Programming C# 》中文版 第4版

孔雀翎----《Programming C# 》中文版 第4版 主页&#xff1a;http://blog.csdn.net/21aspnet/ 时间&#xff1a;2007.8.7 电子工业出版社给我邮寄了此书&#xff0c;所以本人可以先在出版之前一睹为快。 本人曾看过300多本.NET方面的书&#xff0c;感慨颇深。其实一…

iOS开发小技巧--textField成为密码框,view加载完后textField获取焦点

文本框安全输入&#xff1a;Secure Text Entry&#xff08;安全文本输入&#xff09;view加载完后textField获取焦点的正确做法

python出现typeerror原因是_Python 文件添加列表数据后TypeError原因

# -*- coding: utf-8 -*-#打开文件&#xff0c;将文件读入字符串colfopen(pride.txt)textf.read()colstext.split()f2open(data.txt,w)for col in cols:f2.write(col)f2.write(\n)以上代码运行无误。# -*- coding: utf-8 -*-#打开文件&#xff0c;将文件读入字符串colfopen(pri…

LVM逻辑卷创建管理

LVM&#xff08;逻辑分区&#xff09;的创建顺序&#xff1a;物理分区&#xff0d;物理卷&#xff0d;卷组&#xff0d;逻辑卷&#xff0d;挂载。物理卷&#xff08;Physical Volume,PV&#xff09;&#xff1a;就是指硬盘分区&#xff0c;也可以是整个硬盘或已创建的软RAID&am…

Linux环境PHP5.5以上连接SqlServer2008【全网最经典无错版】

linux版本&#xff1a;64位CentOS 6.4 Nginx版本&#xff1a;nginx1.8.0 php版本&#xff1a;php5.5.28 Sqlserver版本&#xff1a;2008 FreeTDS版本&#xff1a;0.95 关于Linux环境安装NginxPHP参考Linux环境Nginx安装与调试以及PHP安装 即可。一般来说&#xff0c;PHPmysql是…

python矩阵运算库效率_python - 布尔矩阵运算的最快方法_performance_酷徒编程知识库...

只需在compute中进行一些小的更改&#xff1a;def compute(m, n):m np.asarray(m)n np.asarray(n)# Apply mask N in advancem2 m & n# Pack booleans into uint8 for more efficient bitwise operations# Also transpose for better caching (maybe?)mb np.packbits(…

hibernate-session中的方法

1.操作实体对象的方法 save() 保存 update() 更新 saveOrUpdate() 保存或更新 delete() 删除 2.操作缓存的方法 clear() 清除所有缓存 evit() 将指定对象清除出缓存 flush() 刷新到数据库中&#xff08;&#xff09;马上执行sql语句&#xff0c;不会清除session缓存&#x…

[JZOJ4786]小a的强迫症

[JZOJ4786]小a的强迫症 题目大意&#xff1a; 有\(n(n\le10^5)\)种颜色的珠子&#xff0c;第\(i\)种颜色有\(num[i]\)个。你要把这些珠子排成一排&#xff0c;使得第\(i\)种颜色的最后一个珠子一定在第\(i1\)种珠子的最后一个珠子之前&#xff0c;求方案数。 思路&#xff1a; …

Servlet,过滤器,监听器,拦截器的区别

由于最近两个月工作比较清闲&#xff0c;个人也比较“上进”&#xff0c;利用工作空余时间&#xff0c;也继续学习了一下&#xff0c;某天突然想起struts2和struts1的区别的时 候&#xff0c;发现为什么struts1要用servlet&#xff0c;而struts2要用filter呢&#xff1f;一时又…

Linux环境Nginx安装多版本PHP

关于Linux环境Nginx安装与调试以及PHP安装参考此文即可&#xff1a;http://blog.csdn.net/unix21/article/details/8544922linux版本&#xff1a;64位CentOS 6.4 Nginx版本&#xff1a;nginx1.8.0 php版本&#xff1a;php5.5.28 & php5.4.44 所谓多版本多版本PHP就是php5.4…

java 扫描tcp端口号_多线程TCP端口扫描 java实现

界面部分&#xff1a;import java.awt.Color;import java.awt.Container;import java.awt.FlowLayout;import java.awt.event.WindowAdapter;import java.awt.event.WindowEvent;import javax.swing.JDialog;import javax.swing.JFrame;import javax.swing.JLabel;import javax…

【go同步编程】

锁 互斥锁 函数write中的这条defer语句保证了在该函数被执行结束之前互斥锁mutex一定会被解锁。 var mutex sync.Mutex func write() { mutex.Lock() defer mutex.Unlock() // 省略若干条语句 } func repeatedlyLock() {var mutex sync.Mutexfmt.Println("Lock the lock. …

Linux环境PHP7.0安装

PHP7和HHVM比较PHP7的在真实场景的性能确实已经和HHVM相当, 在一些场景甚至超过了HHVM。HHVM的运维复杂, 是多线程模型, 这就代表着如果一个线程导致crash了, 那么整个服务就挂了, 并且它不会自动重启。另外它采用JIT, 那么意味着, 重启以后要预热, 没有预热的情况下, 性能较为…

myeclipse java可视化_使用MyEclipse可视化开发Hibernate实例

使用MyEclipse可视化开发Hibernate实例2.7节的例子源代码在配套光盘sourcecode/workspace目录的chapter02_first项目中。这个实例主要演示如何使用MyEclipse的可视化开发工具开发Hibernate应用&#xff0c;利用MyEclipse可以提高我们开发Java EE应用的效率。操作的数据库表还是…

day20 文件上传下载

2019独角兽企业重金招聘Python工程师标准>>> 文件上传基础及api解析&#xff1a; 文件上传最终版&#xff1a; 文件下载&#xff1a; 转载于:https://my.oschina.net/u/2356966/blog/648774

腾讯开源基于 mmap 的高性能 key-value 组件 MMKV

腾讯微信团队宣布开源 MMKV &#xff0c;这是基于 mmap 内存映射的 key-value 组件&#xff0c;底层序列化/反序列化使用 protobuf 实现&#xff0c;主打高性能和稳定性。MMKV 从 2015 年中至今&#xff0c;在 iOS 微信上使用已有近 3 年&#xff0c;其性能和稳定性经过了时间的…

Linux环境thinkphp配置以及数据源驱动修改

项目中需要用到thinkphp&#xff0c;以下简称tp。linux版本&#xff1a;64位CentOS 6.4 Nginx版本&#xff1a;nginx1.8.0 php版本&#xff1a;php5.5.28 thinkphp版&#xff1a;3.2.31.安装LNMP Linux环境Nginx安装与调试以及PHP安装2.项目框架 tp源码下载http://www.thinkphp…

《Linux内核设计与实现》读书笔记 第三章 进程管理

第三章进程管理 进程是Unix操作系统抽象概念中最基本的一种。我们拥有操作系统就是为了运行用户程序&#xff0c;因此&#xff0c;进程管理就是所有操作系统的心脏所在。 3.1进程 概念&#xff1a; 进程&#xff1a;处于执行期的程序。但不仅局限于程序&#xff0c;还包含其他资…

java持续集成soapui_集成testNG到JavaAPI测试-执行多条用例

*****************************************************************在这门课里你将学到Web Services(SOAP WebService和REST API)的手动测试及自动化测试&#xff0c;熟练使用Groovy脚本自动化测试WebService。这门课程设计的是从零基础入门开始学&#xff0c;然后以循序渐进…

python-os

os.listdir(path):path-->路径 返回类型为listos.getcwd() 获取当前工作目录os.chdir() 切换工作目录os.mkdir() 新建目录os.path.exists()os.path.isdir() os.path.join() 拼接字符串路径os.path.exists(rpath) 判断路径是否存在 r原始路径os.path.isdir() 判断是否是文件夹…

NetBeans配置Xdebug 远程调试PHP

很多PHP程序员使用echo&#xff0c;dump等比较原始的方法调试&#xff0c;这是非常落后的。几年前本人写过一篇&#xff1a; NetBeans配置Xdebug 由于那篇文档还需要引用本人写的其他文档&#xff0c;感觉有些分散&#xff0c;所以这里重新写一篇完整的。linux版本&#xff1a;…

java自定义上下文对象_Java框架_Spring应用上下文对象加载配置

我们都知道IOC是spring框架的核心&#xff0c;主要作用是控制反转&#xff0c;把我们需要的对象从容器中提供给我们&#xff0c;但是IOC是如何加载我们所需要的对象的&#xff1f;Spring容器是IOC容器的一种&#xff0c;它通过ApplicationContext接口将我们所需要的配置文件进行…

ThreadLocal源码分析

ThreadLocal的作用 Java对象是线程间共享的&#xff0c;但有时我们需要一些线程间隔离的对象&#xff0c;该对象只能由同一个线程读写&#xff0c;对其他线程不可见。ThreadLocal正式提供了这样的机制&#xff0c;详细使用方式请参考Java ThreadLocal。 ThreadLocal实现原理 自…

远程连接windows出现身份验证错误,提示由于CredSSP加密Oracle修正解决方案

本机操作系统(OS版本:10.0.17134) 远程计算机操作系统&#xff08;OS版本:6.3.9600&#xff09; 远程连接的时候报错“出现身份验证错误&#xff0c;要求的函数不受支持。远程计算机:xxx 这可能是由于CredSSP加密Oracle修正,若要了解详细信息...” 原因是系统更新安装了补丁&am…

MediaWiki安装

MediaWiki可以方便的让你搭建自己的wiki&#xff0c;公司内部使用非常方便官网&#xff1a; https://www.mediawiki.org/wiki/MediaWiki安装MediaWiki的必要环境 PHPMysql 下载最新版解压即可 # tar -xzvf mediawiki-1.25.2.tar.gz # mv mediawiki-1.25.2 wiki 输入首页引导一…

sql的四种连接 用mysql的语句写_170221、浅谈mysql的SQL的四种连接

例子&#xff1a;-------------------------------------------------a表 id name b表 id job parent_id1 张3 1 23 12 李四 2 34 23 王武 3 34 4a.id同parent_id 存在关…

MySQL冷备份的跨操作系统还原

数据来源&#xff1a;linux平台mysql版本为5.7 数据去向&#xff1a;windows平台mysql版本为5.7 操作步骤&#xff1a; 第一步&#xff1a;关闭mysql服务 service mysqld stop 第二步&#xff1a;归档linux平台下mysql的数据目录 tar -czvf data.tar.gz /usr/local/mysql/data …

Java 社区领袖联合发文:别慌,Java 仍然是免费的!

开发四年只会写业务代码&#xff0c;分布式高并发都不会还做程序员&#xff1f; >>> 在去年的 Java One 上&#xff0c;Mark Cavage 当时宣布 Oracle 将逐步开源 Oracle JDK 的专有功能&#xff08;商业特性&#xff09;。Oracle Java 平台产品管理高级总监 Donald …

Squid安装

最新版Squid安装 http://www.squid-cache.org/Versions/v3/3.5/# wget http://www.squid-cache.org/Versions/v3/3.5/squid-3.5.7.tar.gz# tar zxvf squid-3.5.7.tar.gz# cd squid-3.5.7# ./configure --prefix/usr/local/squid# make && make install# chmod -R 777 /…

Java内部类手机专卖店_JAVA——内部类的那些事儿

obj3.func();//3.2 访问静态内部类的静态方法(通过类名访问)Outer.StaInner.staFunc();//4 局部内部类访问局部变量Outer obj4 new Outer();obj4.local();//5 匿名内部类Outer obj5 new Outer();obj5.anonymous();//6 匿名内部类作为参数asPara(new AbstractClass() {public …