概述
设备自身 CPU 温度、电源输入电压、内存使用率等,以及接入到设备的传感器如温度传感器、光敏传感器等,这些硬件的数据输出即是 属性
。
设备将这些硬件的数据上传到阿里云物联网平台,实时显示这些设备的状态和实测数据,这个过程是 上传设备属性
。
1)定义物模型
在阿里云物联网控制台,点击 产品 -> 功能定义 -> 添加自定义功能
填入一下内容:
再定义一个属性:
功能类型:属性
功能名称: 格力空调温度
标识符: gree_temperature
数据类型: float (单精度浮点型)
取值范围:0-35
步长: 0.1
单位: 摄氏度 / °C
读写类型:读写
注意的是,表示符是区分大小写的,相当于 C# 中的变量,笔者这里建议统一使用小写,具体原因后面说明。
注意:读写类型,一个只读、一个读写。
2)编写模型
前面说过, Alink json 是阿里云定义具有一定格式的 Json ,
因此这些属性数据是以 Json 形式上传。在 C# 中,可以通过 类 快速生成 Json 。
参数 | 类型 | 说明 |
---|---|---|
id | string | 消息ID号,在这个设备的生涯中,ID应当是唯一的。可以使用时间戳或guid |
version | string | 协议版本号,目前协议版本号为1.0。固定 "1.0" 即可 |
params | Object | 属性数据,里面包含多个属性对象,每个属性对象包含上报时间(time)和上报的值(value)。 |
time | long | 属性上报时间。 |
value | object | 上报的属性值。 |
method | string | 固定取值 thing.event.property.post |
那么,我们要编写一个类,存储信息,然后转为 Alink json 上传到阿里云物联网服务器。在编写这个模型前,预览要生成的 Alink json :
{
"id": "123456789",
"version": "1.0",
"params": {
"cpu_temperature": {
"value": 58.6,
"time": 1524448722000
},
"gree_temperature": {
"value": 26.6,
"time": 1524448722000
}
},
"method": "thing.event.property.post"
}
我们只需关注 params
部分的编写即可。
在控制台程序中,新建一个类 TestModel
。
public class TestModel
{
public string id { get { return DateTime.Now.Ticks.ToString(); } set { } }
public string version { get { return "1.0"; } set { } }
public Params @params { get; set; }
public class Params
{
这样定义后,我们使用时,只需定义 params 部分即可, id、version等,不需要自己动态取值,做重复劳动。
上面有个 @params
,这是因为 params 是 C# 的关键字,命名字段时为了取消冲突所以加个 @
。
根据我们在阿里云物联网控制台定义的 属性
,继续补充内容:
public class TestModel
{
public string id { get { return DateTime.Now.Ticks.ToString(); } set { } }
public string version { get { return "1.0"; } set { } }
public Params @params { get; set; }
public class Params
{
public Cpu_temperature cpu_temperature { get; set; }
public Gree_temperature gree_temperature { get; set; }
public class Cpu_temperature
{
public float value{ get; set; }
public long time { get; set; }
}
public class Gree_temperature
{
public float value { get; set; }
public long time { get; set; }
}
}
public string @method { get { return "thing.event.property.post"; } set { } }
}
问题是,这样写还不行,因为还没有给 TestModel 里的类进行实例化。
我们可以利用 构造函数 对里面的引用类型进行实例化,当然亦可编写依赖注入容器。。
public class TestModel
{
public string id { get { return DateTime.Now.Ticks.ToString(); } set { } }
public string version { get { return "1.0"; } set { } }
public Params @params { get; set; }
public TestModel()
{
@params = new Params();
}
public class Params
{
public Cpu_temperature cpu_temperature { get; set; }
public Gree_temperature gree_temperature { get; set; }
public Params()
{
cpu_temperature = new Cpu_temperature();
gree_temperature = new Gree_temperature();
}
public class Cpu_temperature
{
public float value{ get; set; }
public long time { get; set; }
}
public class Gree_temperature
{
public float value { get; set; }
public long time { get; set; }
}
}
public string method { get { return "thing.event.property.post"; } set { } }
}
3)上传设备属性数据
编写控制台程序,引入 CZGL.AliIoTClient ,编写基础代码(请替换 DeviceOptions 的信息):
static AliIoTClientJson client;
static void Main(string[] args)
{
再 Program 类中,编写一个方法用来收集属性数据、上传属性数据:
public static void ToServer()
{
启动控制台应用,在阿里云物联网控制台,打开设备,点击 运行状态 ,即可看到上传的属性数据。 文章后面会详细说明 CZGL.AliIoTClient 关于属性上传的具体情况。
当然,这样的数据只是固定赋值的,这里只是演示,具体数据需要开发者采集。下面给出一些模拟数据的方法。
4)模拟数据
笔者编写了三个数据模拟方法:
不需要理会里面是怎么写的,仅是个模拟数据的工具而已,你也可以自己编写相应的模拟数据方法。 里面有四个参数,对应:原始值、最小值、最大值、波动范围。
int 模拟数据
range 是指每次生成 [0,range] 范围的增/减量,
例如 初始值 56 , range = 2
,那么可能 56±0 或 56±1 或 56±2 , 是增还是减,是随机的。但是设置 min 、 max 后,最后生成的值会在此范围内波动。
float、double 模拟数据
对应 float、double,range 的值越大,波动范围越小。默认 range = 8
,大概就是每次 0.1 的波动范围。
其中,float 小数保留两位, double 小数保留 4 位,
需要更高或减少小数位数,修改一下 ...ToString("#0.0000")
模拟属性数据
接下来我们模拟一下两个属性的数据。
在 Program 中定义两个变量存储 cpu 和 空调 数据。
static float cpu_temperature = 50.0F;
static float gree_temperature = 26.0F;
修改 ToServer() 方法
public static void ToServer()
{
在 Main() 方法里增加代码:
// 定时上传数据
while (true)
{
ToServer();
Thread.Sleep(1000);
}
}
至此,已经基本完成。
完整代码如下:
class Program
{
static AliIoTClientJson client;
static void Main(string[] args)
{
运行控制台程序,然后打开阿里云物联网控制台,查看设备的运行状态,打开 自动刷新
,查看数据变化。
如果你觉得每次波动得范围太大,可以把 range 改大一些,如果你觉得数据不稳定,
可以把 min - max 的范围改小一些,模拟的数据值将在此范围波动。
5)设备属性 - CZGL.AliIoTClient
首先要说明,产品创建前,需要设置为 Alinkjson/透传 产品,
因此 CZGL.AliIoTClient 设置了两个客户端类。
类名 | 说明 |
---|---|
AliIoTClientJson | 以Alink json形式上传数据 |
AliIoTClientBinary | 以透传形式上传数据 |
这两个类,仅在 属性、事件、服务 三个功能中数据上传形式有差别,连接服务器、普通Topic等其它数据的使用是完全一致的。
一个产品只能定义一种上传数据的形式。
CZGL.AliIoTClient 中上传属性的方法(Alink json):
获取 UNIX 时间: 由于阿里云要求上传的属性数据等,要带上 Unix 时间,所以笔者一并写在 CZGL.AliIoTClient 了。
public static long GetUnixTime()
使用示例参考上面的过程。
透传
如果你想使用透传,则使用 AliIoTClientBinary 类,
6)关于透传
透传以二进制报文形式上传,例如 0x020000007b00 ,这里是 16 进制,每两位一个字节。
如果是 2进制 ,则是 8位 一个字节。
透传需要在阿里云物联网控制台创建 透传 产品后,设置脚本,将透传数据 转为 Alink json。
透传数据是自定义的,以字节为单位,其中有5个字节为特定字节,以字节位进行拆分的。
记住,是以字节为单位。
透传数据格式标准:
字段 | 字节数 |
---|---|
帧类型 | 1字节 |
请求ID | 4字节 |
属性数据 | N个字节 |
帧类型:
值(16进制) | 说明 |
---|---|
0x00 | 属性上报 |
0x01 | 属性设置 |
0x02 | 上报数据返回结果 |
0x03 | 属性设置设备返回结果 |
0xff | 未知的命令 |
**举例说明 **
很多人是直接把 10进制 或 16进制 直接转换成 2进制 。
例如 0x020000007b00,转为 2进制 :100000000000000000000000000111101100000000。 但是这样是错误的。
以上面 cpu 和 空调温度 举例,要上传属性数据,帧类型为 0x00。
属性 | 10进制 | 16进制 | 2进制 | 划一下2进制 |
---|---|---|---|---|
cpu_temperature | 56 | 38 | 00111000 | 00 11 10 00 |
gree_temperature | 26 | 1a | 00011010 | 00 01 10 10 |
应当这样拆分和设置值:
字节类转 | 字节数 | 16进制 | 2进制 |
---|---|---|---|
进制表示 | 无 | 0x | 无 |
帧类型 | 1字节 | 00 | 00000000 |
ID | 4字节 | 00 00 00 7b | 00000000 00000000 00000000 01111011 |
cpu_temperature | 1 字节 | 38 | 00111000 |
gree_temperature | 1 字节 | 1a | 00011010 |
16进制数据:
0x000000007b381a
2进制数据:
00000000000000000000000000000000011110110011100000011010
将 16进制 或 2进制 的数据存储到 byte[] 变量中,切记要强制转换。 存储时,一个 byte 为一个字节,M个字节,则 byte[M]。
存储:
使用 16进制 存储透传数据,2进制弄不来的。
有些同学非要用 2进制 存储,反正我是弄不来,用 二进制 数值 存储,这个触发我的知识盲区了。
示例(仅对 AliIoTClientBinary 客户端有效):
// 存储透传数据
byte[] b = new byte[7];
b[0] = 0x00
如果上报属性,要求 请输入二进制数据Base64编码后的字符串
,可以使用
byte[] b = new byte[7];
b[0] = 0x00
透传数据的坑很多,这里 CZGL.AliIoTClient 只提供如何处理数据和上传数据,云端的脚本解析请参考
https://help.aliyun.com/document_detail/114621.html?spm=a2c4g.11186623.2.13.209b65b9Q9z0Nx#concept-185365
7)后续说明
其实,每次上传服务器都会作出响应,CZGL.AliIoTClient 默认不接收这些响应信息。
你可以使用 OpenPropertyPostReply()
接收设备属性上传后服务器的响应,应当在连接服务器前使用此方法
使用 Close.PropertyPostReply()
取消接收设备属性上传后服务器的响应。
示例:
client.ClosePropertyPostReply(); // 连接服务器
client.ConnectIoT(topics, null, 60);
上传属性数据,可以分开上传,不需要每次都要上传全部的属性。需要更新哪个属性,就上传这个属性。
原文地址:https://www.cnblogs.com/whuanle/p/10994694.html
.NET社区新闻,深度好文,欢迎访问公众号文章汇总 http://www.csharpkit.com
最后
以上就是老迟到耳机为你收集整理的阿里云物联网 .NET Core 客户端 | CZGL.AliIoTClient:4. 设备上报属性的全部内容,希望文章能够帮你解决阿里云物联网 .NET Core 客户端 | CZGL.AliIoTClient:4. 设备上报属性所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复