Skip to content
RiqueZhang edited this page Jul 28, 2015 · 1 revision

云设备与云端通信SDK接口设计

张运奎                                                                                                                                                                                         下载sdk

TP-LINK TECHNOLOGIES CO., LTD
http://www.tp-link.com.cn
SouthBuilding, No.5 Keyuan Road, Central Zone Science & TechnologyPark, NanShan ShenZhen, P. R. China


版本历史

版本/状态 作者 起止日期 描述
V1.5 张运奎 2015-7-27 1. 增加动态链接库
2. 删除不必要提供的接口
V1.4 张运奎 2015-6-23 1. 修改云设备接口命名及调用方法
V1.3 张运奎 2015-5-25 1. 修改第三方json库为json-c-0.9
V1.2 张运奎 2015-5-22 1. 修改SDK接口排版
V1.1 张运奎 2015-5-21 1. 修改接口deviceConnect,去除回调方法
2. 增加虚接口responseXXX,需调用者实现
3. 修改SDK使用范例
V1.0 张运奎 2015-5-18 初创

摘要

本文档将作为《云设备与云端通信接口设计》设计文档的补充内容,将详细介绍和定义云设备在与云端交互的过程中的一些动态特性及相应的处理策略。同时为简化云设备处理业务,特将这些动态特性和相应的处理策略进行c语言版本的封装,提供Linux平台的SDK。

关键字云设备 云端通信接口 动态特性 处理策略 SDK

目录

1 简介

本文档将作为《云设备与云端通信接口设计》设计文档的补充内容,将详细介绍和定义云设备在与云端交互的过程中的一些动态特性及相应的处理策略。同时为简化云设备处理业务,特将这些动态特性和相应的处理策略进行c语言版本的封装,提供Linux平台的SDK。

本文将从链路管理和业务逻辑两个大方面进行介绍,最后介绍SDK接口定义与使用方法。

链路管理部分包含:

  1. 与云端链接的相关策略,包括建立链接、重新建立链接和断开链接等。

业务逻辑部分包含:

  1. 与收发数据相关的策略,包括收发数据的过程中对异常情况的判断及处理;
  2. 云设备超时处理机制介绍。

回到目录

2 链路管理部分

本节将从云设备与云端建立链接、重新建立链接以及断开链接三个方面介绍云设备的处理策略。

回到目录

2.1 建立链接

云设备在一开机即主动与云端建立链接,主要分三个阶段:建立TCP链接、建立SSL链接以及在SSL链接基础上的与云端三步握手,如图2-1所示:

                                                                             2-1

                                                                                    图2-1 云设备与云端建立链接过程

其中:

  1. TCP链接使用标准的TCP链接建立流程。如果TCP建立过程中失败,将触发重连(详见下述2.2节重新建立连接部分)。
  2. SSL链接使用标准的SSL链接建立流程,需注意在建立SSL链接时要开启对云端证书的验证及对云端域名的验证过程。如果SSL建立过程中失败,将触发重连。
  3. 三步握手过程详见《云设备与云端通信接口设计》中对云设备与云端链路上的初始工作的描述。如果在三步握手过程中出现超时(超时判断策略详见下述3.2.3节的三步握手过程超时判断策略),将触发重连。

回到目录

2.2 重新建立链接

2.2.1 重新建立链接时机

云设备重新建立链接的时机有以下几点:

  1. 开机建立TCP链接或SSL链接失败。
  2. SSL链接建立完成后,如果在与云端交互的三次握手过程中发生超时(详见下述3.2.3节的三步握手过程超时判断策略),则进入重连流程。
  3. 在与云端链接正式建立后,默认的重连策略是:用户触发操作连续超时两次非用户触发操作连续超时三次则触发重连机制。(详见下述3.2节的超时机制)。且这里的计数是针对单个操作进行计数,不对所有操作进行计数。
  4. 每个设备到云端方向的请求,在特定的调用环境中可以选择私有超时处理策略,私有策略优先于默认策略执行,在该策略执行后可选择继续执行默认处理策略或者是跳过;这个机制是为了方便后续业务逻辑定制,目前仅有握手阶段的心跳包采取了私有策略,其他情况下的请求都使用默认策略。
  5. 发送数据失败(判断策略详见下述3.1.1节的发送数据部分)。
  6. 在收到云端的stopConnect事件后,将会按照stopConnect的重连策略进行重连(详见下述2.2.4节)。

回到目录

2.2.2 重新建立链接流程

重新建立链接流程如图2-2所示:

                                                                             2-2

                                                                                    图2-2 云设备重新建立链接流程

在重新建立链接时,首先释放当前的链接,然后不断的尝试建立连接,如果失败则等待一定时间(详见下述2.2.3重连时间间隔部分),然后再次重复重连动作,直到成功。

回到目录

2.2.3 重连时间间隔

重连的时间间隔从1s开始,以指数回退的方式逐渐递增等待的时间,每次时间延长一倍 ;回退时长超过一定限度后,以固定时间间隔进行重试。这个时间间隔应该大于心跳包间隔(15min,即900s);但不宜过长,应该保证在网络恢复以后,在不给云端带来过大压力的前提下尽快重新建立云连接。由于回退是以2为底数的,为了处理方便我们约定为2的10次方即1024s,即超过900s的最小间隔。

如果用户手动发起请求,则立刻进行单次链接请求;如果本次请求失败,则提醒用户,不进行重连,等待下次自动重连。

回到目录

2.2.4 stopConnect重连策略

在云设备收到云端的stopConnect事件后,等待reconnectTime时间后,进入重连流程。

回到目录

2.2.5 用户请求触发的重连

当与云端连接处于断开状态、且自动重连机制处于两次重试请求中间的等待期间,如果用户通过页面发起云服务请求,应该立即发起连接,使得用户的请求得到及时响应。该请求仅发送一次,失败后不会像自动重连循环一样进行指数回退、反复重试,而是直接提醒用户连接失败。如果用户请求发起时,自动重连正在进行中,则以当前这次连接结果通知用户。

