112 lines
2.6 KiB
JavaScript
112 lines
2.6 KiB
JavaScript
const debug = require('debug')
|
|
const logger = debug('serialport/bindings/poller')
|
|
const EventEmitter = require('events')
|
|
const PollerBindings = require('bindings')('bindings.node').Poller
|
|
|
|
const EVENTS = {
|
|
UV_READABLE: 0b0001,
|
|
UV_WRITABLE: 0b0010,
|
|
UV_DISCONNECT: 0b0100,
|
|
}
|
|
|
|
function handleEvent(error, eventFlag) {
|
|
if (error) {
|
|
logger('error', error)
|
|
this.emit('readable', error)
|
|
this.emit('writable', error)
|
|
this.emit('disconnect', error)
|
|
return
|
|
}
|
|
if (eventFlag & EVENTS.UV_READABLE) {
|
|
logger('received "readable"')
|
|
this.emit('readable', null)
|
|
}
|
|
if (eventFlag & EVENTS.UV_WRITABLE) {
|
|
logger('received "writable"')
|
|
this.emit('writable', null)
|
|
}
|
|
if (eventFlag & EVENTS.UV_DISCONNECT) {
|
|
logger('received "disconnect"')
|
|
this.emit('disconnect', null)
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Polls unix systems for readable or writable states of a file or serialport
|
|
*/
|
|
class Poller extends EventEmitter {
|
|
constructor(fd, FDPoller = PollerBindings) {
|
|
logger('Creating poller')
|
|
super()
|
|
this.poller = new FDPoller(fd, handleEvent.bind(this))
|
|
}
|
|
/**
|
|
* Wait for the next event to occur
|
|
* @param {string} event ('readable'|'writable'|'disconnect')
|
|
* @returns {Poller} returns itself
|
|
*/
|
|
once(event, callback) {
|
|
switch (event) {
|
|
case 'readable':
|
|
this.poll(EVENTS.UV_READABLE)
|
|
break
|
|
case 'writable':
|
|
this.poll(EVENTS.UV_WRITABLE)
|
|
break
|
|
case 'disconnect':
|
|
this.poll(EVENTS.UV_DISCONNECT)
|
|
break
|
|
}
|
|
return super.once(event, callback)
|
|
}
|
|
|
|
/**
|
|
* Ask the bindings to listen for an event, it is recommend to use `.once()` for easy use
|
|
* @param {EVENTS} eventFlag polls for an event or group of events based upon a flag.
|
|
* @returns {undefined}
|
|
*/
|
|
poll(eventFlag) {
|
|
eventFlag = eventFlag || 0
|
|
|
|
if (eventFlag & EVENTS.UV_READABLE) {
|
|
logger('Polling for "readable"')
|
|
}
|
|
if (eventFlag & EVENTS.UV_WRITABLE) {
|
|
logger('Polling for "writable"')
|
|
}
|
|
if (eventFlag & EVENTS.UV_DISCONNECT) {
|
|
logger('Polling for "disconnect"')
|
|
}
|
|
|
|
this.poller.poll(eventFlag)
|
|
}
|
|
|
|
/**
|
|
* Stop listening for events and cancel all outstanding listening with an error
|
|
* @returns {undefined}
|
|
*/
|
|
stop() {
|
|
logger('Stopping poller')
|
|
this.poller.stop()
|
|
this.emitCanceled()
|
|
}
|
|
|
|
destroy() {
|
|
logger('Destroying poller')
|
|
this.poller.destroy()
|
|
this.emitCanceled()
|
|
}
|
|
|
|
emitCanceled() {
|
|
const err = new Error('Canceled')
|
|
err.canceled = true
|
|
this.emit('readable', err)
|
|
this.emit('writable', err)
|
|
this.emit('disconnect', err)
|
|
}
|
|
}
|
|
|
|
Poller.EVENTS = EVENTS
|
|
|
|
module.exports = Poller
|