Routing IoTHub device telemetry messages to storage account and Power BI - azure

I am attempting to route device telemetry data for a device connected to Azure IoTHub.
I have defined the custom endpoint in message routing to a storage account with the Encoding format set to JSON and routing query set to true.
This has successfully sent the data to the storage account but the telemetry data in the message body is in base 64 shown below
{"EnqueuedTimeUtc":"2022-07-13T13:03:28.4770000Z","Properties":{},"SystemProperties":{"connectionDeviceId":"SensorTile","connectionAuthMethod":"{\"scope\":\"device\",\"type\":\"sas\",\"issuer\":\"iothub\",\"acceptingIpFilterRule\":null}","connectionDeviceGenerationId":"6*********971","enqueuedTime":"2022-07-13T13:03:28.4770000Z"},"Body":"eyJBY2NlbGVyb21ldGVyIjp7IlkiOi0xNSwiWCI6MTAsIloiOjEwMzZ9LCJ0cyI6IjIwMjItMDctMTNUMTU6MDM6MjguNDAwKzAyMDAiLCJpZCI6IlNlbnNvclRpbGUifQ=="}
Reading the documentation
"When using JSON encoding, you must set the contentType to application/json and contentEncoding to UTF-8 in the message system properties. Both of these values are case-insensitive. If the content encoding is not set, then IoT Hub will write the messages in base 64 encoded format."
I understand it is possible to translate the data to a UTF-8 format by setting the systemProperties contentType to application/json and contentEncoding to UTF-8 but I am unsure where and how to actually do this or can I use another service such as Stream Analytics/Fuctions/EventHub to achive this?
Also is it possible to filter messages via route query so that only telemetry data is routed ignoring the rest?
Any help is greatly appreciated

The content type and content encoding need to be set when sending the message. That means the device is in charge of setting the properties. Here's a few examples in different languages.
C#
using var eventMessage = new Message(Encoding.UTF8.GetBytes(messagePayload))
{
ContentEncoding = Encoding.UTF8.ToString(),
ContentType = "application/json",
};
C
IOTHUB_MESSAGE_HANDLE message_handle = IoTHubMessage_CreateFromString(message);
(void)IoTHubMessage_SetContentTypeSystemProperty(message_handle, "application%2fjson");
(void)IoTHubMessage_SetContentEncodingSystemProperty(message_handle, "utf-8");
Java
Message msg = new Message(msgStr);
msg.setContentType("application/json");
msg.setProperty("temperatureAlert", temperature > 28 ? "true" : "false");

Setting content type and content encoding is the responsibility of the IoT device that is sending messages to the IoT hub. Setting these values depends on the language-specific device SDK used by the IoT device.
Without these settings, the message routing queries based on the message body won't work as mentioned in this link. Also to filter messages based on the telemetry data, you don't need filtering queries. You can create a route with 'Data source' - 'Device Telemetry Messages' so that only device telemetry data will be routed. Please find the attached screenshot for reference:

Related

Why is the Docusign Java SDK is not typesafe?

I'm using the Docusign Java SDK and I'm curious if anyone else noticed it's NOT typesafe. Are there at least constants for the value I can use instead of generic String values.
for example, to send a JSON webhook payload when you use request an envelope signature:
// configure a connect notification
EventNotification eventNotification = new EventNotification();
// Set up the endpoint URL to call (it must be using HTTPS and at least TLS1.1 or higher)
eventNotification.setUrl("my-webhook-url");
// DocuSign will retry on failure if this is set
eventNotification.setRequireAcknowledgment("true"); <---- the String "true"?????
// This would send the documents together with the event to the endpoint
eventNotification.setIncludeDocuments("false"); <---- the String "false"?????
// Allows you to see this in the DocuSign Admin Connect logs section
eventNotification.setLoggingEnabled("true"); <---- the String "true"?????
// send an event when the envelope is sent and completed.
EnvelopeEvent sentEvent = new EnvelopeEvent();
sentEvent.setEnvelopeEventStatusCode("Sent"); <---- the String "Sent"?????
sentEvent.setIncludeDocuments("false");
EnvelopeEvent completedEvent = new EnvelopeEvent();
completedEvent.setEnvelopeEventStatusCode("Completed"); <---- the String "Completed"?????
completedEvent.setIncludeDocuments("false");
eventNotification.setEnvelopeEvents(List.of(sentEvent, completedEvent));
ConnectEventData eventData = new ConnectEventData();
eventData.setVersion("restv2.1"); <---- surely these should be constants....right?
eventData.setFormat("json"); <----
eventNotification.setEventData(eventData);
envelope.setEventNotification(eventNotification);
this documentation led me to use Strings like envelope-completed instead of Completed....which cost me hours of trial and error.
Isn't the whole point of an SDK in a language like Java to be type safe? What am I missing here?
This is not an issue with the Java SDK, but with the swagger file that has definitions for various fields in the DocuSign eSignature REST API.
The swagger file defines many things as strings, even if they do not have to be strings. Changing this now would be a breaking change for many integrations and developers that rely on this (buggy or not) behavior.
This may be fixed in a new version of the API to avoid having backward compatibility issues.