这个机制的处理原则是:用户的主动请求优先级高于后台服务

回到目录

2.3 断开链接

云设备主动断开链接有以下两种情况:

  1. 在每次重新建立链接前,会主动断开当前链接。
  2. 在收到云端的illegalDevice报文后,会主动断开链接,且在本次上电运行过程中不再重连。同时向用户提示信息:“路由器设备信息异常,请联系TP-LINK技术支持4008863400处理。”并显示illegalType所表示的错误码。
  3. 在客户端升级固件前,会断开链接,并在断开链接前使用closeConnection事件通知云端。

回到目录

2.4 心跳包策略

  1. 短链接模式下不启动;
  2. 每次发包前会检查链路状态,当和云端没有成功建立链接的时候,不允许发送;
  3. 正常的心跳包间隔是15min
  4. 正常的心跳包的超时不予以处理,请参照超时处理策略关于心跳包处理的章节3.2.2.2
  5. SSL链路建立成功、开始握手时主动发送一个心跳包,不处理其回包结果(即不影响请求超时计数,而由整个握手过程的定时监控来进行异常处理)。

回到目录

3 业务逻辑部分

3.1 收发数据的异常判断及处理

3.1.1 发送数据

发送数据异常有以下两种情况:

  1. 发送数据接口返回错误(可能由SSL链路异常或底层链路异常等造成),此时将直接触发重连。
  2. 如果TCP链接被云端单向断开(模仿Linux平台下的SIGPIPE信号机制)或者数据没有发送完毕,重试两次以上后重连,任意一次成功后退出并重新计数。

回到目录

3.1.2 收取数据

云设备收取数据发生异常时,也会进行重试收取,但不会导致发送数据或重连等操作,不会对云端造成影响,所以在这里不再详述。

回到目录

3.1.3 对TCP FIN包的处理策略

云设备对FIN包不进行特殊处理,也就是说收到FIN包不会直接触发云设备的重连操作;而是收到FIN包的时候数据无法正常发送后,等到再下次发送操作时,上层发包模块发现链路异常才会触发重连操作。

回到目录

3.2 云设备超时相关机制

3.2.1 超时判断策略

针对单个云操作,在每个云操作报文发出后,如果5s之内(协议要求)没有收到回复报文则认为该操作超时。

回到目录

3.2.2 超时处理策略

3.2.2.1 默认超时处理策略
  1. 请求源自用户,云设备在首个请求超时后,在web页面上提示用户请求超时;再次超时后提示用户网络有问题,请检查网络连接,同时进行链路重连。
  2. 请求源自云设备自身的后台自动请求,则在单个请求连续三次请求超时后进行链路重连。

回到目录

3.2.2.2 heartBeat接口超时处理策略
  1. 三步握手过程中的心跳包,超时后,尝试重新发送心跳请求,若第三次还超时,则进入重连机制,重建链路。
  2. 周期性的心跳包,对云端的响应超时不进行处理,保持链路的连接状态将由其发送失败的情况触发。

回到目录

3.2.2.3 其他接口超时处理策略

其他接口(除heartBeat外的所有从设备端到云端端的接口)均使用默认超时处理策略。

回到目录

3.2.3 三步握手过程超时判断策略

heartBeat操作超时后会尝试三次重新发送,如果仍旧超时则进入重连机制;而收到正常回复或者错误回复都认为云端已经OK。

在收到heartbeat回复起,客户端期望在5s内收到getDeviceInfo请求;若getDeviceInfo操作等待超时,则进入重连机制。

在发送getDeviceInfo回复时,如果发送成功,客户端期望在10s内收到norifyEvent请求(包括了回复报文发送的5s和云端发送请求的5s),如果等待超时则进入重连机制;如果发送回复失败则会直接进入重连机制。

回到目录

4 SDK接口说明

在《云设备与云端通信接口设计》设计文档中定义了云设备与云端之间通信使用的API,这些API按方向分为两类:

  1. 云设备到云端的请求与应答;
  2. 云端到云设备的请求与应答。

在本SDK接口中:

  1. 云设备与云端之间的链路管理与策略配置,详见5.1.2节;
  2. 云设备到云端的请求与应答,通过以下方式完成:
    1. 调用者实现5.1.1.2.1节云设备回调方法cloud_response;
    2. 调用者调用5.1.3节云设备请求接口,获得相应消息ID;
    3. 在回调方法cloud_response中若消息ID匹配,则response_t* 即为相应应答数据结构。
  3. 云端到云设备的请求与应答,通过以下方式完成:
    1. 调用者实现5.1.1.2节云设备回调方法cloud_request_XXX系列方法;
    2. SDK在接收到云端的请求时,触发调用这些接口;
    3. 调用者在相应接口实现中完成对云端请求的应答;
    4. SDK获得该方法的返回值,经过处理后应答云端。
  4. 通用操作接口,定义了错误码、请求与应答数据结构与操作,以及其他操作;
  5. 第三方库,本SDK所使用的JSON库为json-c-0.9。

SDK接口架构图

回到目录

5 SDK接口定义

5.1 云设备接口

5.1.1 结构体

5.1.1.1 device_t
名称 内容
功能 云设备数据结构
声明
typedef struct device_t device_t;
备注 创建:通过接口device_new创建
销毁:通过接口device_destroy销毁
使用:其他云设备接口的必要参数

回到目录

