首先得在华为lot平台注册完设备填写好profil模型,然后在产品里选插件开发,选脚本化开发
然后得明白华为平台编解码大致分四个块,上报数据(上行),数据回应(下行),命令下发(下行),命令响应(上行)。上行的数据需要按照各自项目进行解码,下行需要编码。
直接上代码
//上行消息类型
var MSG_TYPE_PROPERTIES_REPORT = 'properties_report'; //设备上报
var MSG_TYPE_COMMAND_RSP = 'command_response'; //设备返回命令响应
//下行消息类型
var MSG_TYPE_COMMANDS = 'commands'; //平台命令下发
var MSG_TYPE_PROPERTIES_REPORT_REPLY = 'properties_report_reply'; //设备属性上报的响应消息
//消息类型列表
var MSG_TYPE_LIST = {
0: MSG_TYPE_PROPERTIES_REPORT, //码流中0字节标识为设备属性上报
1: MSG_TYPE_PROPERTIES_REPORT_REPLY, //码流中1字节标识为设备属性上报的响应消息
2: MSG_TYPE_COMMANDS, //码流中2字节标识为平台命令下发
3: MSG_TYPE_COMMAND_RSP //码流中3字节标识为设备返回命令响应
};
//下面是解码部分,数据上报解码和命令相应解码,注意判断语句需要自行按照自己项目数据进行判断,仅供参考
function decode(payload, topic) {
var jsonObj = {};
var pdbytes = bytesToHexString([payload[7],payload[8]]);
if(pdbytes==3001)
{
var bytes = new Uint8Array([payload[86],payload[87]]);
var Abytes = new Uint8Array([payload[88],payload[89]]);// 字节数组,16进制表示为[0x12, 0x34]
var Bbytes = new Uint8Array([payload[90],payload[90]]);
var Cbytes = new Uint8Array([payload[92],payload[93]]);
var Dbytes = new Uint8Array([payload[66],payload[67]]);
var rsrq = bytesToSigned16BitInteger(bytes);
var snr = bytesToSigned16BitInteger(Abytes);// 结果为0x3412,即13312
var ecl = bytesToSigned16BitInteger(Bbytes);
var drycell = bytesToSigned16BitInteger(Dbytes);
//var celld = bytesToSigned16BitInteger(Cbytes);
var data = bytesToHexString(payload);
var celld = bytesToHexString([payload[91],payload[92],payload[93],payload[94],payload[95],payload[96]]);
jsonObj = {
"msg_type": "properties_report",
"services": [{
"service_id": "Report2",
"properties": {
//这里就是定义的profil模型,数据上传到平台
"data": data, "rsrp":rsrq,"sinr":snr,"ecl":ecl,"cellld":celld,"drycell":drycell
},
}]
};
//jsonObj = {"RSRP":rsrq,"SNR":snr};
return JSON.stringify(jsonObj);
}//下面是命令响应
else if(pdbytes2==08){var result_code = 0;var value = 151254;
jsonObj = {"msg_type":"command_response","result_code":result_code,"paras":{"value":value}}; return JSON.stringify(jsonObj);}
else{
var data1 = bytesToHexString(payload);
jsonObj = {
"msg_type": "properties_report",
"services": [{
"service_id": "Report2",
"properties": {
"data": data1
},
}]
};
//jsonObj = {"RSRP":rsrq,"SNR":snr};
return JSON.stringify(jsonObj);
}
}
//数组转16进制字符串
function bytesToHexString(byteArray) {
//var hexStringArray = bytesa.map(
// function(byte){
// return byte.toString(16);
// }
// );
//var byte=0x68;
// 将转换后的16进制字符串连接成一个字符串
var hexString = '';
for(var i=0; i<byteArray.length; i++)
{
var byte = new Uint8Array([byteArray[i]]);
var tmp = byte[0].toString(16);
if(tmp.length == 1)
{
tmp = "0" + tmp;
}
hexString+=tmp;
}
return hexString.toUpperCase();
}
function Bytes2Str(byteArray)
{
var str = "";
for(var i=0; i<byteArray.length; i++)
{
var tmp = byteArray[i].toString(16);
if(tmp.length == 1)
{
tmp = "0" + tmp;
}
str += tmp;
}
return str;
}
function bytesToSigned16BitInteger(byteArray) {
// 确保字节数组长度为1个字节(2个字节代表一个16位整数)
if (byteArray.length !== 2) {
throw new Error('The byte array should contain exactly 2 bytes.');
}
// 创建一个缓冲数组并设置为大端模式
var buffer = new ArrayBuffer(2);
var view = new Uint8Array(buffer);
view[0] = byteArray[0]; // 设置高位字节
view[1] = byteArray[1]; // 设置低位字节
// 创建DataView并读取16位有符号整数
var dataView = new DataView(buffer);
var int16 = dataView.getInt16(0, false); // 第二个参数表示使用大端字节序
return int16;
}
/*
示例数据:命令下发时,通过javascript的encode方法将平台JSON格式的数据,编码为二进制码流
传入参数 ->
{"msg_type":"commands","request_id":1,"command_name":"SET_ALARM","service_id":"smokerdector","paras":{"value":1}}
输出结果 ->
[0x02, 0x00, 0x00, 0x00, 0x01]
示例数据:设备上报属性时返回响应消息,通过javascript的encode方法将平台JSON格式的数据,编码为二进制码流
传入参数 ->
{"msg_type":"properties_report_reply","request":"000050005a","result_code":0}
输出结果 ->
[0x01, 0x00]
*/
function encode(json) {
//下面为编码
//转换为JSON对象
var jsonObj = JSON.parse(json);
//获取消息类型
var msgType = jsonObj.msg_type;
var payload = [];
//将JSON格式数据转换为二进制数据
if (msgType == MSG_TYPE_COMMANDS) { // 命令下发
//payload = payload.concat(buffer_int16(2)); // 标识命令下发
//payload = payload.concat(buffer_int16(jsonObj.request_id)); // 命令ID
//if (jsonObj.command_name == 'SET_DEVICE_LEVEL') {
// payload = payload.concat(buffer_int16(0)); // 标识命令名称
//}
//payload=[0x01,0x02,0x04,0x0A];
var paras_value =jsonObj.paras.value;
// payload = payload.concat(buffer_uint8(parseInt(paras_value.substring(0,2),16)));
//payload=buffer_uint8(6);
for(i=0;i<paras_value.length;i=i+2){
payload = payload.concat(buffer_uint8(parseInt(paras_value.substr(i,2),16)));
}
//payload = payload.concat(hexStringToUnsignedInteger(paras_value)); // 设置命令属性值
} else if (msgType == MSG_TYPE_PROPERTIES_REPORT_REPLY) { // 设备属性上报的响应消息
//payload = payload.concat(buffer_int16(1)); // 标识属性上报的响应消息
//if (0 == jsonObj.result_code) {
// payload = payload.concat(buffer_int16(0)); // 标识属性上报消息处理成功
//}
//var paras_value1 ="6800123456";
//for(i=0;i<paras_value1.length;i=i+2){
// payload = payload.concat(buffer_uint8(parseInt(paras_value1.substr(i,2),16)));
// }
}
// payload=[0x01,0x02,0x68,0x04,0x0A];
//返回编码后的二进制数据
return payload;
}
function hexStringToUnsignedInteger(hexString) {
// 将16进制字符串转换为有符号整数
var signedInteger = parseInt(hexString, 16);
// 将有符号整数转换为无符号整数
var unsignedInteger = ~0 >>> 0;
unsignedInteger |= signedInteger;
return unsignedInteger;
}
function hexStringToUint16(hexString) {
// 使用parseInt转换16进制字符串到10进制数字
var uint16 = parseInt(hexString, 16);
// 对结果进行掩码操作,保留16位无符号整数
//uint16 = uint16 & 0xFFFF;
return uint16;
}
//将8位无符号整形转换为byte数组
function buffer_uint8(value) {
var uint8Array = new Uint8Array(1);
var dataView = new DataView(uint8Array.buffer);
dataView.setUint8(0, value);
return [].slice.call(uint8Array);
}
//将16位无符号整形转换为byte数组
function buffer_int16(value) {
var uint8Array = new Uint8Array(2);
var dataView = new DataView(uint8Array.buffer);
dataView.setInt16(0, value);
return [].slice.call(uint8Array);
}
//将32位无符号整形转换为byte数组
function buffer_int32(value) {
var uint8Array = new Uint8Array(4);
var dataView = new DataView(uint8Array.buffer);
dataView.setInt32(0, value);
return [].slice.call(uint8Array);
}