优化rpc;设备在线、离线状态上传

This commit is contained in:
dd 2022-04-15 16:49:58 +08:00
parent ca6f298bf2
commit c916cf1a04
14 changed files with 334 additions and 251 deletions

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -11,5 +11,5 @@
<wt:combobox field="Searcher.IsSuccess" empty-text="@Localizer["Sys.All"]" />
</wt:row>
</wt:searchpanel>
<wt:quote>注意不同平台的rpc的topic和payload均不同后期教程会更新到<a href="http://iotgateway.net/" target="_blank">http://iotgateway.net/</a></wt:quote>
<wt:quote>注意不同平台的rpc的topic和payload均不同后期教程会更新到<a href="http://42.193.160.84/" target="_blank">http://iotgateway.net/</a></wt:quote>
<wt:grid vm="@Model" url="/Rpc/RpcLog/Search" hidden-checkbox="true" hidden-grid-index="true" />

View File

@ -69,7 +69,7 @@
<span class="login-error">@Model.MSD.GetFirstError()</span>
<button type="submit" class="login-button" style="cursor:pointer">@Model.Localizer["Login.Login"]</button>
<div class="login-button" style="cursor:pointer">
<a href="http://iotgateway.net/" target="_blank">跳转教程文档,持续更新,收藏不迷路</a>
<a href="http://42.193.160.84/" target="_blank">跳转教程文档,持续更新,收藏不迷路</a>
</div>
@*<wt:linkbutton window-title="@Model.Localizer["Login.Register"]" class="login-button" style="cursor:pointer" target="ButtonTargetEnum.Layer" window-width="500" window-height="500" url="/Login/Reg" text="@Model.Localizer["Login.Register"]" />*@

Binary file not shown.

View File