5.1.1.2 device_func
名称 内容
功能 云设备回调方法
声明
typedef struct device_func {
	void (*cloud_response)(device_t* device, int msg_id, response_t* response);
	void (*cloud_notify_event)(device_t* device, const char* event, json_object* attribute);
	response_t* (*cloud_request_get_device_info)(device_t* device);
	response_t* (*cloud_request_get_fw_current_ver)(device_t* device);
	response_t* (*cloud_request_unbind_device)(device_t* device, const char* device_id,
							const char* cloud_user_name);
	response_t* (*cloud_request_set_alias)(device_t* device, const char* alias);
	response_t* (*cloud_request_get_fw_download_progress)(device_t* device);
	response_t* (*cloud_request_update_fw)(device_t* device, constchar* fw_url);
	response_t* (*cloud_request_get_wan_info)(device_t* device);
	response_t* (*cloud_request_get_lan_info)(device_t* device);
	response_t* (*cloud_request_get_wifi_basic)(device_t* device, int wifi_band);
	response_t* (*cloud_request_passthrough)(device_t* device, const char* data);
} device_func;
备注

回到目录

5.1.1.2.1 cloud_response
名称 内容
功能 云端应答回调
声明
void (*cloud_response)(device_t* device, int msg_id, response_t* response);
参数 device device_t* 云设备数据结构
msg_id int 消息ID
response response_t* 云端应答数据结构
返回
备注 云端推送相应消息ID的应答结构,必须实现

回到目录

5.1.1.2.2 cloud_notify_event
名称 内容
功能 事件通知回调
声明
void (*cloud_notify_event)(device_t* device, const char* event, json_object* attribute);
参数 device device_t* 云设备数据结构
event const char* 需要通知的事件
attribute json_object* 对应事件的属性,可为NULL
返回
备注 云端端推送消息的通用接口,event参数中可做更多扩展
event attribute
newFirmware:
云端推送用新的可用软件
{“fwUpdateType”:0}
fwUpdateType默认为1
fwUpdateType为0的时候,表示该固件强制升级,不需要用户介入,具体策略由设备端决定
legalDevice:
设备合法性验证成功
illegalDevice:
设备接收到此信息,表示云端禁止该设备接入云;
云端确认设备设备收到该事件后,会主动断开与设备之间的连接。
调用该事件时机包含但不限于如下:设备验证失败、后台主动禁用此设备
{“illegalType”:1}
illegalType:用于描述设备验证不通过的原因:
1:生产数据中无此设备ID,设备验证不通过,设备是非法设备;
2:deviceId、Mac、hwId不匹配,设备验证不通过,设备是非法设备;
3:云端获取设备基本信息失败,包括获取不到信息,信息少;
4:同相同ID的设备同时在线,可能设备存在仿冒;
>=5:待定
stopConnect:
设备接收到此信息,表示云端暂时禁止该设备接入云
{“reconnectTime”:0,“reason”:1}
reconnTime:
路由器重新新发起连接的最少时间间隔,以秒为单位
设备需要在reconnTime后的任意时间才可发起连接reconnTime==0则由设备端决定重连时间间隔
reason:
用于描述设备被断开连接的原因:
1:默认,云端异常,暂时拒绝服务;
2:设备连续多次发送的数据包的magicNum或者length错误;
>=3:待定

回到目录

5.1.1.2.3 cloud_request_get_device_info
名称 内容
功能 获取云设备基本信息
声明
response_t* (*cloud_request_get_device_info)(device_t* device);
参数 device device_t* 云设备数据结构
返回 response_t* 云设备应答数据结构
result deviceId char* 与机型无关、所有设备值唯一
cloudUserName char* 绑定的云账号,未绑定置为空
deviceName char* 设备名称
alias char* 由用户自定义的设备名称;初始值取设备名称(deviceModel+ 空格 + deviceHwVer),如TL-WDR7500 3.0
deviceMac char* 设备MAC地址(设备标贴显示的MAC,如:路由器是LAN MAC)
hwId char* 机型硬件ID
deviceModel char* 机型名称
deviceHwVer char* 硬件版本
fwId char* 设备当前的固件版本ID
fwVer char* 设备当前的固件版本
备注 该回调方法为云设备与云端三步握手的第二步,必须实现

回到目录

5.1.1.2.4 cloud_request_get_fw_current_ver
名称 内容
功能 获取云设备当前firmware版本
声明
response_t* (*cloud_request_get_fw_current_ver)(device_t* device);
参数 device device_t* 云设备数据结构
返回 response_t* 云设备应答数据结构
result fwId char* 设备当前的固件版本ID
fwVer char* 设备当前的固件版本
备注

回到目录

5.1.1.2.5 cloud_request_unbind_device
名称 内容
功能 在云设备上解除绑定云账号
声明
response_t* (*cloud_request_unbind_device)(device_t* device, const char* device_id, const char* cloud_user_name);
参数 device device_t* 云设备数据结构
device_id const char* 设备唯一ID
cloud_user_name const char* 云账号
返回 response_t* 云设备应答数据结构
result
备注 通知设备被解除绑定
该接口无论设备返回何种error code,云端都不处理
下次设备接入云端,调用device_request_bind_device(不带密码)时,云端会返回-20507

回到目录

5.1.1.2.6 cloud_request_set_alias
名称 内容
功能 设置云设备别名
声明
response_t* (*cloud_request_set_alias)(device_t* device, const char* alias);
参数 device device_t* 云设备数据结构
alias const char* 用户自定义的设备名称
返回 response_t* 云设备应答数据结构
result
备注 通过App设置用户自定义设备名称

回到目录

5.1.1.2.7 cloud_request_get_fw_download_progress
名称 内容
功能 获取下载进度
声明
response_t* (*cloud_request_get_fw_download_progress)(device_t* device);
参数 device device_t* 云设备数据结构
返回 response_t* 云设备应答数据结构
result status int 0-失败,1-正在下载,
2-下载完成,3-未开始下载
progress int 下载进度的百分比(0-100之间)
备注 仅当用户下载升级固件时使用
远程升级时,刷新下载进度时获取云设备的下载进度

回到目录

5.1.1.2.8 cloud_request_update_fw
名称 内容
功能 远程软件升级
声明
response_t* (*cloud_request_update_fw)(device_t* device, const char* fw_url);
参数 device device_t* 云设备数据结构
fw_url const char* 待升级软件存放的URL
云设备会从此URL下载固件
返回 response_t* 云设备应答数据结构
result updateTime int 预估软件升级的时间,不包括下载过程
以秒为单位
备注 仅当用户登录后使用
服务端下发软件升级指令