How to check the published payload via receivecallback

I want to know how to subscribe and print the published payload to another device
I tried with sending the payload data which i used to publish by converting it to byte array for parameter of the function receivecallback

Azure functions Response Body is missing in Logic Apps

I am processing data from Event Hub. Whenever events are available in event hub series of azure functions are called sequentially to processes the data.
function A is using event data as input --> function B is using output of function A as an input and likewise 2 more functions are there.
Response body is missing in only one function (same, ex.: function B in picture) in some iterations.
Sometimes response body for one of the azure function is missing however response code is 200. I have logged the response body in azure function before returning the response and it(response body) is present in logs.
What can be the reason of not getting the response body.
In the attached image Function B is having this issue.
Update: After adding concurrency control to 1(So that it runs sequentially) issue is resolved however again after removing concurrency control issue is coming. What can be the issue ?
One of the workaround you can follow to resolve the above issue,
Make sure that all of the azure function has been created in the same region that might be the reason for not getting the request body for one function and getting for others.
Would suggest you to create Azure logic app and functions in the same region.
Another workaround is to provide the content type in your event hub to application/json if still having the same the try to set text/plain.
For more information please refer this MICROSOFT DOCUMENTATION| Receive and respond to inbound HTTPS requests in Azure Logic Apps
For the similar issue please refer this MS Q&A| Http Webhook Outputs does not have body content, only headers .

Logic App Send Message error with JSON

I'm using Logic App to send a message to a service bus on Azure. The logic app starts with a HTTP Request for the trigger which contains a JSON payload in the body. The 'Body' of the request is set as the Content of the Send Message action. Since the payload is JSON when posting I set the Content-Type to application/json. This generates an error on the Send Message action;
{"code":"InvalidTemplate","message":"Unable to process template language expressions in action 'Send_message.' inputs at line '1' and column '1221': 'The template language function 'encodeBase64' expects its parameter to be a string. The provided value is of type 'Object'. Please see https://aka.ms/logicexpressions#encodeBase64 for usage details.'."}
So tried changing the Content-Type to text/plain and it works? Is this a bug or should convert the JSON to a text value somehow before using it in the Send Message action?
Sending a message to service bus requires the message content to be base64 encoded. Since your content is a JSON, you would need to stringify it explicitly prior to encoding, i.e. use #encodeBase64(string(jsonContent))
Changing the content type to text/plain has the same effect, since in that case the content is treated as a string to begin with.

File not supported error while uploading profile image file to IBM Connections using REST API

I'm trying to upload a jpeg file for profile image using the Profiles REST API to IBM Connections_v5.0. I however get an error message "The type of the photo file you provided is not supported".
I'm however able to upload the same file directly using the Connections UI interface directly. I'm setting the MIME type correctly as "image/jpeg".
Also tried with GIF and PNG images but get the same error message.
Any pointers would be very helpful.
I'm just using FF restclient addon to fire a REST call. So basically doing a PUT on /profiles/photo.do?key=....
Content-Type is set as "image/jpeg" and the payload consists of the image data in binary (base 64) encoded.
The payload should just be the binary of the image, there is no need to Base64 encode it.
You should refer to Adding a Profile Photo
You need to use a Key (great stackoverflow post here)
If you know the key for a user's profile you can do the following:
key — This is generated by Connections itself during the population
process. It is used to define the users profile within the context of
Profiles and provides Connections with the ability to associate
content with a user when the users LDAP information has been altered.
It provides a separation of identity and helps facilitate user content
synchronization for Connections.
Once you have a key, you make the following request
URL: https://profiles.enterprise.example.com/profiles/photo.do?key=
b559403a-9r32-2c81-c99w-ppq8bb69442
METHOD: PUT
CONTENT-TYPE: image/png
input the binary content on the stream
you should be able to use "image/jpeg", "image/jpg", "image/png" or "image/gif"
If you have an error after the PUT method, you should add the SystemOut.log lines which are relevant.

Resources