@ -21,7 +21,6 @@ namespace DriverModbusMaster
private SerialPort port = null;
private Modbus.Device.ModbusMaster master = null;
private SerialPortAdapter adapter = null;
private object locker=new object();
#region
[ConfigParameter("设备Id")]
@ -199,135 +198,119 @@ namespace DriverModbusMaster
[Method("功能码:03", description: "ReadHoldingRegisters读保持寄存器")]
public DriverReturnValueModel ReadHoldingRegisters(DriverAddressIoArgModel ioarg)
{
lock (locker)
DriverReturnValueModel ret = new();
try
{
DriverReturnValueModel ret = new();
try
if (IsConnected)
ret = ReadRegistersBuffers(3, ioarg);
else
{
if (IsConnected)
ret = ReadRegistersBuffers(3, ioarg);
else
{
ret.StatusType = VaribaleStatusTypeEnum.Bad;
ret.Message = "TCP连接异常";
}
ret.StatusType = VaribaleStatusTypeEnum.Bad;
ret.Message = "TCP连接异常";
}
catch (Exception ex)
{
ret.StatusType = VaribaleStatusTypeEnum.UnKnow;
ret.Message = ex.Message;
}
return ret;
}
catch (Exception ex)
{
ret.StatusType = VaribaleStatusTypeEnum.UnKnow;
ret.Message = ex.Message;
}
return ret;
}
[Method("功能码:04", description: "ReadHoldingRegisters读输入寄存器")]
public DriverReturnValueModel ReadInputRegisters(DriverAddressIoArgModel ioarg)
{
lock (locker)
DriverReturnValueModel ret = new();
try
{
DriverReturnValueModel ret = new();
try
if (IsConnected)
ret = ReadRegistersBuffers(4, ioarg);
else
{
if (IsConnected)
ret = ReadRegistersBuffers(4, ioarg);
else
{
ret.StatusType = VaribaleStatusTypeEnum.Bad;
ret.Message = "TCP连接异常";
}
ret.StatusType = VaribaleStatusTypeEnum.Bad;
ret.Message = "TCP连接异常";
}
catch (Exception ex)
{
ret.StatusType = VaribaleStatusTypeEnum.UnKnow;
ret.Message = ex.Message;
}
return ret;
}
catch (Exception ex)
{
ret.StatusType = VaribaleStatusTypeEnum.UnKnow;
ret.Message = ex.Message;
}
return ret;
}
[Method("功能码:01", description: "ReadCoil读线圈")]
public DriverReturnValueModel ReadCoil(DriverAddressIoArgModel ioarg)
{
lock (locker)
DriverReturnValueModel ret = new();
try
{
DriverReturnValueModel ret = new();
try
if (IsConnected)
{
if (IsConnected)
var retBool = master.ReadCoils(SlaveAddress, ushort.Parse(ioarg.Address), 1)[0];
if (ioarg.ValueType == DataTypeEnum.Bit)
{
var retBool = master.ReadCoils(SlaveAddress, ushort.Parse(ioarg.Address), 1)[0];
if (ioarg.ValueType == DataTypeEnum.Bit)
{
if (retBool)
ret.Value = 1;
else
ret.Value = 0;
}
if (retBool)
ret.Value = 1;
else
ret.Value = retBool;
ret.StatusType = VaribaleStatusTypeEnum.Good;
ret.Value = 0;
}
else
{
ret.StatusType = VaribaleStatusTypeEnum.Bad;
ret.Message = "TCP连接异常";
}
ret.Value = retBool;
ret.StatusType = VaribaleStatusTypeEnum.Good;
}
catch (Exception ex)
else
{
ret.StatusType = VaribaleStatusTypeEnum.UnKnow;
ret.Message = ex.Message;
ret.StatusType = VaribaleStatusTypeEnum.Bad;
ret.Message = "TCP连接异常";
}
return ret;
}
catch (Exception ex)
{
ret.StatusType = VaribaleStatusTypeEnum.UnKnow;
ret.Message = ex.Message;
}
return ret;
}
[Method("功能码:02", description: "ReadInput读输入")]
public DriverReturnValueModel ReadInput(DriverAddressIoArgModel ioarg)
{
lock (locker)
DriverReturnValueModel ret = new();
try
{
DriverReturnValueModel ret = new();
try
if (IsConnected)
{
if (IsConnected)
var retBool = master.ReadInputs(SlaveAddress, ushort.Parse(ioarg.Address), 1)[0];
if (ioarg.ValueType == DataTypeEnum.Bit)
{
var retBool = master.ReadInputs(SlaveAddress, ushort.Parse(ioarg.Address), 1)[0];
if (ioarg.ValueType == DataTypeEnum.Bit)
{
if (retBool)
ret.Value = 1;
else
ret.Value = 0;
}
if (retBool)
ret.Value = 1;
else
ret.Value = retBool;
ret.StatusType = VaribaleStatusTypeEnum.Good;
ret.Value = 0;
}
else
{
ret.StatusType = VaribaleStatusTypeEnum.Bad;
ret.Message = "TCP连接异常";
}
ret.Value = retBool;
ret.StatusType = VaribaleStatusTypeEnum.Good;
}
catch (Exception ex)
else
{
ret.StatusType = VaribaleStatusTypeEnum.UnKnow;
ret.Message = ex.Message;
ret.StatusType = VaribaleStatusTypeEnum.Bad;
ret.Message = "TCP连接异常";
}
return ret;
}
catch (Exception ex)
{
ret.StatusType = VaribaleStatusTypeEnum.UnKnow;
ret.Message = ex.Message;
}
return ret;
}
@ -463,42 +446,38 @@ namespace DriverModbusMaster
public async Task<RpcResponse> WriteAsync(string RequestId, string Method, DriverAddressIoArgModel Ioarg)
{
lock (locker)
RpcResponse rpcResponse = new() { IsSuccess = false };
try
{
RpcResponse rpcResponse = new() { IsSuccess = false };
try
ushort address = ushort.Parse(Ioarg.Address);
if (!IsConnected)
rpcResponse.Description = "设备连接已断开";
else
{
ushort address = ushort.Parse(Ioarg.Address);
if (!IsConnected)
rpcResponse.Description = "设备连接已断开";
else
//功能码01
if (Method == nameof(ReadCoil))
{
//功能码01
if (Method == nameof(ReadCoil))
{
bool value = Ioarg.Value.ToString() == "1" || Ioarg.Value.ToString().ToLower() == "true";
master.WriteSingleCoilAsync(SlaveAddress, address, value);
rpcResponse.IsSuccess = true;
return rpcResponse;
}
//功能码03
else if (Method == nameof(ReadHoldingRegisters))
{
master.WriteSingleRegisterAsync(SlaveAddress, address, ushort.Parse(Ioarg.Value.ToString()));
rpcResponse.IsSuccess = true;
return rpcResponse;
}
else
rpcResponse.Description = $"不支持写入:{Method}";
bool value = Ioarg.Value.ToString() == "1" || Ioarg.Value.ToString().ToLower() == "true";
master.WriteSingleCoilAsync(SlaveAddress, address, value);
rpcResponse.IsSuccess = true;
return rpcResponse;
}
//功能码03
else if (Method == nameof(ReadHoldingRegisters))
{
master.WriteSingleRegisterAsync(SlaveAddress, address, ushort.Parse(Ioarg.Value.ToString()));
rpcResponse.IsSuccess = true;
return rpcResponse;
}
else
rpcResponse.Description = $"不支持写入:{Method}";
}
catch (Exception ex)
{
rpcResponse.Description = $"写入失败:{Method},{Ioarg}";
}
return rpcResponse;
}
catch (Exception ex)
{
rpcResponse.Description = $"写入失败:{Method},{Ioarg}";
}
return rpcResponse;
}
}
public enum PLC_TYPE

