域名:js ${YourProductKey}.iot-as-mqtt.${YourRegionId}.aliyuncs.com 。
其中,${YourProductKey}请替换为您的产品ProductKey;${YourRegionId}请参见地域和可用区,替换为您在物联网平台创建产品时选择的地域代码。
端口: 1883。
clientID需为全局唯一。如果不同的设备使用相同的clientID同时连接物联网平台,那么先连接的那个设备会被强制断开。
MQTT连接有两种方式。
认证后再连接:首先使用HTTPS连接到```js js iot-auth.cn-shanghai.aliyuncs.com:443
获取认证cert后,再使用MQTT连接到
```js
js/public.iot-as-mqtt.cn-shanghai.aliyuncs.com/1883。
认证连接必须使用TLS加密进行认证。 域名直连:连接域名:js ${productKey}.iot-as-mqtt.cn-shanghai.aliyuncs.com:1883 。
域名直连减少了HTTPS获取证书cert的过程。 资源受限的设备推荐使用域名直连。一些特殊增值服务,例如设备级别的引流,则推荐先HTTPS发送授权后再连接MQTT。在make.setting中设置js FEATURE_MQTT_DIRECT=y
, 然后执行js make reconfig 即
可设置为先认证后再MQTT连接。
在MQTT connect packet中设置MQTT的版本。目前SDK(V2.02)使用MQTT 3.1.1 。
可以修改SDK代码中js src\mqtt\mqtt_client.h IOTX_MC_MQTT_VERSION 的
值,来修改支持的版本。3:3.1版;4:3.1.1版。
认证返回400错误,表示鉴权认证失败。请检查设备证书信息ProductKey、DeviceName和DeviceSecret是否正确。
C语言SDK可以移植到任何能够支持C语言的系统上。如果是iOS系统建议寻找开源的Object-C实现。
mqtt-example程序发送一次消息后会自动退出,可以尝试以下任意一种方式实现长期在线。
js ./mqtt-example loop ,
设备会保持长期在线。while(1)
{
IOT_MQTT_Yield(pclient, 200);
HAL_SleepMs(100);
}
在IOT_MQTT_Construct里面可以设置keepalive_interval_ms的取值。物联网平台使用这个值来作为心跳间隔时间。keepalive_interval_ms的取值范围是60000~300000。
设备端会在keepalive_interval_ms时间间隔发送ping request,然后等待ping response。
如果设备端在keepalive_interval_ms时间内无法收到ping response,或是在进行send以及recv时发生错误,平台就认为此时网络断开,而需要进行重连。
重连机制是平台内部触发,无需使用者接入。重连时,会重新进行认证。如果认证成功就会开始再次进行MQTT connect。重连会一直持续直到再次连接成功。
云端会根据MQTT CONNECT packet里面keepalive的设置,等待ping request。如果在指定时间内没有收到ping request,则认为设备离线。
云端可以接受的最大时延是5秒。
支持。测试场景描述:开发板通过WiFi连接上路由器后,把网线拔掉,MQTT和CCP协议都会自动尝试和server重新建立连接。尝试时间间隔是1s、2s、4s、8s、…,最大间隔时间默认是60s,也就是说断网后超过60s时间仍未连接成功,之后会每隔60s尝试和server重连。您可以设置最大间隔时间。
需要等待ACK的packet都会存放起来,等待ACK。存放量有上限,当需要等待的packet太多到达上限时,就会触发js MQTT_PUSH_TO_LIST_ERROR(-42) error 。
出现错误可能是因为当前网络状态不好,或者是发送的频率过高。如果排除上述两个问题,当前的发送的频率是预期的,那么可以适当的调整IOTX_MC_REPUB_NUM_MAX、 IOTX_MC_SUB_REQUEST_NUM_MAX和IOTX_MC_SUB_NUM_MAX的大小。
如果业务允许,也可以把publish的QoS调整成0。
IOT_MQTT_Yield的作用是尝试接收数据。因此在需要接收数据时,例如subscribe 和 unsubscribe之后,publish QoS1 消息之后,或是希望收到publish 数据时,都需要主动调用该函数。
IOT_MQTT_Yield会尝试接收数据,直到timeout时间到后才会退出。
IOT_MQTT_Yield与HAL_SleepMs的区别 IOT_MQTT_Yield与HAL_SleepMs都是阻塞一段时间,但是IOT_MQTT_Yield实质是去读取数据,而HAL_SleepMs则是系统什么也不做,等待timeout。
需要循环调用IOT_MQTT_Yield ,函数内自动维持心跳和接收数据。
首先需要确定Topic的权限,是不是同时满足发布和订阅。如果是,调用一次IOT_MQTT_Yield,可以接收到多个packet。
如果使用的TCPIP协议栈,可以实现TCP主动通知上层有数据到达,可以改动实现事件触发的方式来触发IOT_MQTT_Yield。但是改动比较大,所以还请自行评估是否需要修改。
修改流程是:
调整utils_net.c里面socket的API,变成可以由TCP数据到达时回调的API。
当TCP主动通知上层有数据到达时,通知到MQTT服务器。让MQTT服务器内部执行IOT_MQTT_Yield,这样就可以不需要外部调用IOT_MQTT_Yield来读取数据。
如果TCP无法做到主动上报数据,但OS支持多线程,也可以在MQTT-example里面再起一个thread,在这个thread里面以下代码用于接收数据。收到数据时,触发主线程进行数据处理,而主线程大部分时间可以用于处理其他逻辑。
while(1) {
IOT_MQTT_Yiled(pclient, 200);
HAL_SleepMs(200);
}
如果使用的系统也不支持多线程,就只能把IOT_MQTT_Yield的timeout时间间隔减小,然后提高调用的频率,在每次调用的时间间隔内执行其他操作,从而做到尽量减少对其他操作的阻塞。
不支持。
在2倍request_timeout_ms时间内,系统未接收到SUBACK packet时,会触发订阅超时,并通过event_handle函数发送超时通知。
请在subscribe之后,立刻执行IOT_MQTT_Yield尝试读取SUBACK,请勿使用HAL_SleepMs。
请检查Topic的操作权限是否为订阅。
如果发布报错“no authorization”,请确认是否为发布权限。
MQTT的协议包受限于IOT_MQTT_Construct里参数的write_buf和read_buf的大小。
MQTT协议包大小不能超过256 KB。超过大小限制的消息会被丢弃。
物联网平台没有制定pub消息payload的具体字段有那些。您根据应用场景制定自己的协议,然后以JSON格式放到pub消息载体里面传给服务端。
MQTT设置的buffer过小,即mqtt_param的pread_buf和pwrite_buf申请过小造成的。可以根据实际需要修改OTA_MQTT_MSGLEN的大小。
OTA升级时,必须使用HTTPS进行固件下载。MQTT只接收版本更新指令,与MQTT的连接方式无关。阿里云不支持HTTP下载固件,因此如果设备没有SSL通信的能力,则不能使用OTA服务。
如果关闭MQTT over TLS则可以成功地订阅和发布信息;打开MQTT over TLS时,建连失败。首先确认mbedtls是否做了修改,这是用于传输层和应用层之间加密的功能,不能随意更改。mbedtls没有修改,则考虑系统时间是否正确,系统时间不对也会导致证书校验失败。
若使用TLS进行MQTT接入,需要下载根证书。
若使用物联网平台提供的demo进行开发,无需再下载根证书,demo中已自带证书。
在MQTT协议和CCP协议下,阿里云物联网平台支持的QoS Level都包括0和1。
版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。