UNPKG

homebridge-homekit-proxy

Version:

Homebridge Homekit Proxy allows you to control HomeKit-enabled Devices directly from within HomeBridege. (Based on homebridge-homekit-controller by MartinPham)

157 lines 5.4 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.HttpWrapper = exports.Sequencer = void 0; const hap_controller_1 = require("hap-controller"); const TIMEOUT = 5000; const MAX_RETRY = 10; class Sequencer { constructor(log) { this._queue = []; this.timer = undefined; this.log = log; } get length() { return this._queue.length; } get busy() { return this.timer !== undefined; } push(call, name, uuid) { const self = this; return new Promise((resolve, reject) => { this._queue.push({ uuid: uuid, name: name, fkt: call, timer: undefined, resolve: resolve, reject: reject, finished: false, retries: MAX_RETRY, }); self.next(); }); } next() { const self = this; this._queue = this._queue.filter((i) => i.finished === false); if (self.timer === undefined && this._queue.length > 0) { const qi = this._queue.shift(); self.timer = setTimeout(() => { self.timer = setTimeout(() => { self.timer = undefined; qi.retries--; if (qi.retries <= 0) { this.log.debug(`Timeout for Task ${qi.name}/${qi.uuid} => GIVING UP`); qi.reject(`Timeout for Task ${qi.name}/${qi.uuid}`); } else { this.log.debug(`Timeout for Task ${qi.name}/${qi.uuid} => RETRY`); this._queue.push(qi); } self.next(); }, 100); }, TIMEOUT); qi .fkt() .then((value) => { if (self.timer) { clearTimeout(self.timer); } self.timer = setTimeout(() => { self.timer = undefined; self._queue .filter((i) => i.name === qi.name && i.uuid == qi.uuid && i.finished === false) .forEach((i) => { i.resolve(value); i.finished = true; }); qi.resolve(value); self.next(); }, 100); }) .catch((e) => { if (self.timer) { clearTimeout(self.timer); } self.timer = setTimeout(() => { self.timer = undefined; qi.reject(e); self.next(); }, 100); }); } } } exports.Sequencer = Sequencer; class HttpWrapper { constructor(log, deviceId, address, port, pairingData) { this.uct = 0; this.listeners = []; this.log = log; this.list = new Sequencer(log); this.client = new hap_controller_1.HttpClient(deviceId, address, port, pairingData); this.client.on('event', this.onEvent.bind(this)); } identify() { const self = this; return self.list.push(() => { return self.client.identify(); }, 'identify', '-'); } getAccessories() { const self = this; return self.list.push(() => { return self.client.getAccessories(); }, 'getAccessories', '-'); } getCharacteristics(characteristics, options) { const self = this; return self.list.push(() => { if (characteristics.length === 0) { return new Promise((resolve) => { resolve({}); }); } return self.client.getCharacteristics(characteristics, options); }, 'getCharacteristics', characteristics.join(', ')); } setCharacteristics(characteristics) { const self = this; return self.list.push(() => { return self.client.setCharacteristics(characteristics); }, 'setCharacteristics', Object.keys(characteristics) .map((k) => `${k}=${characteristics[k]}`) .join(', ')); } subscribeCharacteristics(characteristics) { const self = this; return self.list.push(() => { this.log.debug('Running Subscribe task', characteristics.join(', ')); return self.client.subscribeCharacteristics(characteristics); }, 'subscribeCharacteristics', characteristics.join(', ')); } onEvent(event) { const self = this; this.log.debug('Received Event', event); event.characteristics.forEach((cc) => { const cname = `${cc.aid}.${cc.iid}`; self.listeners .filter((l) => l.c.cname === cname) .forEach((l) => { var _a; self.log.debug(`Notifiying listener for ${(_a = l.c.connect) === null || _a === void 0 ? void 0 : _a.displayName} (${cname})`); l.listener(cc); }); }); } on(c, listener) { this.listeners.push({ c: c, listener: listener, }); return this; } } exports.HttpWrapper = HttpWrapper; //# sourceMappingURL=HttpWrapper.js.map