View File

@ -37,7 +37,6 @@ namespace Plugin
_DrvierManager = drvierManager;
_MyMqttClient = myMqttClient;
_MqttServer = mqttServer;
try
{
using (var DC = new DataContext(connnectSetting, DBType))

View File

@ -1,19 +1,11 @@
using Microsoft.EntityFrameworkCore;
using PluginInterface;
using System;
using System.Collections.Generic;
using System.Linq;
using PluginInterface;
using System.Reflection;
using System.Threading;
using System.Threading.Tasks;
using IoTGateway.DataAccess;
using IoTGateway.Model;
using WalkingTec.Mvvm.Core;
using DynamicExpresso;
using MQTTnet.Server;
using Newtonsoft.Json;
using Microsoft.Extensions.Logging;
using PluginInterface.IoTSharp;
namespace Plugin
{
@ -29,7 +21,8 @@ namespace Plugin
private DateTime TsStartDt = new DateTime(1970, 1, 1);
private CancellationTokenSource tokenSource = new CancellationTokenSource();
private Interpreter Interpreter = null;
private object _lock = new object();
private bool lastConnected = false;
public DeviceThread(Device device, IDriver driver, string ProjectId, MyMqttClient myMqttClient, Interpreter interpreter, IMqttServer mqttServer, ILogger logger)
{
_myMqttClient = myMqttClient;
@ -58,8 +51,9 @@ namespace Plugin
myMqttClient.UploadAttributeAsync(device.DeviceName, device.DeviceConfigs.Where(x => x.DataSide == DataSide.ClientSide).ToDictionary(x => x.DeviceConfigName, x => x.Value));
task = Task.Run(() =>
{
while (true)
{
Thread.Sleep(5000);
while (true)
{
if (tokenSource.IsCancellationRequested)
{
@ -67,92 +61,103 @@ namespace Plugin
return;
}
try
lock (_lock)
{
Dictionary<string, List<PayLoad>> sendModel = new() { { _device.DeviceName, new() } };
var payLoad = new PayLoad() { Values = new() };
if (driver.IsConnected)
try
{
if (_device.DeviceVariables != null)
Dictionary<string, List<PayLoad>> sendModel = new() { { _device.DeviceName, new() } };
var payLoad = new PayLoad() { Values = new() };
if (driver.IsConnected)
{
foreach (var item in _device.DeviceVariables)
if (_device.DeviceVariables != null)
{
var ret = new DriverReturnValueModel();
var ioarg = new DriverAddressIoArgModel
foreach (var item in _device.DeviceVariables)
{
ID = item.ID,
Address = item.DeviceAddress,
ValueType = item.DataType
};
var method = Methods.Where(x => x.Name == item.Method).FirstOrDefault();
if (method == null)
ret.StatusType = VaribaleStatusTypeEnum.MethodError;
else
ret = (DriverReturnValueModel)method.Invoke(_driver, new object[1] { ioarg });
var ret = new DriverReturnValueModel();
var ioarg = new DriverAddressIoArgModel
{
ID = item.ID,
Address = item.DeviceAddress,
ValueType = item.DataType
};
var method = Methods.Where(x => x.Name == item.Method).FirstOrDefault();
if (method == null)
ret.StatusType = VaribaleStatusTypeEnum.MethodError;
else
ret = (DriverReturnValueModel)method.Invoke(_driver, new object[1] { ioarg });
if (ret.StatusType == VaribaleStatusTypeEnum.Good && !string.IsNullOrWhiteSpace(item.Expressions?.Trim()))
if (ret.StatusType == VaribaleStatusTypeEnum.Good && !string.IsNullOrWhiteSpace(item.Expressions?.Trim()))
{
try
{
ret.CookedValue = interpreter.Eval(DealMysqlStr(item.Expressions).Replace("raw", ret.Value?.ToString()));
}
catch (Exception)
{
ret.StatusType = VaribaleStatusTypeEnum.ExpressionError;
}
}
else
ret.CookedValue = ret.Value;
payLoad.Values[item.Name] = ret.CookedValue;
ret.VarId = item.ID;
//变化了才推送到mqttserver用于前端展示
if (DeviceValues[item.ID].StatusType != ret.StatusType || DeviceValues[item.ID].Value?.ToString() != ret.Value?.ToString() || DeviceValues[item.ID].CookedValue?.ToString() != ret.CookedValue?.ToString())
{
//这是设备变量列表要用的
mqttServer.PublishAsync($"internal/v1/gateway/telemetry/{_device.DeviceName}/{item.Name}", JsonConvert.SerializeObject(ret));
//这是在线组态要用的
mqttServer.PublishAsync($"v1/gateway/telemetry/{_device.DeviceName}/{item.Name}", JsonConvert.SerializeObject(ret.CookedValue));
}
DeviceValues[item.ID] = ret;
}
payLoad.TS = (long)(DateTime.UtcNow - TsStartDt).TotalMilliseconds;
if (DeviceValues.Any(x => x.Value.Value == null))
{
try
{
ret.CookedValue = interpreter.Eval(DealMysqlStr(item.Expressions).Replace("raw", ret.Value?.ToString()));
}
catch (Exception)
{
ret.StatusType = VaribaleStatusTypeEnum.ExpressionError;
}
payLoad.Values = null;
payLoad.DeviceStatus = DeviceStatusTypeEnum.Bad;
}
else
ret.CookedValue = ret.Value;
payLoad.Values[item.Name] = ret.CookedValue;
ret.VarId = item.ID;
//变化了才推送到mqttserver用于前端展示
if (DeviceValues[item.ID].StatusType != ret.StatusType || DeviceValues[item.ID].Value?.ToString() != ret.Value?.ToString() || DeviceValues[item.ID].CookedValue?.ToString() != ret.CookedValue?.ToString())
{
//这是设备变量列表要用的
mqttServer.PublishAsync($"internal/v1/gateway/telemetry/{_device.DeviceName}/{item.Name}", JsonConvert.SerializeObject(ret));
//这是在线组态要用的
mqttServer.PublishAsync($"v1/gateway/telemetry/{_device.DeviceName}/{item.Name}", JsonConvert.SerializeObject(ret.CookedValue));
payLoad.DeviceStatus = DeviceStatusTypeEnum.Good;
sendModel[_device.DeviceName] = new List<PayLoad> { payLoad };
myMqttClient.PublishTelemetry(_device, sendModel);
}
DeviceValues[item.ID] = ret;
}
payLoad.TS = (long)(DateTime.Now - TsStartDt).TotalMilliseconds;
if (DeviceValues.Any(x => x.Value.Value == null))
}
else
{
if (driver.Connect())
_myMqttClient.DeviceConnected(_device.DeviceName);
else if (lastConnected)
{
payLoad.Values = null;
payLoad.DeviceStatus = DeviceStatusTypeEnum.Bad;
}
else
{
payLoad.DeviceStatus = DeviceStatusTypeEnum.Good;
sendModel[_device.DeviceName] = new List<PayLoad> { payLoad };
myMqttClient.PublishTelemetry(_device, sendModel);
lastConnected = false;
_myMqttClient.DeviceDisconnected(_device.DeviceName);
}
}
}
else
catch (Exception ex)
{
driver.Connect();
_logger.LogError($"线程循环异常,{_device.DeviceName}", ex);
}
}
catch (Exception ex)
{
_logger.LogError($"线程循环异常,{_device.DeviceName}", ex);
}
Thread.Sleep((int)_driver.MinPeriod);
}
});
}
else
_myMqttClient.DeviceDisconnected(_device.DeviceName);
}
private void MyMqttClient_OnExcRpc(object? sender, RpcRequest e)
@ -173,47 +178,55 @@ namespace Plugin
//执行写入变量RPC
if (e.Method.ToLower() == "write")
{
//没连接就连接
if (!_driver.IsConnected)
_driver.Connect();
//连接成功就尝试一个一个的写入,注意:目前写入地址和读取地址是相同的对于PLC来说没问题其他的要自己改........
if (_driver.IsConnected)
lock (_lock)
{
foreach (var para in e.Params)
bool RpcConnected = false;
//没连接就连接
if (!_driver.IsConnected)
if (_driver.Connect())
RpcConnected = true;
//连接成功就尝试一个一个的写入,注意:目前写入地址和读取地址是相同的对于PLC来说没问题其他的要自己改........
if (_driver.IsConnected)
{
//先查配置项,要用到配置的地址、数据类型、方法(方法最主要是用于区分写入数据的辅助判断比如modbus不同的功能码)
var deviceVariable = _device.DeviceVariables.Where(x => x.Name == para.Key).FirstOrDefault();
if (deviceVariable != null)
foreach (var para in e.Params)
{
DriverAddressIoArgModel ioArgModel = new()
//先查配置项,要用到配置的地址、数据类型、方法(方法最主要是用于区分写入数据的辅助判断比如modbus不同的功能码)
var deviceVariable = _device.DeviceVariables.Where(x => x.Name == para.Key).FirstOrDefault();
if (deviceVariable != null)
{
Address = deviceVariable.DeviceAddress,
Value = para.Value,
ValueType = deviceVariable.DataType
};
var writeResponse = _driver.WriteAsync(e.RequestId, deviceVariable.Method, ioArgModel).Result;
rpcResponse.IsSuccess = writeResponse.IsSuccess;
if (!writeResponse.IsSuccess)
DriverAddressIoArgModel ioArgModel = new()
{
Address = deviceVariable.DeviceAddress,
Value = para.Value,
ValueType = deviceVariable.DataType
};
var writeResponse = _driver.WriteAsync(e.RequestId, deviceVariable.Method, ioArgModel).Result;
rpcResponse.IsSuccess = writeResponse.IsSuccess;
if (!writeResponse.IsSuccess)
{
rpcResponse.Description = writeResponse.Description;
break;
}
}
else
{
rpcResponse.Description = writeResponse.Description;
rpcResponse.IsSuccess = false;
rpcResponse.Description = $"未能找到变量:{para.Key}";
break;
}
}
else
{
rpcResponse.IsSuccess = false;
rpcResponse.Description = $"未能找到变量:{para.Key}";
break;
}
}
if (RpcConnected)
_driver.Close();
}
else//连接失败
{
rpcResponse.IsSuccess = false;
rpcResponse.Description = $"{e.DeviceName} 连接失败";
}
}
else//连接失败
{
rpcResponse.IsSuccess = false;
rpcResponse.Description = $"{e.DeviceName} 连接失败";
}
}
//其他RPC TODO
else
@ -227,12 +240,12 @@ namespace Plugin
//纪录入库
rpcLog.IsSuccess = rpcResponse.IsSuccess;
rpcLog.Description = rpcResponse.Description;
rpcLog.EndTime=DateTime.Now;
rpcLog.EndTime = DateTime.Now;
using (var DC = new DataContext(IoTBackgroundService.connnectSetting, IoTBackgroundService.DBType))
{
DC.Set<RpcLog>().Add(rpcLog);
DC.Set<RpcLog>().Add(rpcLog);
DC.SaveChanges();
}
}
@ -241,6 +254,7 @@ namespace Plugin
public void StopThread()
{
_logger.LogInformation($"线程停止:{_device.DeviceName}");
_myMqttClient.DeviceDisconnected(_device.DeviceName);
if (task != null)
{
_myMqttClient.OnExcRpc -= MyMqttClient_OnExcRpc;

View File

@ -101,21 +101,39 @@ namespace Plugin
}
}
private readonly string tbRpcTopic = "v1/gateway/rpc";
private void OnConnected()
{
//v1/gateway/attributes
//Message: {"device": "Device A", "data": {"attribute1": "value1", "attribute2": 42}}
//v1/gateway/rpc
//{"device": "Device A", "data": {"id": $request_id, "method": "toggle_gpio", "params": {"pin":1}}}
Client.SubscribeAsync(tbRpcTopic, MqttQualityOfServiceLevel.ExactlyOnce);//tb server side rpc
Client.SubscribeAsync($"devices/+/rpc/request/+/+", MqttQualityOfServiceLevel.ExactlyOnce);
Client.SubscribeAsync($"devices/Modbus/attributes/update/", MqttQualityOfServiceLevel.ExactlyOnce);
Client.SubscribeAsync($"devices/+/attributes/response/+", MqttQualityOfServiceLevel.ExactlyOnce);
switch (_systemConfig.IoTPlatformType)
{
case IoTPlatformType.ThingsBoard:
//{"device": "Device A", "data": {"id": $request_id, "method": "toggle_gpio", "params": {"pin":1}}}
Client.SubscribeAsync(tbRpcTopic, MqttQualityOfServiceLevel.ExactlyOnce);
//Message: {"id": $request_id, "device": "Device A", "value": "value1"}
Client.SubscribeAsync("v1/gateway/attributes/response", MqttQualityOfServiceLevel.ExactlyOnce);
//Message: {"device": "Device A", "data": {"attribute1": "value1", "attribute2": 42}}
Client.SubscribeAsync("v1/gateway/attributes", MqttQualityOfServiceLevel.ExactlyOnce);
break;
case IoTPlatformType.IoTSharp:
Client.SubscribeAsync("devices/+/rpc/response/+/+", MqttQualityOfServiceLevel.ExactlyOnce);
Client.SubscribeAsync("devices/+/attributes/update", MqttQualityOfServiceLevel.ExactlyOnce);
//Message: {"device": "Device A", "data": {"attribute1": "value1", "attribute2": 42}}
Client.SubscribeAsync("devices/+/attributes/response/+", MqttQualityOfServiceLevel.ExactlyOnce);
break;
case IoTPlatformType.AliCloudIoT:
break;
case IoTPlatformType.TencentIoTHub:
break;
case IoTPlatformType.BaiduIoTCore:
break;
case IoTPlatformType.OneNET:
break;
default:
break;
}
_logger.LogInformation($"MQTT CONNECTED WITH SERVER ");
}
private readonly string tbRpcTopic = @"v1/gateway/rpc";
private Task Client_ApplicationMessageReceived(MqttApplicationMessageReceivedEventArgs e)
{
@ -299,18 +317,47 @@ namespace Plugin
}
public Task RequestAttributes(string _device, bool anySide, params string[] args)
public Task RequestAttributes(string _devicename, bool anySide, params string[] args)
{
//Topic: v1/gateway/attributes/request
// Message: { "id": $request_id, "device": "Device A", "client": true, "key": "attribute1"}
//Topic: v1/gateway/attributes/response
//Message: {"id": $request_id, "device": "Device A", "value": "value1"}
string id = Guid.NewGuid().ToString();
string topic = $"devices/{_device}/attributes/request/{id}";
Dictionary<string, string> keys = new Dictionary<string, string>();
keys.Add(anySide ? "anySide" : "server", string.Join(",", args));
Client.SubscribeAsync($"devices/{_device}/attributes/response/{id}", MqttQualityOfServiceLevel.ExactlyOnce);
return Client.PublishAsync(topic, Newtonsoft.Json.JsonConvert.SerializeObject(keys), MqttQualityOfServiceLevel.ExactlyOnce);
try
{
string id = Guid.NewGuid().ToString();
switch (_systemConfig.IoTPlatformType)
{
case IoTPlatformType.ThingsBoard:
//{"id": $request_id, "device": "Device A", "client": true, "key": "attribute1"}
Dictionary<string, object> tbRequestData = new Dictionary<string, object>
{
{ "id",id},
{ "device",_devicename},
{ "client",true},
{ "key",args[0]}
};
return Client.PublishAsync("v1/gateway/attributes/request", JsonConvert.SerializeObject(tbRequestData), MqttQualityOfServiceLevel.ExactlyOnce);
case IoTPlatformType.IoTSharp:
string topic = $"devices/{_devicename}/attributes/request/{id}";
Dictionary<string, string> keys = new Dictionary<string, string>();
keys.Add(anySide ? "anySide" : "server", string.Join(",", args));
Client.SubscribeAsync($"devices/{_devicename}/attributes/response/{id}", MqttQualityOfServiceLevel.ExactlyOnce);
return Client.PublishAsync(topic, JsonConvert.SerializeObject(keys), MqttQualityOfServiceLevel.ExactlyOnce);
case IoTPlatformType.AliCloudIoT:
break;
case IoTPlatformType.TencentIoTHub:
break;
case IoTPlatformType.BaiduIoTCore:
break;
case IoTPlatformType.OneNET:
break;
default:
break;
}
}
catch (Exception ex)
{
_logger.LogError($"RequestAttributes:{_devicename}", ex);
}
return Task.CompletedTask;
}
public void PublishTelemetry(Device device, Dictionary<string, List<PayLoad>> SendModel)
@ -353,16 +400,60 @@ namespace Plugin
}
public void DeviceConnected()
public async Task DeviceConnected(string DeviceName)
{
//Topic: v1/gateway/connect
//Message: { "device":"Device A"}
try
{
switch (_systemConfig.IoTPlatformType)
{
case IoTPlatformType.ThingsBoard:
case IoTPlatformType.IoTSharp:
await Client.PublishAsync("v1/gateway/connect", JsonConvert.SerializeObject(new Dictionary<string, string> { { "device", DeviceName } }));
break;
case IoTPlatformType.AliCloudIoT:
break;
case IoTPlatformType.TencentIoTHub:
break;
case IoTPlatformType.BaiduIoTCore:
break;
case IoTPlatformType.OneNET:
break;
default:
break;
}
}
catch (Exception ex)
{
_logger.LogError($"DeviceConnected:{DeviceName}", ex);
}
}
public void DeviceDisconnected()
public async Task DeviceDisconnected(string DeviceName)
{
//Topic: v1/gateway/connect
//Message: { "device":"Device A"}
try
{
switch (_systemConfig.IoTPlatformType)
{
case IoTPlatformType.ThingsBoard:
case IoTPlatformType.IoTSharp:
await Client.PublishAsync("v1/gateway/disconnect", JsonConvert.SerializeObject(new Dictionary<string, string> { { "device", DeviceName } }));
break;
case IoTPlatformType.AliCloudIoT:
break;
case IoTPlatformType.TencentIoTHub:
break;
case IoTPlatformType.BaiduIoTCore:
break;
case IoTPlatformType.OneNET:
break;
default:
break;
}
}
catch (Exception ex)
{
_logger.LogError($"DeviceDisconnected:{DeviceName}", ex);
}
}

Binary file not shown.