回到目录

5.1.1.2.9 cloud_request_get_wan_info
名称 内容
功能 获取云设备WAN口信息
声明
response_t* (*cloud_request_get_wan_info)(device_t* device);
参数 device device_t* 云设备数据结构
返回 response_t* 云设备应答数据结构
result wanType int 0-dynamic
1-static
2-pppoe
3-pppoe+dynamic
4-pppoe+static
5-pptp+dynamic
6-pptp+static
7-l2tp+dynamic
8-l2tp+static
wanIp const char* 云设备WAN口IP
wanMask const char* 掩码
wanGateway const char* 网关
dns1 const char* 主DNS
dns2 const char* 备用DNS
备注

回到目录

5.1.1.2.10 cloud_request_get_lan_info
名称 内容
功能 获取云设备LAN口信息
声明
response_t* (*cloud_request_get_lan_info)(device_t* device);
参数 device device_t* 云设备数据结构
返回 response_t* 云设备应答数据结构
result lanIp const char* 云设备LAN口IP
lanMac const char* 云设备LAN口MAC
备注

回到目录

5.1.1.2.11 cloud_request_get_wifi_basic
名称 内容
功能 获取云设备WiFi基本信息
声明
response_t* (*cloud_request_get_wifi_basic)(device_t* device, int wifi_band);
参数 device device_t* 云设备数据结构
wifi_band int WiFi频段参数:0-2.4G,1-5G
返回 response_t* 云设备应答数据结构
result wifiState int 0-关闭
1-开启
wifiSsid const char* SSID
wifiSecType int 0-无加密
1- WPA/WPA2-PSK
2- WPA/WPA2
3- WEP
wifiKey const char* WiFi密码(optional)
备注 暂不关心WEP及WPA加密

回到目录

5.1.1.2.12 cloud_request_passthrough
名称 内容
功能 透传类型接口
声明
response_t* (*cloud_request_passthrough)(device_t* device, const char* data);
参数 device device_t* 云设备数据结构
data const char* 透传的数据,可为JSON字符串
返回 response_t* 云设备应答数据结构
result responseData const char* 设备响应透传数据的回复,可为JSON字符串
备注 云端不需要关注requestData的内容,只做数据转发,目前主要实现针对App端实现的远程管理
注:requestData及responseData的数据内容请查看《设备配置接口设计》及《SLP平台交互接口设计》

回到目录

5.1.2 云设备基础接口

5.1.2.1 device_new
名称 内容
功能 创建云设备数据结构
声明
device_t* device_new(device_func* func);
参数 func device_func* 云设备回调方法
返回 device_t* 非NULL为成功,NULL为失败
备注 必须在本接口返回成功后,以下接口才可用

回到目录

5.1.2.2 device_destroy
名称 内容
功能 销毁云设备数据结构
声明
int device_destroy(device_t* device);
参数 device device_t* 云设备数据结构
返回 int 0为成功,负数为失败
备注 调用本接口后,以下接口均不可用

回到目录

5.1.2.3 device_connect
名称 内容
功能 建立SSL链接,并完成三步握手过程
声明
int device_connect(device_t* device, const char* host, int port);
参数 device device_t* 云设备数据结构
host const char* 云端主机地址
port int 云端主机端口
返回 int 0为成功,负数为失败
备注

回到目录

5.1.2.4 device_disconnect
名称 内容
功能 断开SSL链接
声明
int device_disconnect(device_t* device);
参数 device device_t* 云设备数据结构
返回 int 0为成功,负数为失败
备注

回到目录

5.1.2.5 device_set_heartbeat_interval
名称 内容
功能 设置云设备向云端发送心跳的时间间隔
声明
int device_set_heartbeat_interval(device_t* device, int second);
参数 device device_t* 云设备数据结构
second int 时间间隔,以秒为单位
返回 int 0为成功,负数为失败
备注 若不进行设置,则默认时间间隔为15分钟
SDK内自行向云端发送心跳

回到目录

5.1.2.6 device_set_request_response_timeout
名称 内容
功能 设置云设备向云端发送请求的超时时间
声明
int device_set_request_response_timeout(device_t* device, int millisecond);
参数 device device_t* 云设备数据结构
millisecond int 超时时间,以毫秒为单位
返回 int 0为成功,负数为失败
备注 若不进行设置,则默认超时时间为5秒

回到目录

5.1.3 云设备请求接口

5.1.3.1 device_request_register
名称 内容
功能 云账号注册
声明
int device_request_register(device_t* device, const char* cloud_user_name, const char* cloud_password, 
				const char* veri_code, int account_type);
参数 device device_t* 云设备数据结构
cloud_user_name const char* 云账号
cloud_password const char* 密码
veri_code const char* 验证码
account_type int 0-邮箱,1-手机号码
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
名称 内容
result
code -20002 请求超时
-20200 邮箱地址格式错误
-20201 电话号码格式错误
-20610 账户类型错误
-20604 账号既不是邮箱也不是手机
-20603 账户已存在
-20607 验证码错误
-20506 该设备已经被绑定给其他账户
-20676 验证码失效,需要重新获取(同一账号连续触发了3次错误的验证码验证,则该账号的验证码失效)

回到目录

5.1.3.2 device_request_reset_cloud_password
名称 内容
功能 重置云账号密码
声明
int device_request_reset_cloud_password(device_t* device, const char* cloud_user_name, const char* cloud_password,
					const char* veri_code, int account_type);
参数 device device_t* 云设备数据结构
cloud_user_name const char* 云账号
cloud_password const char* 密码
veri_code const char* 验证码
account_type int 0-邮箱,1-手机号码
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
名称 内容
result
code -20002 请求超时
-20200 邮箱地址格式错误
-20201 电话号码格式错误
-20610 账户类型错误
-20604 账号既不是邮箱也不是手机
-20600 账户不存在
-20607 验证码错误
-20506 该设备已经被绑定给其他账户
-20676 验证码失效,需要重新获取(同一账号连续触发了3次错误的验证码验证,则该账号的验证码失效)

