public DeviceConnectionEventDTO(DeviceConnectionEvent connectionEvent) { RowKey = DateTime.UtcNow.ToInverseTicksRowKey(); PartitionKey = connectionEvent.DeviceId; DeviceId = connectionEvent.DeviceId; TimeStamp = connectionEvent.TimeStamp; FirmwareSKU = connectionEvent.FirmwareSKU; FirmwareRevision = connectionEvent.FirmwareRevision; RSSI = connectionEvent.RSSI; }
void IListener <DeviceConnectionEvent> .Notify(DeviceConnectionEvent value) { if (_device == null || !ReferenceEquals(_device, value.Device)) { return; } foreach (var listener in _subscriber.Values) { listener.Notify(value.Event); } }
/// <summary> /// IoTHubによるデバイス接続/切断EventDataをDeviceConnectionEventに変換する /// </summary> /// <param name="body">EventDataのBodyプロパティ</param> /// <returns>DeviceConnectionEvent配列</returns> private DeviceConnectionEvent[] GetDeviceConnectionEvents(string body) { return(DeviceConnectionEvent.DeserializeIfInvalidThrowEx(body)); }
private async Task <InvokeResult> HandleSystemMessageAsync(string path, string payload) { Metrics.MessagesProcessed++; PEMBus.InstanceLogger.AddCustomEvent(LagoVista.Core.PlatformSupport.LogLevel.Message, "ListenerMOdule_HandleSystemMessageAsync", "Received System Message", path.ToKVP("topic"), payload.ToKVP("body")); var parts = path.Split('/'); if (parts.Length < 5) { var errMsg = $"NuvIoT service messages must be at least 5 segments {path} is {parts.Length} segments"; PEMBus.InstanceLogger.AddError("ListenerModule__HandleSystemMessage", errMsg); return(InvokeResult.FromError(errMsg)); } var deviceId = parts[3]; var device = await PEMBus.DeviceStorage.GetDeviceByDeviceIdAsync(deviceId); if (device == null) { var errMsg = $"Could not find device with device id {deviceId}."; PEMBus.InstanceLogger.AddError("ListenerModule__HandleSystemMessage", errMsg); return(InvokeResult.FromError(errMsg)); } device.LastContact = DateTime.UtcNow.ToJSONString(); if (parts[4] == "state") { device.DeviceTwinDetails.Insert(0, new DeviceManagement.Models.DeviceTwinDetails() { Timestamp = DateTime.UtcNow.ToJSONString(), Details = payload }); var payloadSegements = payload.Split(','); foreach (var segement in payloadSegements) { var fieldParts = segement.Split('='); if (fieldParts.Length == 2) { var nameParts = fieldParts[0].Split('-'); if (nameParts.Length == 2) { var typeName = nameParts[0]; var key = nameParts[1]; var value = fieldParts[1]; if (typeName != "readonly") { var prop = device.Properties.FirstOrDefault(prp => prp.Key == key); if (prop != null) { if (prop.Value != value) { prop.Value = value; prop.LastUpdated = DateTime.UtcNow.ToJSONString(); prop.LastUpdatedBy = "Device Twin"; } } } else { if (key == "firmwareSku") { device.ActualFirmware = value; device.ActualFirmwareDate = DateTime.Now.ToJSONString(); } if (key == "firmwareVersion") { device.ActualFirmwareRevision = value; device.ActualFirmwareDate = DateTime.Now.ToJSONString(); } } } } } } else if (parts[4] == "err") { var err = parts[5]; var action = parts[6]; var exception = new DeviceException() { ErrorCode = err, DeviceId = device.DeviceId, DeviceUniqueId = device.Id, DeviceRepositoryId = device.DeviceRepository.Id, Timestamp = DateTime.UtcNow.ToString(), }; exception.AdditionalDetails.Add(payload); if (action == "raise") { await PEMBus.InstanceConnector.HandleDeviceExceptionAsync(exception); } else if (action == "clear") { await PEMBus.InstanceConnector.ClearDeviceExceptionAsync(exception); } } else if (parts[4] == "iovalues") { var values = payload.Split(','); if (values.Length != 16) { throw new InvalidDataException($"IO Configuration from device should consist of 16 comma delimited values, message consists of ${values.Length} items."); } for (int idx = 0; idx < 8; ++idx) { if (!String.IsNullOrEmpty(values[idx + 8])) { var sensor = device.SensorCollection.Where(sns => sns.Technology != null && sns.Technology.Value == DeviceManagement.Models.SensorTechnology.ADC && sns.PortIndex == idx).FirstOrDefault(); if (sensor != null) { sensor.Value = values[idx + 8]; sensor.LastUpdated = DateTime.UtcNow.ToJSONString(); } } } for (int idx = 0; idx < 8; ++idx) { if (!String.IsNullOrEmpty(values[idx])) { var sensor = device.SensorCollection.Where(sns => sns.Technology != null && sns.Technology.Value == DeviceManagement.Models.SensorTechnology.IO && sns.PortIndex == idx).FirstOrDefault(); if (sensor != null) { sensor.Value = values[idx]; sensor.LastUpdated = DateTime.UtcNow.ToJSONString(); } } } await PEMBus.SensorEvaluator.EvaluateAsync(device); } else if (parts[4] == "geo") { var values = payload.Split(','); if (values.Length < 2) { throw new InvalidDataException($"Geo Location Data type must contain a minimum of 2 fields for latitude and longitude, message consists of ${values.Length} items."); } if (!double.TryParse(values[0], out double lat)) { throw new InvalidDataException($"Invalid Latitude value [{values[0]}]."); } if (lat > 90 || lat < -90) { throw new InvalidDataException($"Invalid Latitude value [{values[0]}], must be between -90 and 90."); } if (!double.TryParse(values[1], out double lon)) { throw new InvalidDataException($"Invalid Longitude value [{values[1]}]."); } if (lon > 180 || lon < -180) { throw new InvalidDataException($"Invalid Latitude value [{values[1]}], must be between -180 and 180."); } device.GeoLocation = new LagoVista.Core.Models.Geo.GeoLocation() { LastUpdated = DateTime.UtcNow.ToJSONString(), Latitude = lat, Longitude = lon, }; } else if (parts[4] == "online") { device.ConnectionTimeStamp = DateTime.UtcNow.ToJSONString(); var rssi = -1.0; var reconnect = false; var payloadSegements = payload.Split(','); foreach (var segement in payloadSegements) { var fieldParts = segement.Split('='); if (fieldParts.Length == 2) { var nameParts = fieldParts[0].Split('-'); if (nameParts.Length == 2) { var typeName = nameParts[0]; var key = nameParts[1]; var value = fieldParts[1]; if (typeName != "readonly") { var prop = device.Properties.FirstOrDefault(prp => prp.Key == key); if (prop != null) { if (prop.Value != value) { if (prop.AttributeType.Value == DeviceAdmin.Models.ParameterTypes.TrueFalse) { if (value == "1") { value = "true"; } else if (value == "0") { value = "false"; } else { value = value.ToLower(); } } prop.Value = value; prop.LastUpdated = DateTime.UtcNow.ToJSONString(); prop.LastUpdatedBy = "Device Twin"; } } } else { if (key == "firmwareSku") { device.ActualFirmware = value; device.ActualFirmwareDate = DateTime.Now.ToJSONString(); } if (key == "firmwareVersion") { device.ActualFirmwareRevision = value; device.ActualFirmwareDate = DateTime.Now.ToJSONString(); } if (key == "rssi") { double.TryParse(value, out rssi); } if (key == "reconnect") { reconnect = value != "0"; } } } } } var connectionEvent = new DeviceConnectionEvent() { DeviceId = device.Id, FirmwareRevision = device.ActualFirmwareRevision, FirmwareSKU = device.ActualFirmware, TimeStamp = DateTime.UtcNow.ToJSONString(), RSSI = rssi, Reconnect = reconnect }; await PEMBus.DeviceConnectionEvent.AddDeviceEventConnectionEvent(connectionEvent); } await PEMBus.DeviceStorage.UpdateDeviceAsync(device); var json = JsonConvert.SerializeObject(Models.DeviceForNotification.FromDevice(device), _camelCaseSettings); var notification = new Notification() { Payload = json, Channel = EntityHeader <Channels> .Create(Channels.Device), ChannelId = device.Id, PayloadType = "Device", DateStamp = DateTime.UtcNow.ToJSONString(), MessageId = Guid.NewGuid().ToId(), Text = "Device Updated", Title = "Device Updated" }; await PEMBus.NotificationPublisher.PublishAsync(Targets.WebSocket, notification); notification = new Notification() { Payload = json, Channel = EntityHeader <Channels> .Create(Channels.DeviceRepository), ChannelId = device.DeviceRepository.Id, PayloadType = "Device", DateStamp = DateTime.UtcNow.ToJSONString(), MessageId = Guid.NewGuid().ToId(), Text = "Device Updated", Title = "Device Updated" }; await PEMBus.NotificationPublisher.PublishAsync(Targets.WebSocket, notification); foreach (var group in device.DeviceGroups) { notification = new Notification() { Payload = json, Channel = EntityHeader <Channels> .Create(Channels.DeviceGroup), ChannelId = group.Id, PayloadType = "Device", DateStamp = DateTime.UtcNow.ToJSONString(), MessageId = Guid.NewGuid().ToId(), Text = "Device Updated", Title = "Device Updated" }; await PEMBus.NotificationPublisher.PublishAsync(Targets.WebSocket, notification); } return(InvokeResult.Success); }