从 HttpTrigger 函数读取 Azure IoT 中心遥测
Read Azure IoT Hub Telemetry from HttpTrigger Function
用例
我有一个 Iot Hub 设备,可以将遥测数据发送到 IoT Hub。
我想使用函数处理遥测数据,例如存储到数据库中。
函数
我在 VS2019 中创建了以下函数并将其发布到 Azure:
[FunctionName("HttpTrigger")]
public static async Task<HttpResponseMessage> Run(
[HttpTrigger(AuthorizationLevel.Anonymous, "post")]HttpRequestMessage req,
ILogger log)
{
log.LogInformation("C# HTTP trigger function processed a request.");
var messages = await req.Content.ReadAsAsync<JArray>();
// If the request is for subscription validation, send back the validation code.
if (messages.Count > 0 && string.Equals((string)messages[0]["eventType"],
"Microsoft.EventGrid.SubscriptionValidationEvent",
System.StringComparison.OrdinalIgnoreCase))
{
log.LogInformation("Validate request received");
return req.CreateResponse<object>(new
{
validationResponse = messages[0]["data"]["validationCode"]
});
}
// The request is not for subscription validation, so it's for one or more events.
foreach (JObject message in messages)
{
// Handle one event.
EventGridEvent eventGridEvent = message.ToObject<EventGridEvent>();
log.LogInformation($"Subject: {eventGridEvent.Subject}");
log.LogInformation($"Time: {eventGridEvent.EventTime}");
log.LogInformation($"Event data: {eventGridEvent.Data.ToString()}");
}
return req.CreateResponse(HttpStatusCode.OK);
}
活动订阅
在 IoT 中心,我使用 Web 挂钩端点类型创建了一个触发函数的事件订阅。
问题
事件数据的正文似乎已加密 (?):
{{
"properties": {},
"systemProperties": {
"iothub-connection-device-id": "smartmeter",
"iothub-connection-auth-method": "{\"scope\":\"device\",\"type\":\"sas\",\"issuer\":\"iothub\",\"acceptingIpFilterRule\":null}",
"iothub-connection-auth-generation-id": "637057961942743477",
"iothub-enqueuedtime": "2019-10-05T08:09:17.973Z",
"iothub-message-source": "Telemetry"
},
"body": "eyJEYXRlVGltZSI6IjIwMTktMTAtMDVUMTA6MDk6MjkiLCJBY3R1YWxUYXJyaWYiOjEsIkFjdHVhbFBvd2VyRGVsaXZlcmVkIjoyNzEuMCwiVG90YWxFbGVjdHJpY2l0eURlbGl2ZXJlZFRhcnJpZjEiOjYwMTU1NzcuMCwiVG90YWxFbGVjdHJpY2l0eURlbGl2ZXJlZFRhcnJpZjIiOjYwMjc5NTIuMH0="
}}
虽然在云端Shell我可以看到可读数据。我还可以通过使用 .Net 中的 EventHubClient 将设备读取到云消息来查看可读数据。
我错过了什么?我怎样才能解密正文?
正文是 Base64 编码的,你可以用
https://docs.microsoft.com/en-us/dotnet/api/system.convert.frombase64string?view=netframework-4.8
这是您邮件的可读正文:
{"DateTime":"2019-10-05T10:09:29","ActualTarrif":1,"ActualPowerDelivered":271.0,"TotalElectricityDeliveredTarrif1":6015577.0,"TotalElectricityDeliveredTarrif2":6027952.0 }
您的设备在未指定 content-type 和 content-encoding 的情况下发送了遥测数据,请参阅 [=] 中缺少这些属性20=]系统属性对象。
设备在发送遥测数据时需要填充这些系统属性,然后您将在事件消息中看到:
"systemProperties":{
"iothub-content-type":"application/json",
"iothub-content-encoding":"utf-8",
...
并且事件的 data.body 将是 json 格式的文本。
更多详情here。
用例
我有一个 Iot Hub 设备,可以将遥测数据发送到 IoT Hub。 我想使用函数处理遥测数据,例如存储到数据库中。
函数
我在 VS2019 中创建了以下函数并将其发布到 Azure:
[FunctionName("HttpTrigger")]
public static async Task<HttpResponseMessage> Run(
[HttpTrigger(AuthorizationLevel.Anonymous, "post")]HttpRequestMessage req,
ILogger log)
{
log.LogInformation("C# HTTP trigger function processed a request.");
var messages = await req.Content.ReadAsAsync<JArray>();
// If the request is for subscription validation, send back the validation code.
if (messages.Count > 0 && string.Equals((string)messages[0]["eventType"],
"Microsoft.EventGrid.SubscriptionValidationEvent",
System.StringComparison.OrdinalIgnoreCase))
{
log.LogInformation("Validate request received");
return req.CreateResponse<object>(new
{
validationResponse = messages[0]["data"]["validationCode"]
});
}
// The request is not for subscription validation, so it's for one or more events.
foreach (JObject message in messages)
{
// Handle one event.
EventGridEvent eventGridEvent = message.ToObject<EventGridEvent>();
log.LogInformation($"Subject: {eventGridEvent.Subject}");
log.LogInformation($"Time: {eventGridEvent.EventTime}");
log.LogInformation($"Event data: {eventGridEvent.Data.ToString()}");
}
return req.CreateResponse(HttpStatusCode.OK);
}
活动订阅
在 IoT 中心,我使用 Web 挂钩端点类型创建了一个触发函数的事件订阅。
问题
事件数据的正文似乎已加密 (?):
{{
"properties": {},
"systemProperties": {
"iothub-connection-device-id": "smartmeter",
"iothub-connection-auth-method": "{\"scope\":\"device\",\"type\":\"sas\",\"issuer\":\"iothub\",\"acceptingIpFilterRule\":null}",
"iothub-connection-auth-generation-id": "637057961942743477",
"iothub-enqueuedtime": "2019-10-05T08:09:17.973Z",
"iothub-message-source": "Telemetry"
},
"body": "eyJEYXRlVGltZSI6IjIwMTktMTAtMDVUMTA6MDk6MjkiLCJBY3R1YWxUYXJyaWYiOjEsIkFjdHVhbFBvd2VyRGVsaXZlcmVkIjoyNzEuMCwiVG90YWxFbGVjdHJpY2l0eURlbGl2ZXJlZFRhcnJpZjEiOjYwMTU1NzcuMCwiVG90YWxFbGVjdHJpY2l0eURlbGl2ZXJlZFRhcnJpZjIiOjYwMjc5NTIuMH0="
}}
虽然在云端Shell我可以看到可读数据。我还可以通过使用 .Net 中的 EventHubClient 将设备读取到云消息来查看可读数据。
我错过了什么?我怎样才能解密正文?
正文是 Base64 编码的,你可以用 https://docs.microsoft.com/en-us/dotnet/api/system.convert.frombase64string?view=netframework-4.8
这是您邮件的可读正文: {"DateTime":"2019-10-05T10:09:29","ActualTarrif":1,"ActualPowerDelivered":271.0,"TotalElectricityDeliveredTarrif1":6015577.0,"TotalElectricityDeliveredTarrif2":6027952.0 }
您的设备在未指定 content-type 和 content-encoding 的情况下发送了遥测数据,请参阅 [=] 中缺少这些属性20=]系统属性对象。
设备在发送遥测数据时需要填充这些系统属性,然后您将在事件消息中看到:
"systemProperties":{
"iothub-content-type":"application/json",
"iothub-content-encoding":"utf-8",
...
并且事件的 data.body 将是 json 格式的文本。
更多详情here。