回到目录

5.1.3.3 device_request_get_cloud_account_status
名称 内容
功能 获取云账号状态
声明
int device_request_get_cloud_account_status(device_t* device, const char* cloud_user_name);
参数 device device_t* 云设备数据结构
cloud_user_name const char* 云账号
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
名称 内容
result status int 当前账户的状态
0-未注册账户,1-正常用户,2-被锁定用户
code -20200 邮箱地址格式错误
-20201 电话号码格式错误
-20604 账号既不是邮箱又不是手机

回到目录

5.1.3.4 device_request_bind_device
名称 内容
功能 绑定云账号和设备(含登录)
声明
int device_request_bind_device(device_t* device, const char* device_id, const char* cloud_user_name, 
				const char * cloud_password);
参数 device device_t* 云设备数据结构
device_id const char* 设备唯一ID
cloud_user_name const char* 云账号
cloud_password const char* 密码
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
名称 内容
result
code -20002 请求超时
-20501 Device ID不存在,无该设备
-20200 邮箱地址格式错误
-20201 电话号码格式错误
-20604 账号既不是邮箱又不是手机
-20601 密码格式错误
-20600 账户不存在
-20601 账户名与密码不匹配
-20506 该设备已经被绑定给其他账户
-20507 该设备已经被APP端或者云端解除绑定(用于设备启动后的登录过程)
-20661 账号被锁定,密码输入错误次数过多,账号被锁定2小时

回到目录

5.1.3.5 device_request_unbind_device
名称 内容
功能 在云设备上解除绑定云账号
声明
int device_request_unbind_device(device_t* device, const char* device_id, const char* cloud_user_name);
参数 device device_t* 云设备数据结构
device_id const char* 设备唯一ID
cloud_user_name const char* 云账号
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
名称 内容
result
code -20002 请求超时
-20501 Device ID不存在,无该设备
-20200 邮箱地址格式错误
-20201 电话号码格式错误
-20604 账号既不是邮箱又不是手机
-20600 账户不存在

回到目录

5.1.3.6 device_request_get_fw_list
名称 内容
功能 查询可用新firmware列表
声明
int device_request_get_fw_list(device_t* device, const char* fw_id, const char* hw_id);
参数 device device_t* 云设备数据结构
fw_id const char* 当前设备的fwId
hw_id const char* 当前设备的hwId
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
名称 内容
result fwList json_object* Array
fwList fwType int enum类型,定义待拓展
例如此版软件重要程度等,目前默认为0
fwVer char* 软件版本
fwReleaseDate char* 软件发布日期
fwUrl char* 可用软件下载地址
fwReleaseLog char* 软件发布日志
fwReleaseLogUrl char* 完整日志连接地址(optional)
fwLocation int 适用范围(optional)
0-通用版(默认),1-henna河南的特制版(待定)
code -20002 请求超时
-20504 硬件ID不存在
-20505 固件ID不存在
-20703 硬件ID及固件ID不匹配
备注 响应结果为上述结构的一个数组,所以支持用户在多个release版本中选择
如果此列表为空,则认为设备当前已是最新版本
当云端收到此API请求时,需要获取当前云设备的版本,仅返回此版本之后的版本信息
fwReleaseLogUrl,当fwReleaseLog过长超出字数范围后,提供完整的ReleaseLog显示页面的链接
Array最大条目8条

回到目录

5.1.3.7 device_request_push_fw_download_progress
名称 内容
功能 云设备主动推送下载进度
声明
int device_request_push_fw_download_progress(device_t* device, int status, int progress);
参数 device device_t* 云设备数据结构
status int 当前状态
0-失败,1-正在下载,2-下载完成
progress int 下载进度的百分比(0-100之间)
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
云设备主动向服务端推送下载固件进度
正在下载时可不主动通知,下载失败或下载完成时需向server推送上报
名称 内容
result
code -20002 请求超时
-20701 推送的下载状态错误
-20702 推送的下载进度错误

回到目录

5.1.3.8 device_request_get_reg_veri_code
名称 内容
功能 获取注册验证码
声明
int device_request_get_reg_veri_code(device_t* device, const char* cloud_user_name, int account_type);
参数 device device_t* 云设备数据结构
cloud_user_name const char* 云账号
account_type int 0-邮箱,1-手机号码
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
用户注册时,通过邮箱或者手机发送验证码给用户,以完成注册
验证码有效时间为1小时
名称 内容
result
code -20002 请求超时
-20200 邮箱地址格式错误
-20201 电话号码格式错误
-20604 账号既不是邮箱又不是手机
-20603 账户已存在
-20610 账户类型错误
-20662 设备被锁定,24小时内不能再发送验证码

回到目录

5.1.3.9 device_request_get_reset_password_veri_code
名称 内容
功能 获取重设密码的验证码
声明
int device_request_get_reset_password_veri_code(device_t* device, const char* cloud_user_name,
						int account_type);
参数 device device_t* 云设备数据结构
cloud_user_name const char* 云账号
account_type int 0-邮箱,1-手机号码
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
用户忘记密码时,通过邮箱或者手机发送验证码给用户,以完成重新设置密码
验证码有效时间为1小时
名称 内容
result
code -20002 请求超时
-20200 邮箱地址格式错误
-20201 电话号码格式错误
-20604 账号既不是邮箱又不是手机
-20600 账户不存在
-20610 账户类型错误
-20662 设备被锁定,24小时内不能再发送验证码

回到目录

