mastering the iot with javascript and c++ - günter obiltschnig

36
Mastering The IoT With JavaScript And C++ Günter Obiltschnig Applied Informatics Software Engineering GmbH [email protected] @obiltschnig, @macchina_io

Upload: withthebest

Post on 15-Apr-2017

133 views

Category:

Technology


3 download

TRANSCRIPT

Page 1: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Mastering The IoT With JavaScript And C++

Günter Obiltschnig Applied Informatics Software Engineering GmbH [email protected] @obiltschnig, @macchina_io

Page 2: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

About Me

hard-core C++ developer (20+ years), who also likes JavaScript

“full stack++”, embedded, hardware to web frontend + cloud

POCO C++ Libraries (2004)

Applied Informatics GmbH (2006)

my-devices.net (2010)

AIS Radar for iOS (2011)

macchina.io (2013)

Page 3: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

m .ioacchina|‘makkina| – A modular open source toolkit for building

embedded IoT applications that connect sensors, devices and cloud services.

Page 4: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

IoT Gateway

my-devices.netCloud Services

AirVantage, Amazon, Bluemix, Carriots, etc.

HTTP(S), REST MQTT

Remote Access my-devices.net

device apps local “business logic”

web services web visualization

database discoverability

Mobile/Web Clients

Devices/Sensor Networks

CoAP, IEEE 802.15.4, Modbus, USB, Bluetooth LE,

RS-232

Page 5: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

POCOC++ LIBRARIES

platform abstraction, multithreading, XML and JSON processing, filesystem access,stream, datagram and multicast sockets, HTTP server and client, crypto, SSL/TLS, etc.

Remoting serialization, remote methods and events, IPC

Open Service Platform dynamic module system service registry web application server user authentication/authorization

Platform

JavaScript V8 JavaScript engine and C++ bindings/bridging

Devices and Sensors Sensors, Serial Port, GNSS/GPS, Accelerometer, I/O, …

Protocols MQTT, CoAP, Modbus, Bluetooth LE, XBee, …

Services WebEvent, DeviceStatus, NetworkEnvironment, …

WebUI Login, Launcher, Bundles, Playground, etc.

IoT Components

Page 6: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

> open source (Apache 2.0 License)

> built in C++ for best performance and efficiency (JavaScript for parts of web interface)

> modular and extensible

> mature, proven codebase: POCO C++ Libraries, Google V8, Eclipse Paho, SQLiteAngularJS, jQuery, OpenLayers, Ace (text editor),+ Applied Informatics OSP and Remoting frameworks

> C++-to-JavaScript bridge

> Raspberry Pi, Beaglebone, Edison, RED, MangOH, etc.

> prototype on Linux or OS X host, easily deploy to device

> web interface with JavaScript editor

Page 7: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Why JavaScript?

> Popular and widely known*

> Standardized

> Easy to integrate into an existing framework

> Multiple embeddable engines available

> Good performance (for a scripting language)

> I like it ;-)

* but not necessarily universally liked

Page 8: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Sensors & Devices Protocols Cloud Services

Temperature, Ambient Light, Humidity, Air Pressure, etc.

HTTP, HTTPS AirVantage

I/O, LED, Trigger, Rotary Encoder

MQTT Bluemix

Accelerometer CoAP* Twitter

GNSS/GPS WebEvent Amazon IoT

Barcode Reader, RFID* WebTunnel Twilio (SMS)

XBee (ZigBee, IEEE 802.15.4) XBee API my-devices.net

TI SensorTag Bluetooth LE any with MQTT API

Serial Port Modbus any with HTTP/REST API

* planned

Page 9: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Pro Users and Device Manufacturers

> add device specific APIs

> make devices programmable in JavaScript for partners or end users

> device specific app store (sell additional software features)

> additional frameworks (Shell, UPnP, Remoting SOAP and JSON-RPC)

> customizable web user interface

> improved user authentication and authorization

> signed bundles

> pro support

Page 10: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Usage Examples

> Building Automation

> Vehicle Telematics/Connected Cars

> Energy Manager(photovoltaics and battery controller)

> Industrial Internet of Things Platform

Page 11: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Demo

Page 12: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Inside macchina.io

Page 13: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

POCOC++ LIBRARIES

platform abstraction, multithreading, XML and JSON processing, filesystem access,stream, datagram and multicast sockets, HTTP server and client, crypto, SSL/TLS, etc.

Remoting serialization, remote methods and events, IPC

Open Service Platform dynamic module system service registry web application server user authentication/authorization

Platform

JavaScript V8 JavaScript engine and C++ bindings/bridging

Devices and Sensors Sensors, Serial Port, GNSS/GPS, Accelerometer, I/O, …

Protocols MQTT, CoAP, Modbus, Bluetooth LE, XBee, …

Services WebEvent, DeviceStatus, NetworkEnvironment, …

WebUI Login, Launcher, Bundles, Playground, etc.

