ble-bean-stream
v0.1.0
Published
Take a bean instance from ble-bean and make it a Node stream.
Downloads
2
Readme
BLE-Bean Stream
Take a Bean instance from ble-bean and make it a Node stream.
The LightBlue Bean by Punch Through Design is a great little Bluetooth Arduino platform. And the ble-bean module is awesome for connecting to the Bean from a Node application.
This module provides a stream-based interface to the LightBlue Bean given a Bean instance that you obtain from ble-bean. From there, you can pipe the Readable stream to the console, a transform stream, file or database. See the Examples for more.
Important
This module is designed to work exclusively with the LightBlue Bean by Punch Through Design.
This module depends on ble-bean. So you must first install and require that module. Then obtain a bean instance via one of the discovery methods.
This module is unofficial, and is not affiliated with Punch Through Design in any way whatsoever.
We at Humans Forward recognize that software is commonly built upon the amazing efforts of others. Therefore, we'd like to give shout-outs to the creators of the Bean, and to the following module authors:
Installation
npm install ble-bean
npm install ble-bean-stream
Usage
Read the temperature every 5 seconds and pipe to JSON.stringify()
'use strict';
const Bean = require('ble-bean');
const beanStream = require('ble-bean-stream');
// Transform stream that formats data as JSON strings
const json = new require('stream').Transform({objectMode: true});
json._transform = (chunk, encoding, callback) => {
json.push(JSON.stringify(chunk) + '\r\n');
callback();
}
// Ask ble-bean to discover a Bean
Bean.discover((bean) => {
// Start Bean streaming
// NOTE: The Readable stream will call bean.connectAndSetup()
let beanReadable = beanStream.createReadStream(bean, {
poll: 5000, // Interval in millis
pollTemp: true
});
beanReadable.pipe(json).pipe(process.stdout);
});
// Produces:
// {"device":"fec9e916...","temp":{"celsius":24}}
// {"device":"fec9e916...","temp":{"celsius":23}}
// ...
Examples
poll-to-console — Periodically reads the accelerometer, temperature, and scratch values one and two. Logs the readings to the console as JSON.
poll-to-mysql — Periodically reads the accelerometer and temperature. Logs the readings to a MySQL table.
notify-to-mongo — Subscribes to change notifications for scratch one, two and three. Logs the scratch values to a MongoDB collection.
serial-to-file — Listens for data sent over the virtual serial port and writes it to a file.
API
Module interface
Assuming:
const beanStream = require('ble-bean-stream');
beanStream.createReadStream(bean, options)
— Factory method to create a new BeanReadable instance with a given bean and options.beanStream.BeanReadable
— Exposes the BeanReadable class that can be instantiated vianew BeanReadable(bean, options)
.
Examples:
'use strict';
const beanStream = require('ble-bean-stream');
// Discover and call createReadStream()
Bean.discover((bean) => {
let beanReadable = beanStream.createReadStream(bean, {listenSerial: true});
beanReadable.pipe(...);
});
// Discover and instantiate
Bean.discover((bean) => {
let beanReadable = new beanStream.BeanReadable(bean, {listenSerial: true});
beanReadable.pipe(...);
});
Class: BeanReadable
A BeanReadable object connects to a discovered Bean, sets up any configured polling timers and/or event listeners, and emits data as objects. A typical pattern is to pipe a BeanReadble into a Transform stream for formatting or filtering.
new BeanReadable(bean, options)
Constructor. Creates a new BeanReadable with a given bean and options. The options object is evaluated by BeanReadable, and is also forwarded to the underlying HookedReadable stream.
bean (Bean)
A Bean instance that is provided by one of the ble-bean (noble-device) discovery methods.
options (Object)
beforePush
(Function) — A callback to invoke every time an object is pushed into the stream. Courtesy of HookedReadable.Example:
// Add a 'timestamp' property beforePush: function(data) { data.timestamp = new Date(); return data; }
highWaterMark
(Number) — The maximum number of objects to store in the internal stream buffer. Default is 16. If you are piping Bean data into a slow writer, such as a database, this number should be increased to mitigate back-pressure.poll
(Number) — Configures the BeanReadable timer to periodically gather readings from the Bean's sensors and/or scratch characteristics.- A value of 0 (the default) will poll the sensors only once, then stop.
- A value >= 500 is the number of milliseconds between each polling cycle.
- A value < 500 is equivalent to 500 (i.e. you cannot poll faster than every 0.5 seconds).
This option only configures the polling cycle; therefore, you should specify one or more of the secondary 'poll' options below.
pollAccell: true
— Read acceleration values when the polling timer elapses. Anaccell
object will be emitted from the stream.{ "accell": { "x": 0.00782, "y": 0.10166, "z": 1.02051 }, "device": "fec9e916..." }
pollBatt: true
— Read the battery level (in percent) when the polling timer elapses. Abatt
object will be emitted from the stream.{ "batt": { "level": 98 }, "device": "fec9e916..." }
pollTemp: true
— Read ambient temperature when the polling timer elapses. Atemp
object will be emitted from the stream.{ "temp": { "celsius": 19 }, "device": "fec9e916..." }
pollScratch
(String) — Read one or more of the scratch characteristics (1–5) when the polling timer elapses.Examples:
pollScratch: '1,3,5' // OR pollScratch: '135'
When configured, a respective
scratch1...5
object will be emitted from the stream. For convenience, scratch data is represented as string, integer, and unsigned integer.{ "scratch1": { "data": "ABCDEFG", "int": 16961, "uint": 16961 }, "device": "fec9e916..." }
notifyScratch
(String) — Subscribe to change notifications for one or more of the scratch characteristics (1–5).Examples:
notifyScratch: '2,4' // OR notifyScratch: '24'
When configured, a respective
scratch1...5
object will be emitted from the stream (seepollScratch
above).listenSerial: true
— Subscribe to data sent over the Virtual Serial port. The Serial Message Protocol appears to deliver serial messages in 63 byte chunks; therefore, multipleserial
objects may be emitted for each Serial print.{ "serial": { "data": "Hello from Bean\r\n" }, "device": "fec9e916..." }
To reassemble serial data into proper messages, one could implement a Transform stream that concatenates and re-emits data based on a delimiter.
Stream objects info
and error
BeanReadable emits information and error objects to convey its state. A downstream Transform can be implemented to format or filter these objects as needed. See the examples for more.
{
"info": {
"message": "Connected"
},
"device": "fec9e916..."
}
{
"error": {
"message": "Noble error"
},
"device": "fec9e916..."
}