5.1.3.10 device_request_check_reg_veri_code
名称 内容
功能 检查注册验证码是否正确
声明
int device_request_check_reg_veri_code(device_t* device, const char* cloud_user_name, const char* veri_code);
参数 device device_t* 云设备数据结构
cloud_user_name const char* 云账号
veri_code const char* 验证码
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
在用户提交注册前,可先告诉用户验证码是否正确
名称 内容
result
code -20002 请求超时
-20676 验证码失效,需要重新获取(同一账号连续触发了3次错误的验证码验证,则该账号的验证码失效)
-20200 邮箱地址格式错误
-20604 账号格式错误,既不是邮箱也不是手机号码
-20201 电话号码格式错误
-20607 验证码错误

回到目录

5.1.3.11 device_request_check_reset_password_veri_code
名称 内容
功能 检查重设密码的验证码是否正确
声明
int device_request_check_reset_password_veri_code(device_t* device, const char* cloud_user_name,
							const char* veri_code);
参数 device device_t* 云设备数据结构
cloud_user_name const char* 云账号
veri_code const char* 验证码
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
在用户提交重设密码前,可先告诉用户验证码是否正确
名称 内容
result
code -20002 请求超时
-20200 邮箱地址格式错误
-20201 电话号码格式错误
-20604 账号既不是邮箱又不是手机
-20676 验证码失效,需要重新获取(同一账号连续触发了3次错误的验证码验证,则该账号的验证码失效)
-20607 验证码错误

回到目录

5.1.3.12 device_request_modify_cloud_password
名称 内容
功能 修改云账号密码
声明
int device_request_modify_cloud_password(device_t* device, const char* cloud_user_name,
						const char* old_cloud_password,
						const char* new_cloud_password);
参数 device device_t* 云设备数据结构
cloud_user_name const char* 云账号
old_cloud_password const char* 原云账号密码
new_cloud_password const char* 新云账号密码
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
名称 内容
result
code -20002 请求超时
-20200 邮箱地址格式错误
-20201 电话号码格式错误
-20604 账号既不是邮箱又不是手机
-20615 原密码格式错误
-20600 账户不存在
-20601 账户名与密码不匹配
-20616 新密码格式错误,包括长度不符合要求
-20661 账户已锁定,密码输入错误次数过多,账号被锁定2小时

回到目录

5.1.3.13 device_request_notify_event
名称 内容
功能 事件通知
声明
int device_request_notify_event(device_t* device, const char* event, json_object* attribute);
参数 device device_t* 云设备数据结构
event const char* 需要通知的事件
attribute json_object* 对应事件的属性
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
设备端推送消息的通用接口,event参数中可做更多扩展
event attribute
closeConnection:
云端推送用新的可用软件
{“reason”:0}
reason(int),设备断开连接的原因
0-默认,1-准备更新固件,2-更换拨号方式或重新拨号

回到目录

5.1.3.14 device_request_push_plugin_list
名称 内容
功能 云设备报告插件列表
声明
int device_request_push_plugin_list(device_t* device, const char* fw_id, json_object* pre_installed_list,
					json_object* manual_installed_list);
参数 device device_t* 云设备数据结构
fw_id const char* 当前DUT上运行的Firmware ID
pre_installed_list json_object* Array,预安装插件列表
manual_installed_list json_object* Array,用户手动安装插件列表
Item of
Array
pluginId const char* 一个功能插件的唯一标识
version const char* 版本号
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
由云设备向云端提交已安装的功能插件列表的详细信息
名称 内容
result notInstalled int 未安装的插件数量
canUpdate int 可升级的插件数量
good int 优秀插件数量
excellent int 精选插件数量
code -20002 请求超时
-20902 plugin id not exist
-20903 plugin version not exist
-20904 preinstalled list size not right
-20905 manual install list size not right
-20906 list items are duplicate(pre_installed_list与manual_installed_list之间或者单个List内容有重复)
-20907 上报的Plugin信息中有与设备FW及HW不匹配的情况
备注 云端端根据该列表返回未安装和需要更新的插件列表
注意事项:
1. 已下架插件不会计入各相关数量中
2. 优秀插件和精选插件数量,指的是该设备所适配的插件数量,包括已安装与未安装的

回到目录

5.1.3.15 device_request_get_can_update_plugins
名称 内容
功能 云设备请求可更新插件信息
声明
int device_request_get_can_update_plugins(device_t* device, int index_start, int index_end);
参数 device device_t* 云设备数据结构
index_start int 请求一批可更新插件的起始序号
index_end int 结束序号
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
用于检查某一个Plugin的更新情况,返回当前可更新插件最新版本信息
名称 内容
result num int 响应的可更新Plugin列表数量
list json_object* Array,列表key值
Item of
Array
pluginId char* 一个功能插件的唯一标识
name char* 名称
version char* 版本号
size char* 安装后占用flash体积(值为int)
author char* 功能插件发布者
tag char* Plugin的标签
updateLog char* 更新说明
dataUrl char* 安装包下载的URL
webZipForAppUrl char* 手机端安装包URL
descForWebUrl char* 功能描述URL(用于web端)
descForAppUrl char* 功能描述URL(用于app端)
icoForWebUrl char* 图标URL(用于web端)
icoForAppUrl char* 图标URL(用于app端)
releaseTime char* 发布时间
components char* 该功能插件的组件
code -20002 请求超时
-20901 参数逻辑错误index_start大于index_end

回到目录

5.1.3.16 device_request_get_not_installed_plugins
名称 内容
功能 云设备请求未安装插件信息
声明
int device_request_get_not_installed_plugins(device_t* device, int index_start, int index_end);
参数 device device_t* 云设备数据结构
index_start int 请求一批未安装插件的起始序号
index_end int 结束序号
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
名称 内容
result num int 响应的可更新Plugin列表数量
list json_object* Array,列表key值
Item of
Array
pluginId char* 一个功能插件的唯一标识
name char* 名称
version char* 版本号
size char* 安装后占用flash体积(值为int)
author char* 功能插件发布者
tag char* Plugin的标签
updateLog char* 更新说明
dataUrl char* 安装包下载的URL
webZipForAppUrl char* 手机端安装包URL
descForWebUrl char* 功能描述URL(用于web端)
descForAppUrl char* 功能描述URL(用于app端)
icoForWebUrl char* 图标URL(用于web端)
icoForAppUrl char* 图标URL(用于app端)
releaseTime char* 发布时间
components char* 该功能插件的组件
code -20002 请求超时
-20901 参数逻辑错误index_start大于index_end

