I wanted to share a project that we have implemented in the Madrid Office, this project was developed by Juan Rueda and me.

This idea came after the posts from Daphne Ng and Barry Shang about how to interact with data using PI WebAPI and python.

 

 

Overview

 

The idea is to access to real-time data from the PI System, in order to trigger visible and audible alarms. Depending on the outputs that we get from the PI WebAPI queries the alarms would be one or others. We will be using basic Python coding and already built libraries from Python and Raspberry PI.

 

 

Setup

 

The data from the PI Data Archive is going to be contextualize in our PI AF Server in a Database.

This database is going to be indexed in a webserver with PI WebAPI.

The Raspberry PI will do the following tasks with a python script:

    1. Access to the data through PI WebAPI with URL.
    2. Parse and analyze the output from the URL.
    3. Control the relays and audio from the speakers.

 

Components

 

  • Raspberry PI rev.2 model B.
  • 8 modules relay (in our case we are only using 3 of them).
  • Tower Light.
  • Set of speakers.

 

 

The connection between the Raspberry PI, 8 modules Relay and the Tower Light is made by simple wiring. The signals are sent by the GPIO's from the Raspberry PI to the relays, then the relays will open or close in order to light up the tower.

 

 

Python Script

 

We are looking into using Cron task manager in order to run the python script at every reboot of the Raspberry PI

Another possibility would be to run it as a daemon service.

At the current time this script is being launch from a command window.

 

Libraries

 

We will be using the following libraries for the script. Keep in mind that the RPI.GPIO library needs to be downloaded from the Raspberry PI repository.

 

import urllib2, urllib

import ssl

import RPi.GPIO as GPIO

import time

import subprocess

import errno

 

Work arround to SSL certification issues.

 

In our case we were having some certificate issues with SSL, since this is not a production enviroment and it was giving us a little bit of trouble we decided to disable the SSL certificate validation.

In order to disable HTTPS certificate validation by default in Python versions 2.7.9 or above you could use this snippet of code.

 

from socket import error as SocketError

try:

    _create_unverified_https_context = ssl._create_unverified_context

except AttributeError:

    pass

else:

    # Handle target environment that doesn't support HTTPS verification

    ssl._create_default_https_context = _create_unverified_https_context

 

Variable definitions

 

Define our variables. urlSP and usrlEN. These are the url's that are going to get the data through the PIWebAPI webserver.

 

urlSP= 'https://madrid-cs2/piwebapi/streams/P0zF1wU3Q-KUudBKNuK3HsAAU8oCAAU1RBUkxJR0hUXEZSQV9DSVNDT0NDX1NQQU5JU0hfQ0FMTFNXQUlUSU5H/value'

urlEN= 'https://madrid-cs2/piwebapi/streams/P0zF1wU3Q-KUudBKNuK3HsAA_wEBAAU1RBUkxJR0hUXEZSQV9DSVNDT0NDX0VOR19DQUxMU1dBSVRJTkc/value'

 

In the image below you can find the output of a query to PI WebAPI with a URL like the above. We are only going to use the result of  value (i.e "0"), in our case. You could also get the timestamp.

 

 

Then we have to setup the different pins of the Raspberry PI in order to send signals to the relays. Each output pin is assigned to a light.

 

GPIO.setmode(GPIO.BCM)

GPIO.setwarnings(False)

GPIO.setup(21,GPIO.OUT) # Yellow light

GPIO.setup(16,GPIO.OUT) # Green light

GPIO.setup(20,GPIO.OUT) # Red Light

 

"Calling" Function.

 

In order to parse the information coming from PI WebAPI and to check if there is connection to the server with no errors. We are going to use the "calling" function. This function is going to return a value that is going to be analyze in the main code by IF statements.

 

def calling(url):

 

The first thing would be to open a connection with HTTPS using “svc-chiquetetes” user through basic authentication.

 

    password_manager = urllib2.HTTPPasswordMgrWithDefaultRealm()

    password_manager.add_password(None, url, 'svc-chiquetetes', <password>)

    auth = urllib2.HTTPBasicAuthHandler(password_manager) # create an authentication handler

    opener = urllib2.build_opener(auth) # create an opener with the authentication handler

    urllib2.install_opener(opener) # install the opener...

    req_headers = {'Content-Type': 'application/json'}

    request = urllib2.Request(url, headers = req_headers)

 

Test if there is any possible HTTP or URL errors. We are doing this to avoid the script to stop. If there is any error the function will return 100.

 

   try:

        response = urllib2.urlopen(request).read()

    except urllib2.HTTPError, err:

        return ('100')

    except urllib2.URLError, err:

        return ('100')

 

Parse the output of the URL in order to get the data from the "value".

 

   parse=response.split(",")

    parse1= parse[1]

    parse2=parse1.split(":")

    call=parse2[1]

   return call

 

This is the main body of the code in which we will calling to the functions and analyzing the data coming from them. The main body is always running in an infinite loop.

Creation of variables SP and EN that would be getting the value of the attribute.

 

Main corp

 

while 1:

   SP=calling(urlSP)

   EN=calling(urlEN)

 

Analisys of the data coming from the functions.

First of all we will check if the connection to the webserver is not in error, or there is issues reading the data from the URL.

 

    if SP!='100' or EN!='100':

 

If the value from the first call SP is not equal to 0 then the red light will turn on and in this case also a sound will be played.

 

        if SP!='0':

            GPIO.output(20,1)

            subprocess.call(["aplay","Sound.wav"])       

        else:

            GPIO.output(20,0)

 

If the value from the first call EN is not equal to 0 then the yellow light will turn on.

 

        if EN!='0':

            GPIO.output(21,1)

        else:

            GPIO.output(21,0)

 

If both of the values from SP and EN are equal to zero then  only the green light will be on.    

 

        if SP=='0' and EN=='0':

            GPIO.output(16,1)

        else:

            GPIO.output(16,0)

 

If there is a connection error or issues reading the data from the URL all the lights will turn on.

 

    else:

         GPIO.output(21,1)

         GPIO.output(20,1)

         GPIO.output(16,1)

 

Conclusion

 

This project is made to show the possibilities that PI System and the Raspberry PI can bring.

The code could be improved in different ways in order to gain in performance, but it gives a good idea of what you can do with simple coding and a Raspberry PI.

You could make the code as complex as you need in order to for example make the lights blink or use light towers with more colors.