1.SDK下载
JT704SDK(JT704SDK_V2.rar) 下载地址
JT704SDK测试工具(JT704SDK_Test.rar) 下载地址
如果需要测试工具及SDK开发源码,请与商务申请
2.集成开发说明
2.1.集成开发语言及框架说明
JT704SDK(Jt704DataParser.dll)及测试工具(Test.exe)是基于C#语言,.NET Framework 4.6.1目标框架开发的。该SDK的集成开发环境也是需要依赖于C#语言以及.NET Framework 4.6.1目标框架。
2.2.集成说明
(1)将Jt704DataParser.dll引入到自己的网关程序中,引入方法如下:
鼠标右键项目下的”引用”,选择”添加引用(R)…”
选择下图中”浏览(B)…”,找到你解压JT704SDK20210806.rar后的文件夹,选中Jt704DataParser.dll与对应的Json字符串序列化/反序列化包Newtonsoft.Json.dll即可完成对SDK的引用
(2)调用Jt704DataParser.dll中的解析方法receiveData
receiveData()是一个重载方法,你可以传入16进制字符串或者byte[],一般我们网关程序接收到的设备数据是以二进制流进行传输的,所以我们这里建议使用此重载方法receiveData(byte[] bytes);
当然如果你想通过16进制字符串进行测试,也可以使用receiveData(string strData);
strData:就是我们接收到的设备数据转成16进制后的字符串
2.3.核心代码
Jt704DataParser.dll
(1)解析类DataParser.cs
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace Jt704DataParser
{
public class DataParser
{
private static byte[] endbytes = null;// 上一次未处理的剩余字节
/// <summary>
/// 解析16进制原始数据
/// </summary>
/// <param name="strData"></param>
/// <returns></returns>
public static string receiveData(string strData)
{
byte[] bytes = Common.HexStringToBytes(strData);
return receiveData(bytes);
}
/// <summary>
/// 解析2进制原始数据
/// </summary>
/// <param name="bytes"></param>
/// <returns></returns>
public static string receiveData(byte[] bytes)
{
byte[] newBytes = null;
if (endbytes != null && endbytes.Length > 0)
{
newBytes = new byte[endbytes.Length + bytes.Length];
bytes = Common.CombineBytes(endbytes, bytes);
}
else
{
newBytes = new byte[bytes.Length];
newBytes = bytes;
}
int i = 0;//初始化byte[]下标
byte[] parserBytes = null;//去除正确包头之前的数据后的数据
foreach (var item in newBytes)
{
if (item == 0x7E)
{
parserBytes = new byte[newBytes.Length - i];
parserBytes = newBytes.Skip(i).Take(newBytes.Length - i).ToArray();
return parserLocation(parserBytes);
}
else if (item == '(')
{
parserBytes = new byte[newBytes.Length - i];
parserBytes = newBytes.Skip(i).Take(newBytes.Length - i).ToArray();
return parserCommand(parserBytes);
}
i++;
}
return null;
}
private static string parserLocation(byte[] bytes) {
byte[] frame = PacketUtil.decodePacket(bytes);
if (frame == null) {
endbytes = bytes;
return null;
}
//定义定位数据实体类
Result model = new Result();
//消息ID
int msgId = Common.SwapUInt16(BitConverter.ToUInt16(frame, 1));
//消息体属性
int msgBodyAttr = Common.SwapUInt16(BitConverter.ToUInt16(frame, 3));
//消息体长度
int msgBodyLen = msgBodyAttr & 0x03FF;
byte[] terminalNumArr = bytes.Skip(5).Take(6).ToArray();
model.DeviceID = Common.ByteToHexStr(terminalNumArr).TrimStart('0');
//消息流水号
int msgFlowId = Common.SwapUInt16(BitConverter.ToUInt16(frame, 11));
//消息体
byte[] msgBodyArr = bytes.Skip(13).Take(msgBodyLen).ToArray();
if (msgId == 0x0200)
{
//解析消息体
LocationData locationData = PacketUtil.parseLocationBody(msgBodyArr);
locationData.Index=msgFlowId;
locationData.DataLength=msgBodyLen;
model.MsgType="Location";
model.DataBody=locationData;
string replyMsg = PacketUtil.replyBinaryMessage(terminalNumArr, msgFlowId);
model.ReplyMsg=replyMsg;
}
else
{
model.MsgType = "heartbeat";
}
return JsonConvert.SerializeObject(model);
}
/// <summary>
/// 解析指令数据
/// </summary>
/// <param name="bytes"></param>
/// <returns></returns>
private static string parserCommand(byte[] bytes)
{
Result result = new Result();
byte[] newBytes = null;
int tailIndex = Common.BytesIndexOf(bytes, 0x29) + 1;
if (tailIndex > 0)
{
if (bytes.Length > tailIndex)
{
endbytes = bytes.Skip(tailIndex).Take(bytes.Length - tailIndex).ToArray();
}
newBytes = bytes.Skip(0).Take(tailIndex).ToArray();
}
else
{
endbytes = new byte[bytes.Length];
endbytes = bytes;
}
if (newBytes != null && newBytes.Length > 0)
{
//转换成()带括号的数据
string msgAscii = Common.ByteToASCII(newBytes);
//按逗号拆分字符串
char[] p = new char[] { ',' };
//返回的数组中,包含空字符串
string[] msgArrays = msgAscii.Replace("(", "").Replace(")", "").Split(p, StringSplitOptions.None);
result.DeviceID = msgArrays[0];
string msgType = string.Empty;
if (msgArrays.Length > 5)
{
msgType = msgArrays[3] + msgArrays[4];
}
else
{
return null;
}
result.MsgType = msgType;
result.DataBody = msgAscii;
string replyMsg = string.Empty;
if (msgType.Equals("BASE2") && msgArrays[5].ToUpper().Equals("TIME"))
{
replyMsg = PacketUtil.replyBASE2Message(msgArrays);
}
result.ReplyMsg = replyMsg;
return JsonConvert.SerializeObject(result);
}
else
{
return null;
}
}
}
}
(2)公共方法类:Common.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Text.RegularExpressions;
using System.Threading.Tasks;
namespace Jt704DataParser
{
public class Common
{
/// <summary>
/// 16进制格式字符串转字节数组
/// </summary>
/// <param name="hexString"></param>
/// <returns></returns>
public static byte[] HexStringToBytes(string hexString)
{
hexString = Regex.Replace(hexString, @".{2}", "$0 ");
//以 ' ' 分割字符串,并去掉空字符
string[] chars = hexString.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries);
byte[] returnBytes = new byte[chars.Length];
//逐个字符变为16进制字节数据
for (int i = 0; i < chars.Length; i++)
{
returnBytes[i] = Convert.ToByte(chars[i], 16);
}
return returnBytes;
}
/// <summary>
/// 合并数组
/// </summary>
/// <param name="bytes1"></param>
/// <param name="bytes2"></param>
/// <returns></returns>
public static byte[] CombineBytes(byte[] bytes1, byte[] bytes2)
{
List<byte> tmp = new List<byte>(bytes1.Length + bytes2.Length);
tmp.AddRange(bytes1);
tmp.AddRange(bytes2);
byte[] merged = tmp.ToArray();
return merged;
}
/// <summary>
/// 报告指定的 System.Byte[] 在此实例中的第一个匹配项的索引。
/// </summary>
/// <param name="srcBytes">被执行查找的 System.Byte[]。</param>
/// <param name="searchBytes">要查找的 System.Byte[]。</param>
/// <returns>如果找到该字节数组,则为 searchBytes 的索引位置;如果未找到该字节数组,则为 -1。如果 searchBytes 为 null 或者长度为0,则返回值为 -1。</returns>
public static int BytesIndexOf(byte[] srcBytes, byte searchBytes)
{
if (srcBytes == null) { return -1; }
if (srcBytes.Length == 0) { return -1; }
for (int i = 0; i < srcBytes.Length; i++)
{
if (srcBytes[i] == searchBytes)
{
return i;
}
}
return -1;
}
/// <summary>
/// 16进制字符串转ASCII
/// </summary>
/// <param name="Data"></param>
/// <param name="istrans"></param>
/// <returns></returns>
public static string HexStrToAsciiString(string Data, bool istrans)
{
if (istrans)
{
Data = Regex.Replace(Data, @"(?is)(?<=^([0-9a-f]{2})+)(?!$)", " ");
Data = Data.Replace("3D 00", "3D ").Replace("3D 11", "2C ").Replace("3D 14", "28 ").Replace("3D 15", "29 ").Replace(" ", "");
}
int count = Data.Length / 2;
string strContent = "";
char[] num = new char[count];
for (int i = 0; i < count; i++)
{
string str = Data.Substring(i * 2, 2);
byte by = Convert.ToByte(Convert.ToInt32(str, 16));
num[i] = Convert.ToChar(by);
strContent += num[i].ToString();
}
return strContent;
}
/// <summary>
/// 二进制转ASCII
/// </summary>
/// <param name="bt"></param>
/// <returns></returns>
public static string ByteToASCII(byte[] bt)
{
string lin = "";
for (int i = 0; i < bt.Length; i++)
{
lin = lin + bt[i] + " ";
}
string[] ss = lin.Trim().Split(new char[] { ' ' });
char[] c = new char[ss.Length];
int a;
for (int i = 0; i < c.Length; i++)
{
a = Convert.ToInt32(ss[i]);
c[i] = Convert.ToChar(a);
}
string b = new string(c);
return b;
}
/// <summary>
/// 时间格式转换
/// </summary>
/// <param name="bytes"></param>
/// <returns></returns>
public static DateTime GetDataTime(byte[] bytes)
{
return DateTime.ParseExact(ByteToHexStr(bytes), "yyMMddHHmmss", System.Globalization.CultureInfo.CurrentCulture);
}
public static DateTime GetDataTime(string strdate)
{
return DateTime.ParseExact(strdate, "yyMMddHHmmss", System.Globalization.CultureInfo.CurrentCulture);
}
/// <summary>
/// 获取二进制第index位的值
/// </summary>
/// <param name="number"></param>
/// <param name="index"></param>
/// <returns></returns>
public static int getBitValue(long number, int index)
{
return (number & (1 << index)) > 0 ? 1 : 0;
}
/// <summary>
/// 字节数组转16进制字符串
/// </summary>
/// <param name="byteDatas"></param>
/// <returns></returns>
public static string ByteToHexStr(byte[] byteDatas)
{
StringBuilder builder = new StringBuilder();
for (int i = 0; i < byteDatas.Length; i++)
{
builder.Append(string.Format("{0:X2}", byteDatas[i]));
}
return builder.ToString().Trim();
}
public static ushort SwapUInt16(ushort v)
{
return (ushort)(((v & 0xff) << 8) | ((v >> 8) & 0xff));
}
public static uint SwapUInt32(uint v)
{
return (uint)(((SwapUInt16((ushort)v) & 0xffff) << 0x10) |
(SwapUInt16((ushort)(v >> 0x10)) & 0xffff));
}
/// <summary>
/// Short转Bytes
/// </summary>
/// <param name="number"></param>
/// <returns></returns>
public static byte[] ShortToBytes(short number)
{
byte byte2 = (byte)(number >> 8);
byte byte1 = (byte)(number & 255);
byte[] bytes = new byte[2];
bytes[0] = byte1;
bytes[1] = byte2;
return bytes.Reverse().ToArray();
}
/// <summary>
/// 随机short
/// </summary>
/// <returns></returns>
public static short RandomNumber(int min, int max)
{
Random rd = new Random();
return (short)rd.Next(min, max);
}
/// <summary>
/// 计算校验码
/// </summary>
/// <param name="bytes"></param>
/// <returns></returns>
public static byte xor(List<byte> bytes)
{
int checksum = 0;
foreach (byte b in bytes) {
checksum ^= b;
}
return (byte)(checksum &0xff);
}
/// <summary>
/// 转义
/// </summary>
/// <param name="inBytes"></param>
/// <returns></returns>
public static byte[] escape(List<byte> inBytes)
{
List<byte> outBytes = new List<byte>();
foreach (byte b in inBytes) {
if (b == 0x7E) {
outBytes.AddRange(HexStringToBytes("7D02"));
}else if (b == 0x7D) {
outBytes.AddRange(HexStringToBytes("7D01"));
} else {
outBytes.Add(b);
}
}
return outBytes.ToArray();
}
}
}
(3)解包工具类PacketUtil.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace Jt704DataParser
{
public class PacketUtil
{
public static byte[] decodePacket(byte[] bytes) {
//查找消息尾
byte[] msgBodyNoHeader = bytes.Skip(1).Take(bytes.Length - 1).ToArray();
int tailIndex = Common.BytesIndexOf(msgBodyNoHeader, 0x7E);
if (tailIndex <= 0) {
return null;
}
return unescape(bytes, tailIndex).ToArray();
}
/// <summary>
/// 反转义
/// </summary>
/// <param name="bytes"></param>
/// <param name="bodyLen"></param>
/// <returns></returns>
public static List<byte> unescape(byte[] bytes, int bodyLen)
{
int i = 0;
List<byte> frame = new List<byte>();
while (i < bodyLen)
{
byte b = bytes[i];
if (b == 0x7D)
{
byte nextByte = bytes[i+1];
if (nextByte == 0x01)
{
frame.Add(0x7D);
}
else if (nextByte == 0x02)
{
frame.Add(0x7E);
}
else
{
//异常数据
frame.Add(b);
frame.Add(nextByte);
}
i += 2;
}
else
{
frame.Add(b);
i++;
}
}
return frame;
}
/// <summary>
/// 解析定位消息体
/// </summary>
/// <param name="msgBodyBuf"></param>
/// <returns></returns>
public static LocationData parseLocationBody(byte[] msgBodyBuf)
{
//报警标志
long alarmFlag = Common.SwapUInt32(BitConverter.ToUInt32(msgBodyBuf, 0));
//状态
long status = Common.SwapUInt32(BitConverter.ToUInt32(msgBodyBuf, 4));
//纬度
double lat = Common.SwapUInt32(BitConverter.ToUInt32(msgBodyBuf, 8))* 0.000001;
//经度
double lon = Common.SwapUInt32(BitConverter.ToUInt32(msgBodyBuf, 12)) * 0.000001;
//海拔高度,单位为米
int altitude = Common.SwapUInt16(BitConverter.ToUInt16(msgBodyBuf, 16));
//速度
double speed = Common.SwapUInt16(BitConverter.ToUInt16(msgBodyBuf, 18))*0.1;
//方向
int direction = Common.SwapUInt16(BitConverter.ToUInt16(msgBodyBuf, 20));
//定位时间
DateTime gpsZonedDateTime = Common.GetDataTime(msgBodyBuf.Skip(22).Take(6).ToArray());
//根据状态位的值判断是否南纬和西经
if (Common.getBitValue(status, 2) == 1)
{
lat = -lat;
}
if (Common.getBitValue(status, 3) == 1)
{
lon = -lon;
}
//定位状态
int locationType = Common.getBitValue(status, 18);
if (locationType == 0)
{
locationType = Common.getBitValue(status, 1);
}
if (locationType == 0)
{
locationType = Common.getBitValue(status, 6) > 0 ? 2 : 0;
}
//报警状态
int alarm = -1;
if (Common.getBitValue(alarmFlag, 16) == 1)
{
alarm = (int)AlarmTypeEnum.ALARM_1;
}
//后盖状态
int backCover = Common.getBitValue(status, 7);
//唤醒源
long awaken = (status >> 24) & 0x0f;
LocationData locationData = new LocationData();
locationData.GpsTime = gpsZonedDateTime;
locationData.Latitude=lat;
locationData.Longitude=lon;
locationData.LocationType=locationType;
locationData.Speed=(int)speed;
locationData.Direction=direction;
locationData.Alarm=alarm;
locationData.BackCover=backCover;
locationData.Awaken=(int)awaken;
//处理附加信息
if (msgBodyBuf.Length > 28)
{
byte[] extraBytes = msgBodyBuf.Skip(28).Take(msgBodyBuf.Length - 28).ToArray();
parseExtraInfo(extraBytes, locationData);
}
return locationData;
}
/// <summary>
/// 解析附加信息
/// </summary>
/// <param name="msgBody"></param>
/// <param name="location"></param>
private static void parseExtraInfo(byte[] msgBody, LocationData location)
{
byte[] extraInfoBuf = null;
while (msgBody.Length > 1)
{
int extraInfoId = msgBody[0];
int extraInfoLen = msgBody[1];
if (msgBody.Length-2 < extraInfoLen)
{
break;
}
extraInfoBuf = msgBody.Skip(2).Take(extraInfoLen).ToArray();
msgBody= msgBody.Skip(2+ extraInfoLen).Take(msgBody.Length-(2 + extraInfoLen)).ToArray();
switch (extraInfoId)
{
case 0x0F:
//解析温度数据
double temperature = -1000.0;
temperature = parseTemperature(Common.SwapUInt16(BitConverter.ToUInt16(extraInfoBuf, 0)));
location.Temperature=(int)temperature;
break;
//无线通信网络信号强度
case 0x30:
int fCellSignal = extraInfoBuf[0];
location.GSMSignal = fCellSignal;
break;
//卫星数
case 0x31:
int fGPSSignal = extraInfoBuf[0];
location.GpsSignal = fGPSSignal;
break;
//电池电量百分比
case 0xD4:
int fBattery = extraInfoBuf[0];
location.Battery=fBattery;
break;
//电池电压
case 0xD5:
int fVoltage = Common.SwapUInt16(BitConverter.ToUInt16(extraInfoBuf, 0));
location.Voltage=fVoltage * 0.01;
break;
case 0xFD:
//小区码信息
int mcc = Common.SwapUInt16(BitConverter.ToUInt16(extraInfoBuf, 0));
location.MCC=mcc;
int mnc = extraInfoBuf[2];
location.MNC=mnc;
long cellId = Common.SwapUInt32(BitConverter.ToUInt32(extraInfoBuf, 3));
location.CELLID= cellId;
int lac = Common.SwapUInt16(BitConverter.ToUInt16(extraInfoBuf, 7));
location.LAC=lac;
break;
case 0xFE:
long mileage = Common.SwapUInt32(BitConverter.ToUInt32(extraInfoBuf, 0));
location.Mileage=mileage;
break;
default:
break;
}
}
}
/// <summary>
/// 温度解析
/// </summary>
/// <param name="temperatureInt"></param>
/// <returns></returns>
private static double parseTemperature(int temperatureInt)
{
if (temperatureInt == 0xFFFF)
{
return -1000;
}
double temperature = ((short)(temperatureInt << 4) >> 4) * 0.1;
if ((temperatureInt >> 12) > 0)
{
temperature = -temperature;
}
return temperature;
}
/// <summary>
/// 回复内容
/// </summary>
/// <param name="terminalNumArr"></param>
/// <param name="msgFlowId"></param>
/// <returns></returns>
public static string replyBinaryMessage(byte[] terminalNumArr, int msgFlowId) {
List<byte> byteList = new List<byte>();
byteList.AddRange(Common.HexStringToBytes("8001"));
byteList.AddRange(Common.HexStringToBytes("0005"));
byteList.AddRange(terminalNumArr);
byteList.AddRange(Common.ShortToBytes(Common.RandomNumber(0, 65534)));
byteList.AddRange(Common.ShortToBytes((short)msgFlowId));
byteList.AddRange(Common.HexStringToBytes("0200"));
byteList.Add(0x00);
byteList.Add(Common.xor(byteList));
byte[] bytes = Common.escape(byteList);
List<byte> replyList = new List<byte>();
replyList.Add(0x7E);
replyList.AddRange(bytes);
replyList.Add(0x7E);
return Common.ByteToHexStr(replyList.ToArray());
}
/// <summary>
/// 授时
/// </summary>
/// <param name="itemList"></param>
/// <returns></returns>
public static string replyBASE2Message(string[] itemList)
{
try
{
string strBase2Reply = string.Format("({0},{1},{2},{3},{4},{5})", itemList[0], itemList[1]
, itemList[2], itemList[3], itemList[4], DateTime.UtcNow.ToString("yyyyMMddHHmmss"));
return strBase2Reply;
}
catch (Exception e)
{
return "";
}
}
}
}
2.4.返回消息及说明
(1)心跳数据
原始数据:
7E000200007501804283100001267E
返回消息:
{"DeviceID":"750180428310","MsgType":"heartbeat","DataBody":null,"ReplyMsg":null}
返回消息描述
{"DeviceID":设备ID,"MsgType":消息类型(heartbeat:心跳)}
(2)定位数据
原始数据:
7E0200003B7501809250040102000000000004000201588F0F06CA3C52002700000000181106123212D4015AD502015C30011431010CFD0901CC00000010922866EF014A0F0201406E7E
返回消息:
{
"DeviceID": "750180925004",
"DataBody": {
"Speed": 0,
"GpsTime": "2018-11-06T12:32:12Z",
"Temperature": 32,
"MNC": 0,
"Mileage": 0,
"BackCover": 0,
"Index": 258,
"Latitude": 22.581007,
"Awaken": 0,
"MCC": 460,
"Direction": 0,
"Longitude": 113.91701,
"LAC": 10342,
"Alarm": -1,
"Battery": 90,
"GpsSignal": 12,
"Voltage": 3.48,
"DataLength": 59,
"CELLID": 4242,
"LocationType": 1,
"GSMSignal": 20
},
"ReplyMsg": "7e800100057501809250040dbd0102020000077e",
"MsgType": "Location"
}
返回消息描述
{
"DeviceID": 终端号,
"DataBody": {
"Speed": 速度,
"GpsTime": 定位时间(UTC),
"Temperature": 温度,
"MCC": 小区码信息MCC,
"MNC": 小区码信息MNC,
"LAC": 小区码信息LAC,
"CELLID": 小区码信息CI,
"Mileage": 里程值(km),
"BackCover": 后盖状态(1:开;0:关),
"Index": 流水号,
"Latitude": 纬度(WGS84),
"Longitude": 经度(WGS84),
"Awaken": 唤醒源(0:RTC上报 3:开盖上报 4:关盖上报),
"Direction": 方向(0~360,0表示正北),
"Alarm": 报警类型(1:主机拆卸报警;-1:无报警),
"Battery": 电量值(0~100%),
"GpsSignal": 卫星颗数,
"Voltage": 电压值(单位:V),
"DataLength": 数据长度,
"LocationType": 定位类型(1:GPS定位;0:不定位),
"GSMSignal": GSM信号值
},
"ReplyMsg": 需要回复终端的指令,
"MsgType": 数据类型(Location:定位数据)
}
(3)指令数据解析
原始数据:
283730303136303831383030302c312c3030312c424153452c312c312c32303135303431385f473330302c302c4265694875616e2c3131333742303353494d3930304d36345f53545f4d4d532c38393836303034323139313133303237323534392c3031323230373030353632303933322c3436302c30302c343234332c3638373729
返回消息:
{
"DeviceID": "700160818000",
"DataBody": "(700160818000,1,001,BASE,1,1,20150418_G300,0,BeiHuan,1137B03SIM900M64_ST_MMS,89860042191130272549,012207005620932,460,00,4243,6877)",
"ReplyMsg": "",
"MsgType": "BASE1"
}
返回消息描述
{
"DeviceID": 设备ID,
"DataBody": 消息体内容,
"ReplyMsg": 回复设备的消息(为空则表示不需要回复),
"MsgType": 指令类型
}
3.指令消息
3.1.查询终端基本信息
消息体内容(DataBody):
(700160818000,1,001,BASE,1,1,20150418_G300,0,BeiHuan,1137B03SIM900M64_ST_MMS,89860042191130272549,012207005620932,460,00,4243,6877)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | BASE,1 | 指令类型(BASE1) |
3 | 20150418_G300 | 当前设备的版本号。 |
4 | 0,BeiHuan | 前面的0表示英文,1表示其它语言的Unicode码,ASCII码表示,如:报警62A5 8B66上传是8个字节。此处为英语,名称为BeiHuan |
5 | 1137B03SIM900M64_ST_MMS | GSM模块版本。 |
6 | 89860042191130272549 | SIM卡的ICCID。 |
7 | 012207005620932 | GSM模块的IMEI号 |
8 | 460,00,4243,6877 | 网络信息:460 移动国家代码,即MCC信息,此处表示中国;00电信运营商网络号码,MNC信息(中国移动为00,中国联通为01);4243 基站编号CELL ID信息;6877 位置区域码LAC信息。CELL ID与LAC为十六进制,即4243转为十进制为16963。 |
3.2.授时(同步GMT时间)
消息体内容(DataBody):
(700160818000,1,001,BASE,2,20111018123820)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | BASE,2 | 指令类型(BASE2) |
3 | 20111018123820 | 设置的时间(yyyyMMddHHmmss) |
3.3.远程重启终端
消息体内容(DataBody):
(700160818000,1,001,BASE,3)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | BASE,3 | 指令类型(BASE3) |
3.4.恢复出厂设置
消息体内容(DataBody):
(700160818000,1,001,BASE,4)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | BASE,4 | 指令类型(BASE4) |
3.5.查询/设置上传间隔和休眠定时唤醒间隔
消息体内容(DataBody):
(700160818000,1,001,BASE,6,60,30)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | BASE,6 | 指令类型(BASE6) |
3 | 60 | 上传间隔,以秒为单位,保留字段,暂无意义。 |
4 | 30 | 设备正常工作间隔,单位分钟,默认1440分钟,取值范围(5~1440)。 |
3.6.设置/查询设备本地时差
消息体内容(DataBody):
(2310915002,1,001,BASE,8, 480)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | BASE,8 | 指令类型(BASE8) |
3 | 480 | 时差值,此处单位为分钟 |
3.7.查询/设置主从IP地址与端口号、APN及用户名与密码等参数
消息体内容(DataBody):
(700160818000,1,001,BASE,10,211.154.112.98,1088,211.154.112.98,1088,CMNET,abc,123456)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | BASE,10 | 指令类型(BASE10) |
3 | 211.154.112.98 | 主IP(域名) |
4 | 1088 | 主端口 |
5 | 211.154.112.98 | 从IP(域名) |
6 | 1088 | 从端口 |
7 | CMNET | APN名称 |
8 | abc | 用户名 |
9 | 123456 | 密码 |
3.8.查询/设置/删除设备工作闹钟
消息体内容(DataBody):
(700160818000,1,001,BASE,32,1,480)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | BASE,32 | 指令类型(BASE32) |
3 | 1 | 1则表明当前有效闹钟个数,闹钟时间点最多4个;返回0表示当前没有有效闹钟 |
4 | 480 | 设置一个设备闹钟的时间,以分钟为单位(范围为:0~1439) |
3.9.设置/调试选项
消息体内容(DataBody):
(2310915002,1,001,DEBUG,2,2,1)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 2310915002 | 设备ID |
2 | DEBUG,2 | 指令类型(DEBUG2) |
3 | 2 | 2: 没意义,固定字段 |
4 | 1 | 1: 表示调试GPS模块原始输出信息 2表示调试GPRS原始输出AT指令信息 |
3.10.设置设备进入休眠的时间
消息体内容(DataBody):
(700160818000,1,001,DEBUG,15,10)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 2310915002 | 设备ID |
2 | DEBUG,15 | 指令类型(DEBUG15) |
3 | 10 | 10: 表示设备10秒钟后进入休眠 |
3.11.查询设备还可以存储多少条数据
消息体内容(DataBody):
(700160818000,1,001,DEBUG,19,1000)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | DEBUG,19 | 指令类型(DEBUG19) |
3 | 1000 | 1000表示设备可以存储1000条数据 |
3.12.查询/设置/启用基站授时
消息体内容(DataBody):
(700160818000,1,001,DEBUG,26,1)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | DEBUG,26 | 指令类型(DEBUG26) |
3 | 1 | 返回1则表明启用基站授时,0表示关闭基站授时。 |
3.13.查询卡信息
消息体内容(DataBody):
(700160818000,1,001,DEBUG,27,123456789,888888888)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | DEBUG,27 | 指令类型(DEBUG27) |
3 | 123456789 | 123456789表示ICCID |
4 | 888888888 | 888888888表示IMSI |
3.14.通知设备MCU升级
消息体内容(DataBody):
(700160818000,1,001,OTA,1,1,20120102)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | OTA,1 | 指令类型(OTA1) |
3 | 1 | 1:表示同意升级,只有当设备的当前版本号低于要升级的版本号的时候才返回1.若设备返回0表示拒绝升级,即设备当前的Firmware版本和升级的Firmware版本相同或者更高。服务器只有在收到同意升级以后才发送第一个Firmware数据包. |
4 | 20120102 | 当前设备的Firmware版本号. |
3.15.发送Firmware数据包
消息体内容(DataBody):
(700160818000,1,001,OTA,2,0,200,100)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | OTA,2 | 指令类型(OTA2) |
3 | 0 | 1表示保存成功,0表示保存失败,如果失败重发. |
4 | 200 | 接收到的Firmware数据包序号. |
5 | 100 | 下一条需要发送的数据包序号. |
3.16.取消Firmware升级
消息体内容(DataBody):
(700160818000,1,001,OTA,3,1,20120222)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | OTA,3 | 指令类型(OTA3) |
3 | 1 | 1表示取消成功,0表示取消失败。如果该指令的版本号和正在升级的固件版本号不符的话就可能取消失败. |
4 | 20120222 | 设备正在升级的版本号 |
3.17.完成Firmware传输
消息体内容(DataBody):
(700160818000,1,001,OTA,4,1)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | OTA,4 | 指令类型(OTA4) |
3 | 1 | 该参数可以为1或者为0,1表示接受该指令,并根据指令执行。0表示:接受的数据不完全,拒绝升级. |
3.18.查询发送下条Firmware数据包序号
消息体内容(DataBody):
(700160818000,1,001,OTA,5,1,200)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | OTA,5 | 指令类型(OTA5) |
3 | 1 | 1:代表目前正在接收的固件和查询的相同,0表示目前接收的固件和查询的不同. |
4 | 200 | 如果查询的固件版本号比设备的版本号新的话,该参数表示下一条需要发送的序号。如果查询的版本号和正在升级的版本号不同的话,则该参数为1.即代表需要重新下载现在查询的固件. |
3.19.查询当前stm32固件的版本号
消息体内容(DataBody):
(700160818000,1,001,OTA,6,JT704_V103R001)
消息体内容描述:
序号 | 示例 | 说明 |
---|---|---|
1 | 700160818000 | 设备ID |
2 | OTA,6 | 指令类型(OTA6) |
3 | JT704_V103R001 | 固件版本号 |