回到目录

5.1.3.17 device_request_check_plugin_update
名称 内容
功能 云设备请求某一个功能插件更新情况
声明
int device_request_check_plugin_update(device_t* device, const char* plugin_id, const char* version,
					int property);
参数 device device_t* 云设备数据结构
plugin_id const char* 一个功能插件的唯一标识
version const char* 版本号
property int 预装插件还是用户手动插件
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
用于检查某一个Plugin的更新情况
名称 内容
result pluginId char* 一个功能插件的唯一标识
status int 该插件在云设备端应该显示的状态
1-已安装且可更新,2-已是最新
name char* 名称
version char* 版本号
size char* 安装后占用flash体积(值为int)
author char* 功能插件发布者
tag char* Plugin的标签
updateLog char* 更新说明
dataUrl char* 安装包下载的URL
webZipForAppUrl char* 手机端安装包URL
descForWebUrl char* 功能描述URL(用于web端)
descForAppUrl char* 功能描述URL(用于app端)
icoForWebUrl char* 图标URL(用于web端)
icoForAppUrl char* 图标URL(用于app端)
releaseTime char* 发布时间
components char* 该功能插件的组件
onShelf int 插件是否上架
0-已下架,1-已上架
code -20002 请求超时
-20902 plugin id不存在
-20903 plugin version不存在
-20907 上报的Plugin信息中有与设备FW及HW不匹配的情况
备注 当该系列插件已下架时,返回输入参数指定的插件版本信息,并status = 2,即告知设备,其所安装插件版本已为最新,不能再升级

回到目录

5.1.3.18 device_request_get_plugin_info
名称 内容
功能 云设备请求某一个功能插件更新情况
声明
int device_request_get_plugin_info(device_t* device, const char* plugin_id, const char* version, int property);
参数 device device_t* 云设备数据结构
plugin_id const char* 一个功能插件的唯一标识
version const char* 版本号
property int 预装插件还是用户手动插件
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
用于获取某一个Plugin的完整信息
名称 内容
result pluginId char* 一个功能插件的唯一标识
name char* 名称
version char* 版本号
size char* 安装后占用flash体积(值为int)
author char* 功能插件发布者
tag char* Plugin的标签
updateLog char* 更新说明
dataUrl char* 安装包下载的URL
webZipForAppUrl char* 手机端安装包URL
descForWebUrl char* 功能描述URL(用于web端)
descForAppUrl char* 功能描述URL(用于app端)
icoForWebUrl char* 图标URL(用于web端)
icoForAppUrl char* 图标URL(用于app端)
releaseTime char* 发布时间
components char* 该功能插件的组件
onShelf int 插件是否上架
0-已下架,1-已上架
code -20002 请求超时
-20902 plugin id不存在
-20903 plugin version不存在
-20907 上报的Plugin信息中有与设备FW及HW不匹配的情况

回到目录

5.1.3.19 device_request_get_plugins
名称 内容
功能 云设备按插件类型获取插件信息
声明
int device_request_get_plugins(device_t* device, int index_start, int index_end, const char* category);
参数 device device_t* 云设备数据结构
index_start int 起始序号
index_end int 结束序号
category const char* 插件类型(normal、good、excellent)
返回 int 消息ID,负数为失败
备注 通过回调方法cloud_response返回云端应答数据结构response_t*
名称 内容
result num int 响应的可更新Plugin列表数量
list json_object* Array,列表key值
Item of
Array
pluginId char* 一个功能插件的唯一标识
name char* 名称
version char* 版本号
size char* 安装后占用flash体积(值为int)
author char* 功能插件发布者
tag char* Plugin的标签
updateLog char* 更新说明
dataUrl char* 安装包下载的URL
webZipForAppUrl char* 手机端安装包URL
descForWebUrl char* 功能描述URL(用于web端)
descForAppUrl char* 功能描述URL(用于app端)
icoForWebUrl char* 图标URL(用于web端)
icoForAppUrl char* 图标URL(用于app端)
releaseTime char* 发布时间
components char* 该功能插件的组件
goodIcoUrl char* 优秀插件的图标URL(optional)
(优秀插件才有此项)
excellentImgUrl char* 精选插件的图标URL(optional)
(精选插件才有此项)
code -20002 请求超时
-20901 参数逻辑错误index_start大于index_end
备注 不返回已下架插件的相关信息
若输入参数category为不存在的类型,则返回空列表

回到目录

5.2 通用操作接口

5.2.1 错误码接口

5.2.1.1 error_code_t
名称 内容
功能 云设备数据结构
声明
typedef enum error_code_t{
	…
} error_code_t;
备注 云端返回的错误码信息,参见《云设备与云端通信接口设计》

回到目录

5.2.1.2 error_code_get_msg
名称 内容
功能 获取指定错误码的错误信息
声明
char* error_code_get_msg(error_code_t err_code);
参数 code error_code_t 错误码
返回 char* 不需要使用free释放内存

回到目录

5.2.2 应答包接口

5.2.2.1 response_t
名称 内容
功能 应答包数据结构
声明
typedef struct response_t response_t;
备注 创建:通过接口response_new/response_new_with_XXX创建
销毁:通过接口response_put销毁

回到目录

5.2.2.2 response_get
名称 内容
功能 增加指定response_t的引用计数
声明
response_t* response_get(response_t* response);
参数 response response_t* response_t实例
返回 response_t* 使用完成后,必须调用response_put

回到目录

5.2.2.3 response_put
名称 内容
功能 减少指定response_t的引用计数,当其为0时并释放相应内存
声明
void response_put(response_t* response);
参数 response response_t* response_t实例
返回

回到目录