IoT Components

Page 14: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

POCO C++ Libraries

> Started 2004

> ~300.000 LOC

> 1000+ classes

> on GitHub since 2012 1730+ stars640+ forks40-200 clones/day

> ~100 contributors

> Boost License

> http://pocoproject.org

POSIX, WIN32, other (RT)OS API

Foundation

C++ and C Standard LibrariesAp

plic

atio

n

Zip

Net

Crypto

Data

SQLite

ODBC

MySQL

NetSSL

Util

Tools, Utilities and additional Libraries

XML JSON

Page 15: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

V8

> Google’s JavaScript Engine

> Used by Chrome/Chromium and node.js

> C++ library, (reasonably) easy to integrate and to extend

> Compiles JavaScript to native code (x86, ARM, MIPS)

> Great performance

> BSD License

Page 16: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Remoting

> Similar to .NET Remoting or Java RMI, but for C++

> Code generator parses annotated C++ header files and generates code(serialization/deserialization, method dispatching, helpers)

> Supports different transports (binary TCP, SOAP, JSON-RPC)

> Used for automatic C++-to-JavaScript bridging

> Will also be used to implement sandbox mechanism

Page 17: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Open Service Platform (OSP)

> Inspired by OSGi, but for C++ (also JavaScript, Python, etc.)

> Dynamic module system based on bundles(Zip files with metadata, shared libs, other files)

> Dependency and lifecycle management

> Services and service registry

> Web Server

POCO Core Libraries(Foundation, XML, Util, Net)

OperatingSystem

API

Std. C/C++ LibrariesService Registry

Portable Runtime Environment

Life

Cyc

le

Man

agem

ent

Bundle Managem

ent

Stand

ard

Service

s

Bundles

install, resolve, start, stop and uninstall bundles

provide services to other bundles and find services

provided by other bundles

manage bundle versionsand dependencies

web server, web- and console-

based management, user authentication and authorization,

preferences, etc.

application-specific functionality and services

Page 18: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Combining POCO C++ Libraries and V8

> JavaScript is single-threaded and garbage-collected

> POCO is multithreaded (specifically web server)

> Make C++ object available to JavaScripteasy for static objects, just provide Wrapper

> Allow JavaScript code to create C++ objectseasy if you don’t care about memory/resource leaks

> Register a callback function called by GC when object is deletedallows you to properly delete underlying c++ object

> However, V8 does not do callbacks when script endswrapped C++ objects won’t be deleted, leaks resulting

> Need to track every C++ object a script creates and clean up afterwards :-(

Page 19: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Automatic JavaScript Wrappers for C++ Objects

Page 20: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// Sensor.h

//@ remote class Sensor: public Device { public: Poco::BasicEvent<const double> valueChanged;

virtual double value() const = 0; virtual bool ready() const = 0; };

Page 21: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Sensor.h

RemoteGen

lots of generated source files

RemoteGen.xml

Page 22: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Service<<generatedFrom>>

IService

ServiceProxyServiceRemoteObject

The interface class has all @remote methods from the service class.

ServiceSkeleton

<<invokes>>

<<generated>>

<<generated>><<generated>>

<<generated>>Service

ServerHelper

<<generated>>

Registers Skeleton, RemoteObject and EventDispatcher (if needed) with the Object

Request Broker.

ServiceProxyFactory

<<creates>>

<<generated>>Service

ClientHelper

<<generated>>

Registers ProxyFactory with the Object Request

Broker.

<<registers>><<registers>>

<<registers>>

ServiceEventSubscriber

<<generated>>Service

EventDispatcher

<<generated>>

<<registers>>

Page 23: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

var tempSensor = ...;

