CONOCIENDO LAS APIS DE SOFIA 2 – API Node.js

Entre las novedades de la Release 2.8.0 de SOFIA2 (https://about.sofia2.com/2014/05/30/publicada-release-2-8-0-de-sofia2/) tenemos el API Node.js

Este API nos permite el desarrollo de aplicaciones cliente para SOFIA2 (KPs) programados en Node.js (http://nodejs.org/). El API utiliza el Gateway MQTT para conectar con la plataforma, lo que permite mantener una conexión bidireccional entre el KP y el SIB, disponiendo de este modo de todo el juego de operaciones SSAP incluyendo las suscripciones.

El API Node.js para SOFIA2 está disponible para su descarga desde http://sofia2.com/desarrollador.html:

La descarga consiste en un fichero ZIP que incluye las librerías necesarias para crear un KP que conecte con la plataforma, así como ejemplos de utilización de las distintas operaciones:

Una vez descomprimido tenemos la siguiente estructura:

Donde:

· XXTEA.js y base64.js: Librerías utilizada por el API para cifrar los mensajes SSAP mediante el algoritmo XXTEA (http://unpocodejava.wordpress.com/2013/06/13/que-es-el-algoritmo-xxtea/).

· SSAPMessageGenerator.js: Librería de generación de mensajes SSAP. Abstrae al programador de la construcción de los mensajes SSAP mediante funciones especificas para cada tipo de mensaje SSAP. En el siguiente post https://about.sofia2.com/2014/04/14/conociendo-el-protocolo-de-interoperabilidad-de-sofia2-ssap/ se detalla el protocolo de mensajería SSAP, cada uno de los mensajes y sus atributos. Esta librería proporciona las siguientes funciones para construir mensajes SSAP:

o generateJoinByTokenMessage(token, instance): Genera un mensaje SSAP de tipo JOIN.

o generateLeaveMessage(sessionKey): Genera un mensaje SSAP de tipo LEAVE.

o generateInsertMessage (data, ontology, sessionKey): Genera un mensaje SSAP de tipo INSERT en lenguaje Nativo de la BDTR

o generateInsertWithQueryTypeMessage (data, ontology, queryType, sessionKey): Genera un mensaje SSAP de tipo INSERT pudiendo utilizar los lenguajes Nativo y SQLLIKE.

o generateUpdateMessage (data, query, ontology, sessionKey): Genera un mensaje SSAP de tipo UPDATE en lenguaje Nativo de la BDTR.

o generateUpdateWithQueryTypeMessage (data, query, ontology, queryType, sessionKey): Genera un mensaje SSAP de tipo UPDATE pudiendo utilizar los lenguajes Nativo y SQLLIKE.

o generateDeleteMessage (query, ontology, sessionKey): Genera un mensaje SSAP de tip DELETE en lenguaje Nativo de la BDTR.

o generateDeleteWithQueryTypeMessage (query, ontology, queryType, sessionKey): Genera un mensaje SSAP de tipo DELETE, pudiendo utilizar los lenguajes Nativo y SQLLIKE.

o generateQueryMessage (query, ontology, sessionKey): Genera un mensaje de tipo SSAP de tipo QUERY utilizando los criterios en Nativo de la BDTR

o generateQueryWithQueryTypeMessage (query, ontology, queryType, queryParams, sessionKey): Genera un mensaje SSAP de tipo QUERY, pudiendo utlizar los lenguajes Nativo y SQLLIKE, o bien utilizar una consulta predefinida en el SIB.

o generateSubscribeMessage (suscription, ontology, refresh, sessionKey): Genera un mensaje SSAP de tipo SUBSCRIBE, utilizando los criterios en lenguaje Nativo de la BDTR.

o generateSubscribeWithQueryTypeMessage (suscription, ontology, queryType, refresh, sessionKey): Genera un mensaje SSAP de tipo SUBSCRIBE, pudiendo utilizar una sentencia los lenguajes Nativo y SQLLIKE, o bien utilizar una consulta predefinida en el SIB.

o generateUnsubscribeMessage (subscriptionId, ontology, sessionKey): Genera un mensaje SSAP de tipo UNSUBSCRIBE.

· kpMQTT.js: Librería de comunicación con el SIB, permite al programador conectarse al SIB y enviar y recibir mensajes SSAP de manera transparente, sin necesidad de tratar aspectos relativos al protocolo de comunicación. Proporciona las siguientes funciones:

o KpMQTT(): Constructor

o connect (host, port): Establece una conexión MQTT física con el Gateway MQTT del SIB

o disconnect (): Cierra una conexión MQTT física con el Gateway MQTT del SIB.

o isConnected (): Indica si existe una conexión física activa

o send (ssapMessage, subscriptionCallback): Permite enviar un mensaje SSAP al SIB y recibir su respuesta de manera síncrona. El parámetro subscriptionCallback es opcional, y solo se utiliza al enviar un mensaje SSAP SUBSCRIBE para registra la función callback a través de la que recibirán los mensajes INDICATION (notificaciones de suscripción).

o sendCipher (ssapMessage, subscriptionCallback): Igual que send, solo que cifra el mensaje SSAP mediante el algoritmo XXTEA y una clave de cifrado.

o setCipherKey(cipherKey): Establece el valor de la clave de cifrado XXTEA.

o json2Object (msg): Utilidad para convertir una cadena en formato JSON en un objeto JSON.

o object2Json (msg): Utilidad para convertir un objeto JSON en su cadena equivalente.

· samples: Carpeta con ejemplos de utilización. Contiene ficheros mostrando ejemplos funcionales de todos los mensajes SSAP.

· mqtt: Cliente MQTT utilizado por el API.

· node_modules: Modulos utilizados por el API. Esta carpeta puede borrarse si se instalan localmente los módulos necesarios mediante el comando npm install <modulo> a medida que son demandados por Node.js

A continuación vamos a ver cómo utilizar el API siguiendo uno de los ejemplos proporcionados. En concreto seguiremos el ejemplo que podemos encontrar en samples/subscribe.js:

En primer lugar, es necesario importar las librerías del API que vamos a utilizar. En concreto kpMQTT para enviar y recibir mensajes con el SIB, SSAPMessageGenerator para generar los mensajes SSAP, y un módulo que utiliza el API internamente, waitfor


var kp = require('../kpMQTT');

var ssapMessageGenerator = require("../SSAPMessageGenerator");

var wait = require("../node_modules/wait.for/waitfor");

Lo siguiente es crear la conexión física con el SIB. Conectaremos con el despliegue en cloud de SOFIA2 en sofia2.com:


var miKp = new kp.KpMQTT();

//Connect to SIB

miKp.connect('sofia2.com', 1880);

A continuación, ya en la función main del programa generamos un mensaje SSAP de tipo JOIN y lo enviamos al SIB para autenticarnos con nuestro token e iniciar una sesión lógica mediante una sessionkey devuelta por el SIB:


// JOIN Message generation

var ssapMessageJOIN = ssapMessageGenerator.generateJoinByTokenMessage('e5e8a005d0a248f1ad2cd60a821e6838', 'KPTestTemperatura:KPTestTemperatura01');

//Send message to SIB

var joinResponse = miKp.send(ssapMessageJOIN);

//Process JOIN message

var joinBody=miKp.json2Object(joinResponse.body);

if(joinBody.ok){

sessionKey = joinResponse.sessionKey;

console.log('Session created with SIB with sessionKey: ' + sessionKey);

El siguiente paso será suscribirse a una consulta en el SIB, para ello, generaremos y enviaremos un mensaje de tipo SUBSCRIBE, pero previamente es necesario declarar la función que hará de callback para recibir las notificaciones de suscripción desde el SIB, es decir, vamos a declarar la función a través de la cual, el SIB nos enviará mensajes de tipo SSAP INDICATION con las notificaciones de nuestra suscripción. Para ello, fuera de la función main, declaramos esta función callback, que recibirá por argumentos el mensaje de tipo INDICATION:


//Listener function to receive INDICATION messages for subscriptions notifications

function indicationMessageCallback(data){

wait.launchFiber(indicationMessage, data);

}

Como vemos, esta función lo que hace es invocar a otra función llamada indicationMessage lanzándola en un hilo, esto es debido a que para poder gestionar el mecanismo petición-respuesta síncronos del protocolo SSAP, las peticiones al SIB tienen que ser lanzadas en un hilo. En el ejemplo, lo que hacemos una vez recibida la notificación en esta función callback, enviamos nuevos mensajes al SIB para desuscribirnos mediante un mensaje SSAP UNSUBSCRIBE y para cerrar la sesión lógica mediante un mensaje SSAP LEAVE.

De este modo, una vez definida la función callback para recibir notificaciones, procedemos a generar un mensaje SSAP de tipo SUBSCRIBE, indicando una sentencia de suscripción, y procedemos a enviarlo al SIB registrando la función callback en la propia instrucción send:


// SUBSCRIBE message generation

var ssapMessageSUBSCRIBE =ssapMessageGenerator.generateSubscribeWithQueryTypeMessage('Select * from TestSensorTemperatura where Sensor.measure=25', 'TestSensorTemperatura', 'SQLLIKE', 0, sessionKey);

var subscribeResponse = miKp.send(ssapMessageSUBSCRIBE, indicationMessageCallback);

var subscribeBody=miKp.json2Object(subscribeResponse.body)

if(subscribeBody.ok){

console.log('Subscribed to SIB with SubscriptionId: '+subscribeBody.data);

subsId=subscribeBody.data;

Una vez suscritos, lo siguiente que hacemos es enviar un mensaje SSAP de tipo INSERT, con una instancia de ontología, que cumple la sentencia de suscripción. De este modo, el SIB notificará a nuestro KP dicha esta nueva instancia de ontología, invocando a la función callback que registramos en el punto anterior para que podamos procesar la instancia:


// INSERT message generation

var ontologyInstance = "{ \"Sensor\": { \"geometry\": { \"coordinates\": [ 40.512967, -3.67495 ], \"type\": \"Point\" }, \"assetId\": \"S_Temperatura_00066\", \"measure\": 25, \"timestamp\": { \"$date\": \"2014-04-29T08:24:54.005Z\" } } }";

var ssapMessageINSERT = ssapMessageGenerator.generateInsertMessage(ontologyInstance, 'TestSensorTemperatura', sessionKey);

var insertResponse = miKp.send(ssapMessageINSERT);

var insertBody=miKp.json2Object(insertResponse.body)

if(insertBody.ok){

console.log('Ontology Instance inserted in the SIB with ObjectId: '+insertBody.data);

}else{

console.log('Error inserting Ontology Instance in the SIB');

}

Como ya hemos comentado, la función callback que recibe el mensaje INDICATION de notificación a la suscripción, lanza otra función en un nuevo hilo. En esta función lo que hacemos es mostrar por consola el mensaje recibido, y procedemos es a desuscribirnos del SIB mediante un mensaje SSAP UNSUBSCRIBE indicando el id de suscripción recibido en la respuesta del mensaje SSAP SUBSCRIBE. Finalmente cerramos la sesión SSAP enviando un mensaje SSAP LEAVE y cerramos la conexión física MQTT mediante la instrucción disconnect:


function indicationMessage(data){

console.log("Indication Message Received: "+miKp.object2Json(data));

// UNSUBSCRIBE message generation

var ssapMessageUNSUBSCRIBE=ssapMessageGenerator.generateUnsubscribeMessage(subsId, 'TestSensorTemperatura', sessionKey);

var unsubscribeResponse = miKp.send(ssapMessageUNSUBSCRIBE);

var unsubscribeBody=miKp.json2Object(unsubscribeResponse.body);

if(unsubscribeBody.ok){

console.log('Unsubscribed from SIB');

}else{

console.log('Error unsubscribing from SIB');

}

// LEAVE Message generation

var ssapMessageLEAVE=ssapMessageGenerator.generateLeaveMessage(sessionKey);

//Send message to SIB

var leaveResposne = miKp.send(ssapMessageLEAVE);

var leaveBody=miKp.json2Object(leaveResposne.body)

if(leaveBody.ok){

console.log('Session closed with SIB');

}else{

console.log('Error closing session with SIB');

}

//Disconnect from SIB

miKp.disconnect();

}

De este modo, si ejecutamos el ejemplo, vemos como se cumplen los pasos que hemos mostrado:

1. Se envía el mensaje SSAP JOIN para crear una sesión lógica, recibiéndose una sessionkey.

2. Se envía el mensaje SSAP SUBSCRIBE suscribiéndose a la sentencia mostrada y recibiendo el identificador de la suscripción.

3. Se Inserta una Instancia de ontología que cumple con los criterios de la sentencia de la suscripción, recibiéndose el Identificador de la instancia en BDTR.

4. Se recibe la notificación desde el SIB a través de un mensaje SSAP INDICATION

5. Se desuscribe de la sentencia utilizando el identificador de la suscripción mediante un mensaje SSAP UNSUBSCRIBE

6. Cierra la sesión lógica SSAP mediante un mensaje SSAP LEAVE indicando la sessionkey.

CONOCIENDO LAS APIS DE SOFIA 2 – API Node.js

Responder

Introduce tus datos o haz clic en un icono para iniciar sesión:

Logo de WordPress.com

Estás comentando usando tu cuenta de WordPress.com. Cerrar sesión / Cambiar )

Imagen de Twitter

Estás comentando usando tu cuenta de Twitter. Cerrar sesión / Cambiar )

Foto de Facebook

Estás comentando usando tu cuenta de Facebook. Cerrar sesión / Cambiar )

Google+ photo

Estás comentando usando tu cuenta de Google+. Cerrar sesión / Cambiar )

Conectando a %s