5.2.2.4 response_new
名称 内容
功能 创建response_t实例
声明
response_t* response_new();
参数
返回 response_t* 使用完成后,必须调用response_put

回到目录

5.2.2.5 response_new_with_error_code
名称 内容
功能 创建包含指定应答错误码的response_t实例
声明
response_t* response_new_with_error_code(error_code_t err_code);
参数 err_code error_code_t 应答错误码
返回 response_t* 使用完成后,必须调用response_put

回到目录

5.2.2.6 response_new_with_result
名称 内容
功能 创建包含指定应答结果的response_t实例
声明
response_t* response_new_with_result(json_object* result);
参数 result json_object* 应答结果
返回 response_t* 使用完成后,必须调用response_put

回到目录

5.2.2.7 response_set_err_code
名称 内容
功能 设置指定response_t实例的应答错误码
声明
int response_set_err_code(response_t* response, error_code_t err_code);
参数 response response_t* response_t实例
err_code error_code_t 应答错误码
返回 int 0为成功,负数为失败

回到目录

5.2.2.8 response_get_err_code
名称 内容
功能 获取指定response_t实例的应答错误码
声明
error_code_t response_get_err_code(response_t* response);
参数 response response_t* response_t实例
返回 error_code_t

回到目录

5.2.2.9 response_set_err_msg
名称 内容
功能 设置指定response_t实例的应答错误信息
声明
int response_set_err_msg(response_t* response, const charchar* msg);
参数 response response_t* response_t实例
msg const char* 应答错误信息
返回 int 0为成功,负数为失败

回到目录

5.2.2.10 response_get_err_msg
名称 内容
功能 获取指定response_t实例的应答错误信息
声明
char* response_get_err_msg(response_t* response);
参数 response response_t* response_t实例
返回 char* 不需要使用free释放内存

回到目录

5.2.2.11 response_set_result
名称 内容
功能 设置指定response_t实例的应答结果
声明
int response_set_result(response_t* response, json_object* result);
参数 response response_t* response_t实例
result json_object* 应答结果
返回 int 0为成功,负数为失败

回到目录

5.2.2.12 response_get_result
名称 内容
功能 获取指定response_t实例的应答结果
声明
json_object* response_get_result(response_t* response);
参数 response response_t* response_t实例
返回 json_object* 不需要调用json_object_put

回到目录

5.2.2.13 response_get_from_json_object
名称 内容
功能 通过指定的json_object实例,创建response_t实例
声明
response_t* response_get_from_json_object(json_object* json);
参数 json json_object* json_object实例
返回 response_t* 使用完成后,必须调用response_put

回到目录

5.2.2.14 response_to_json_object
名称 内容
功能 将指定消息ID和response_t实例,转换成json_object实例
声明
json_object* response_to_json_object(int msg_id, response_t* response);
参数 msg_id int 消息ID
response response_t* response_t实例
返回 json_object* 使用完成后,必须调用json_object_put

回到目录

5.3 第三方库

5.3.1 库json-c

json-c的使用方法,可参考https://github.com/json-c/json-c

回到目录

6 SDK使用方法

6.1 目录结构

本SDK的目录,主要分为头文件目录inc和库文件目录lib。

头文件目录inc,提供了本SDK所提供的接口文件,包括:

  1. json相关宏定义,base.h;
  2. 云设备操作接口,device.h;
  3. 错误码定义,error_code.h;
  4. 应答包接口,response.h。

库文件目录lib,提供了本SDK所提供的库文件,包括:

  1. 静态链接库,libdeviceAPI.a;
  2. 动态链接库,libdeviceAPI.so。

回到目录

6.2 编译与链接

6.2.1 静态链接库

在源码文件中引用device.h,再执行编译命令:

gcc -g -lssl -lrt –lm -L/usr/local/lib/ –ljson -L../lib -ldeviceAPI *.c

其中,../lib为当前目录到库文件目录的相对目录,deviceAPI为静态链接库的库名。

回到目录

6.2.2 动态链接库

在源码文件中引用device.h,将libdeviceAPI.so移动到/usr/local/lib/,再执行编译命令:

gcc -g -lssl -lrt –lm -L/usr/local/lib/ –ljson -ldeviceAPI *.c

其中,deviceAPI为静态链接库的库名。

回到目录

6.3 使用范例

#include <stdlib.h>
#include <string.h>
#include "../inc/device.h"

static void response(device_t* device, int msg_id, response_t* response);
static void notify_event(device_t* device, const char* event, json_object* attribute);
static response_t* get_device_info(device_t* device);
static response_t* get_fw_current_ver(device_t* device);
static response_t* unbind_device(device_t* device, const char* device_id, const char* cloud_user_name);
static response_t* set_alias(device_t* device, const char* alias);
static response_t* get_fw_download_progress(device_t* device);
static response_t* update_fw(device_t* device, const char* fw_url);
static response_t* get_wan_info(device_t* device);
static response_t* get_lan_info(device_t* device);
static response_t* get_wifi_basic(device_t* device, int wifi_band);
static response_t* passthrough(device_t* device, const char* data);

int main(int argc, char** argv)
{
	device_func func;
	func.cloud_response = response;
	func.cloud_notify_event = notify_event;
	func.cloud_request_get_device_info = get_device_info;
	func.cloud_request_get_fw_current_ver = get_fw_current_ver;
	func.cloud_request_unbind_device = unbind_device;
	func.cloud_request_set_alias = set_alias;
	func.cloud_request_get_fw_download_progress = get_fw_download_progress;
	func.cloud_request_update_fw = update_fw;
	func.cloud_request_get_wan_info = get_wan_info;
	func.cloud_request_get_lan_info = get_lan_info;
	func.cloud_request_get_wifi_basic = get_wifi_basic;
	func.cloud_request_passthrough = passthrough;

	device_t* device = device_new(&func);
	device_connect(device, "127.0.0.1", 50443);
	…
	device_disconnect(device);
	device_destroy(device);

	return 0;
}

回到目录

Clone this wiki locally