tempSensor.on(‘valueChanged', function(ev) { var temp = ev.data; // ... });

if (tempSensor.ready()) { var temp = tempSensor.value(); // ... }

Page 24: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

JavaScript Samples

Page 25: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// sensors.js (search sensors by physical quantity)

var sensors = {};

var illuminanceRefs = serviceRegistry.find( 'io.macchina.physicalQuantity == "illuminance"'); if (illuminanceRefs.length > 0) { sensors.illuminance = illuminanceRefs[0].instance(); }

var temperatureRefs = serviceRegistry.find( 'io.macchina.physicalQuantity == "temperature"'); if (temperatureRefs.length > 0) { sensors.temperature = temperatureRefs[0].instance(); }

var humidityRefs = serviceRegistry.find( 'io.macchina.physicalQuantity == "humidity"'); if (humidityRefs.length > 0) { sensors.humidity = humidityRefs[0].instance(); }

module.exports = sensors;

Page 26: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// sensors.js (search sensors by ID)

var sensors = {};

var illuminanceRef = serviceRegistry.findByName( 'io.macchina.xbee.sensor.illuminance#0013A20040A4D7F7'); if (illuminanceRef) { sensors.illuminance = illuminanceRef.instance(); }

var temperatureRef = serviceRegistry.findByName( 'io.macchina.xbee.sensor.temperature#0013A20040A4D7F7'); if (temperatureRef) { sensors.temperature = temperatureRef.instance(); }

var humidityRef = serviceRegistry.findByName( 'io.macchina.xbee.sensor.humidity#0013A20040A4D7F7'); if (humidityRef) { sensors.humidity = humidityRef.instance(); }

module.exports = sensors;

Page 27: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// database.js

var data = require('data');

module.exports = {

path: bundle.persistentDirectory + 'logger.db',

session: new data.Session('SQLite', database.path),

logIntervalSeconds: application.config.getInt( 'datalogger.intervalSeconds', 30),

keepDataSeconds: application.config.getInt( 'datalogger.keepDataSeconds', 3600) };

Page 28: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// logger.js

var sensors = require('sensors'); var db = require('database');

db.session.execute('PRAGMA journal_mode=WAL'); db.session.execute('CREATE TABLE IF NOT EXISTS datalog ( \ timestamp INTEGER, \ illuminance FLOAT, \ temperature FLOAT, \ humidity FLOAT \ )');

setInterval( function() { db.session.execute('INSERT INTO datalog VALUES (?, ?, ?, ?)', DateTime().epoch, sensors.illuminance.value(), sensors.temperature.value(), sensors.humidity.value()); }, db.logIntervalSeconds*1000);

Page 29: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// logger.js (continued)

setInterval( function() { var cutoffTime = DateTime().epoch - db.keepDataSeconds; db.session.execute('DELETE FROM datalog WHERE timestamp < ?', cutoffTime); }, db.keepDataSeconds*1000);

Page 30: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// history.jss - GET /history.jss?item=temperature&maxItems=10

var db = require('database');

var validItems = ['temperature', 'humidity', 'illuminance'];

var data = [];

db.session.pageSize = form.maxItems ? parseInt(form.maxItems) : 20; var item = form.item;

if (validItems.indexOf(item) > -1) { var recordSet = db.session.execute( 'SELECT timestamp, ' + item + ' FROM datalog ORDER BY timestamp DESC');

Page 31: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// history.jss (continued)

for (var row = 0; row < recordSet.rowCount; row++) { var time = recordSet.getValue('timestamp'); var value = recordSet.getValue(item); var date = new LocalDateTime(1970, 1, 1); date.addSeconds(time);

data[recordSet.rowCount - row - 1] = { timestamp: date.format('%H:%M:%S'), value: value };

recordSet.moveNext(); } recordSet.close(); }

response.contentType = 'application/json'; response.write(JSON.stringify(data)); response.send();

Page 32: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// MQTT to AirVantage

var sensors = require('sensors');

var mqttClientRefs = serviceRegistry.find('io.macchina.mqtt.id == "airvantage"'); if (mqttClientRefs.length > 0) { console.log('MQTT Client found'); var mqttClient = mqttClientRefs[0].instance();

setInterval(function() {

var epoch = "" + 1000*DateTime().epoch; // seconds to milliseconds var payload = {}; payload[epoch] = {

"sensors.temperature": sensors.temperature.value(), "sensors.humidity": sensors.humidity.value() "sensors.illuminance": sensors.illuminance.value() }; mqttClient.publish('JA347400060803/messages/json', JSON.stringify(payload), 0);

}, 10000);

Page 33: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

// twilio.js

var net = require('net');

module.exports = {

sendSMS: function(to, message) {

var accountSID = application.config.getString("twilio.accountSID"); var authToken = application.config.getString("twilio.authToken"); var from = application.config.getString("twilio.from");

var twilioHttpRequest = new net.HTTPRequest( "POST", "https://api.twilio.com/2010-04-01/Accounts/" + accountSID + "/SMS/Messages" ); twilioHttpRequest.authenticate(accountSID, authToken); twilioHttpRequest.contentType = "application/x-www-form-urlencoded"; twilioHttpRequest.content = "From=" + encodeURIComponent(from) + "&To=" + encodeURIComponent(to) + "&Body=" + encodeURIComponent(message);

twilioHttpRequest.send(function(result) { console.log("Twilio SMS Response: %O", result); });

};

Page 34: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

var sensors = require('sensors'); var twilio = require('twilio');

var enableSMS = true;

sensors.illuminance.on('valueChanged', function(ev) {

logger.notice("valueChanged: " + ev.data);

if (ev.data < 10) { logger.warning("Lights out!"); if (enableSMS) { twilio.sendSMS("+4367612345678", "Lights out!"); enableSMS = false; } } else if (ev.data > 50) { enableSMS = true; } });

Page 35: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

Q&A

Page 36: Mastering the IoT With JavaScript and C++ - Günter Obiltschnig

[email protected] | @obiltschnig | obiltschnig.com macchina.io | my-devices.net | pocoproject.org | www.appinf.com