Reputation: 1
I'm trying to send messages from a sensor (temperature, humidty, pressure) to the Azure IoT Hub with use of a raspberry pi zero and a python script. I reached the point where i succesfully deliver data to the IoT Hub and also the blob storage. But when I check the json-Files on the storage container they have a completly different content and don't include any of my sensor data. Afterwards it is my goal to check the stored data with another python script.
They look something like this:
{"EnqueuedTimeUtc":"2021-06-21T16:24:45.6680000Z","Properties":{},"SystemProperties":{"connectionDeviceId":"RaspberryPi","connectionAuthMethod":"{"scope":"device","type":"sas","issuer":"iothub","acceptingIpFilterRule":null}","connectionDeviceGenerationId":"637555519600003402","enqueuedTime":"2021-06-21T16:24:45.6680000Z"},"Body":"eyJ0ZW1wZXJhdHVyZSI6IDMxLjIyLCAicHJlc3N1cmUiOiA5NzEuODA3ODE4NTk0NTY0NCwgImh1bWlkaXR5IjogNDIuNDUzMjg4NTAwMjE3ODgsICJ0aW1lIjogIjIwMjEtMDYtMjEgMTc6MjQ6NDQuNzgyODYyIn0="}
The Code i use for getting the sensor data and sending them to the IoT Hub looks like this:
import datetime
import json
import time
import smbus
import Adafruit_DHT
from ctypes import c_short
from ctypes import c_byte
from ctypes import c_ubyte
from azure.iot.device import IoTHubDeviceClient, Message
DEVICE = 0x76
CONNECTION_STRING = "HostName=...;DeviceId=...;SharedAccessKey=..."
bus = smbus.SMBus(1)
def getShort(data, index):
return c_short((data[index + 1] << 8) + data[index]).value
def getUShort(data, index):
return (data[index + 1] << 8) + data[index]
def getChar(data, index):
result = data[index]
if result > 127:
result -= 256
return result
def getUChar(data, index):
result = data[index] & 0xFF
return result
def readBME280ID(addr=DEVICE):
REG_ID = 0xD0
chip_id, chip_version = bus.read_i2c_block_data(addr, REG_ID, 2)
return chip_id, chip_version
def readBME280All(addr=DEVICE):
REG_DATA = 0xF7
REG_CONTROL = 0xF4
REG_CONFIG = 0xF5
REG_CONTROL_HUM = 0xF2
REG_HUM_MSB = 0xFD
REG_HUM_LSB = 0xFE
OVERSAMPLE_TEMP = 2
OVERSAMPLE_PRES = 2
MODE = 1
OVERSAMPLE_HUM = 2
bus.write_byte_data(addr, REG_CONTROL_HUM, OVERSAMPLE_HUM)
control = OVERSAMPLE_TEMP << 5 | OVERSAMPLE_PRES << 2 | MODE
bus.write_byte_data(addr, REG_CONTROL, control)
cal1 = bus.read_i2c_block_data(addr, 0x88, 24)
cal2 = bus.read_i2c_block_data(addr, 0xA1, 1)
cal3 = bus.read_i2c_block_data(addr, 0xE1, 7)
dig_T1 = getUShort(cal1, 0)
dig_T2 = getShort(cal1, 2)
dig_T3 = getShort(cal1, 4)
dig_P1 = getUShort(cal1, 6)
dig_P2 = getShort(cal1, 8)
dig_P3 = getShort(cal1, 10)
dig_P4 = getShort(cal1, 12)
dig_P5 = getShort(cal1, 14)
dig_P6 = getShort(cal1, 16)
dig_P7 = getShort(cal1, 18)
dig_P8 = getShort(cal1, 20)
dig_P9 = getShort(cal1, 22)
dig_H1 = getUChar(cal2, 0)
dig_H2 = getShort(cal3, 0)
dig_H3 = getUChar(cal3, 2)
dig_H4 = getChar(cal3, 3)
dig_H4 = (dig_H4 << 24) >> 20
dig_H4 = dig_H4 | (getChar(cal3, 4) & 0x0F)
dig_H5 = getChar(cal3, 5)
dig_H5 = (dig_H5 << 24) >> 20
dig_H5 = dig_H5 | (getUChar(cal3, 4) >> 4 & 0x0F)
dig_H6 = getChar(cal3, 6)
wait_time = 1.25 + (2.3 * OVERSAMPLE_TEMP) + ((2.3 * OVERSAMPLE_PRES) + 0.575) + ((2.3 * OVERSAMPLE_HUM) + 0.575)
time.sleep(wait_time / 1000)
data = bus.read_i2c_block_data(addr, REG_DATA, 8)
pres_raw = (data[0] << 12) | (data[1] << 4) | (data[2] >> 4)
temp_raw = (data[3] << 12) | (data[4] << 4) | (data[5] >> 4)
hum_raw = (data[6] << 8) | data[7]
var1 = ((((temp_raw >> 3) - (dig_T1 << 1))) * (dig_T2)) >> 11
var2 = (((((temp_raw >> 4) - (dig_T1)) * ((temp_raw >> 4) - (dig_T1))) >> 12) * (dig_T3)) >> 14
t_fine = var1 + var2
temperature = float(((t_fine * 5) + 128) >> 8);
var1 = t_fine / 2.0 - 64000.0
var2 = var1 * var1 * dig_P6 / 32768.0
var2 = var2 + var1 * dig_P5 * 2.0
var2 = var2 / 4.0 + dig_P4 * 65536.0
var1 = (dig_P3 * var1 * var1 / 524288.0 + dig_P2 * var1) / 524288.0
var1 = (1.0 + var1 / 32768.0) * dig_P1
if var1 == 0:
pressure = 0
else:
pressure = 1048576.0 - pres_raw
pressure = ((pressure - var2 / 4096.0) * 6250.0) / var1
var1 = dig_P9 * pressure * pressure / 2147483648.0
var2 = pressure * dig_P8 / 32768.0
pressure = pressure + (var1 + var2 + dig_P7) / 16.0
humidity = t_fine - 76800.0
humidity = (hum_raw - (dig_H4 * 64.0 + dig_H5 / 16384.0 * humidity)) * (
dig_H2 / 65536.0 * (1.0 + dig_H6 / 67108864.0 * humidity * (1.0 + dig_H3 / 67108864.0 * humidity)))
humidity = humidity * (1.0 - dig_H1 * humidity / 524288.0)
if humidity > 100:
humidity = 100
elif humidity < 0:
humidity = 0
return temperature / 100.0, pressure / 100.0, humidity
def awaitConnection():
url = 'http://www.google.de'
content = None
while content == None:
try:
response = urllib.request.urlopen(url)
content = response.read()
except:
continue
def iothub_client_init():
client = IoTHubDeviceClient.create_from_connection_string(CONNECTION_STRING)
return client
def main():
print("Ctrl-C zum Beenden")
while True:
try:
client = iothub_client_init()
print("Sending data to IoT Hub, press Ctrl-C to exit")
while True:
temperature, pressure, humidity = readBME280All()
msg={"temperature":temperature,"pressure":pressure,"humidity":humidity,"time":str(datetime.datetime.now())}
message = Message(json.dumps(msg))
print("Nachricht senden: {}".format(message))
client.send_message(message)
print("Nachricht erfolgreich an IoT-Hub gesendet")
time.sleep(6)
except KeyboardInterrupt:
print("IoTHubClient stopped")
if __name__ == "__main__":
main()
Since I'm new to this whole thing I'm thankful for any kind of advice.
Upvotes: 0
Views: 326
Reputation: 1
Thanks for the fast reply and the annotation with the base64 format. It really helped me.
I checked the setting for Message Routing of my Iot Hub. As shown in the picture the route of the Storage Endpoint the system properties include contentType application/json and contentEncoding utf-8 already. But the data format in the storage stays the same. Am I missing something?
And is there any way to get rid of the various data which is in front of every base24-data?
Upvotes: 0
Reputation: 8245
have a look at the document, where is described, that:
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.
Upvotes: 1
Reputation: 4448
I haven’t worked with this, but your message body is a base64 encoded JSON payload, presumably the one you’re expecting to see:
eyJ0ZW1wZXJhdHVyZSI6IDMxLjIyLCAicHJlc3N1cmUiOiA5NzEuODA3ODE4NTk0NTY0NCwgImh1bWlkaXR5IjogNDIuNDUzMjg4NTAwMjE3ODgsICJ0aW1lIjogIjIwMjEtMDYtMjEgMTc6MjQ6NDQuNzgyODYyIn0=
Is encoded version of this:
{
"temperature": 31.22,
"pressure": 971.8078185945644,
"humidity": 42.45328850021788,
"time": "2021-06-21 17:24:44.782862
}
This is likely due to how the Message type works, wrapping the body of the message in an envelope.
Upvotes: 0