Using the Datonis Python SDK

From Datonis
Jump to: navigation, search
Datonis Documentation Home > Build your connected Thing > Using Datonis Python SDK

Download SDK binaries

You can download the Aliot-SDK-Examples zip file from github. Extract the zip file in your local directory. Python folder contains a python_agent. zip and sample.py file.

First set the python path to point python_agent.zip file

Set python path

export PYTHONPATH=$PYTHONPATH:/<path-to-folder>/python_agent.zip

Aliot (Altizon Internet Of Things) agents are embedded agents sitting at an endpoint that stream data to Datonis. To understand how an Aliot Agent works, we will be walking through the sample agent file in detail. Firstly we require following files to be imported in your sample code.

Import

import json
import logging
import math
import random
import sys
import time
import os

Configure Datonis Gateway

You will then need to configure the agent to send data securely to Datonis. The following lines of code achieve this. Since the Aliot agent can act as a gateway for multiple Things, the SDK provides a gateway object that can hold the information about multiple Things.

The GatewayConfig function takes access_key, secret_key and protocol as parameter. Add the access_key and secret_key obtained by downloading the key-pair in the GatewayConfig function. The protocol can be 'http', 'https', 'mqtt' or 'mqtts'. If you wish to use bidirectional data transfer, please use mqtt.

Construct a gateway that helps us send various types of events to Datonis. To test the connection call connect function on gateway.

Gateway Configuration

gateway_config = GatewayConfig(<access_key>, <secret_key>, <protocol>,[optional])
gateway = gateway_config.create_gateway()
if gateway.connect() == False:
    logging.error("Failed to connect to Datonis")
else:
    logging.info("Successfully connected to Datonis")

Create Thing object and register your Thing

After the device is able to connect to Datonis, add thing details of the thing whose data you want to send. Things detail include thing_key, thing_name and thing_description. If you wish to use MQTT/MQTTS protocol set bi_directional as true and add instruction handler if you require instruction execution support.

Try to register your Thing, if registration is successfully continue further else verify your thing_key from Datonis portal.

Add Thing Details

thing = Thing()
thing.thing_key = <thing_key>
thing.name = 'LivingRoom'
thing.description = 'The living room temperature and humidity device.'

# Uncomment lines below if you are using MQTT/MQTTs and require instruction execution support
# thing.bi_directional = True
# gateway.instruction_handler = my_instruction_handler
 
if gateway.thing_register(thing) == False:
    logging.error("Failed to register thing")
    sys.exit(1)
else:
    logging.info("Registered thing: " + thing.name + " with metadata: " + str(thing.data))

Sending Data

Create a hash of data as metric name and metric value. In our example, metric name is 'temperature' and 'humidity' and its corresponding value. If you want to send waypoint data (data related to location of Thing) create a array named waypoint and insert latitude and longitude information.

Then create thing event by calling aliot_util.create_thing_event() function. create_thing_event function basically takes 4 parameters, thing object, data hash, waypoint array and timestamp. The thing object created previously is a mandatory parameter while you wish to whose what data you want to send and set rest parameters to None. Your can choose to send timestamp, default it will send current time.

Sending Data

data = {'temperature': <temperature_value>, 'humidity': <humidity_value>}
waypoint = [<latitude>, <longitude>]
thing_event = aliot_util.create_thing_event(thing, data, waypoint, int(time.time()*1000))
if gateway.thing_event(thing_event) == True:
    logging.error("Sent event data for thing: " + str(thing_event))
else:
    logging.error("Failed to send event data for thing: " + str(thing_event))

Sending Heartbeat

You can also send heartbeat messages to Datonis. These messages does not send any data but assures Datonis that your Thing is still connected.

Sending heartbeat

if gateway.thing_heartbeat(thing) == False:
    logging.warn("Could not send hearbeat for thing: " + thing.name)
else:
    logging.info("Heartbeat sent for thing: " + thing.name)

Sending Alerts

Things can also send alerts to Datonis, which is not an event data but data send during abnormal situation such as a thermometer reporting reading that are out of permissible range. The alert function takes thing_key, alert message as string, alert level as integer and alert_data as hash. Alert message can be any user defined message which states the cause of alert.

Alert level can only be of four types:

  1. Info : value = 0
  2. Warning : value= 1
  3. Error : value = 2
  4. Critical : value = 3

Alert data has to be a hash representing a key and value pair.

Sending Alerts

if gateway.alert(thing.thing_key, <message>, <alert_level>, {'temperature':'98'}) == True:
    logging.info('Successfully sent ' + <message> + ' alert to datonis')
else:
    logging.warn('Failed to send ' + <message> + ' alert to datonis')

Instruction Handler (Bi-directional communication)

When using the MQTT/MQTTS protocols for communication, agents can not only send events to the Datonis platform, but also receive instructions from the platform. These instructions can be interpreted by the agent to perform necessary actions. E.g. Shutting down a machine/device attached to an agent, calibrating a thing based on the errors in its readings etc. The following snippet handles an instruction sent by the Datonis platform and sends back an acknowledgement.

Instruction Handler

def my_instruction_handler(gateway, timestamp, thing_key, alert_key, instruction):
    logging.info('Successfully handled incoming instruction: ' + json.dumps(instruction))
    if gateway.instruction_ack(alert_key, 'Successfully handled instruction', 1, {'execution_status':'success'}):
        logging.info('Sent instruction execution ACK back to datonis')
    else:
        logging.warn('Could not send instruction execution ACK back to datonis')