UNPKG

homebridge-unifi-access

Version:

Homebridge UniFi Access plugin providing complete HomeKit integration for the UniFi Access ecosystem with full support for most features including autoconfiguration, motion detection, multiple controllers, and realtime updates.

114 lines (78 loc) 3.32 kB
/* Copyright(C) 2017-2025, HJD (https://github.com/hjdhjd). All rights reserved. * * server.js: homebridge-unifi-access webUI server API. * * This module is heavily inspired by the homebridge-config-ui-x source code and borrows from both. * Thank you oznu for your contributions to the HomeKit world. */ "use strict"; import { featureOptionCategories, featureOptions } from "../dist/access-options.js"; import { AccessApi } from "unifi-access"; import { HomebridgePluginUiServer } from "@homebridge/plugin-ui-utils"; import util from "node:util"; class PluginUiServer extends HomebridgePluginUiServer { errorInfo; constructor() { super(); this.errorInfo = ""; // Register getErrorMessage() with the Homebridge server API. this.#registerGetErrorMessage(); // Register getDevices() with the Homebridge server API. this.#registerGetDevices(); // Register getOptions() with the Homebridge server API. this.#registerGetOptions(); this.ready(); } // Register the getErrorMessage() webUI server API endpoint. #registerGetErrorMessage() { // Return the most recent error message generated by the Protect API. this.onRequest("/getErrorMessage", () => this.errorInfo); } // Register the getDevices() webUI server API endpoint. #registerGetDevices() { // Return the list of Protect devices. this.onRequest("/getDevices", async (controller) => { try { const log = { debug: () => {}, error: (message, parameters = []) => { // Save the error to inform the user in the webUI. this.errorInfo = util.format(message, ...(Array.isArray(parameters) ? parameters : [parameters])); // eslint-disable-next-line no-console console.error(this.errorInfo); }, info: () => {}, warn: () => {} }; // Connect to the Access controller. const udaApi = new AccessApi(log); if(!(await udaApi.login(controller.address, controller.username, controller.password))) { return []; } // Bootstrap the controller. It will emit a message once it's received the bootstrap JSON, or you can alternatively wait for the Promise to resolve. if(!(await udaApi.getBootstrap())) { return []; } const devices = udaApi.devices.filter(x => x.is_managed); devices.sort((a, b) => { const nonEmpty = (...args) => args.find(v => (v !== undefined) && (v !== null) && (v !== "")); const aCase = nonEmpty(a.alias, a.name, a.model).toLowerCase(); const bCase = nonEmpty(b.alias, b.name, b.model).toLowerCase(); return aCase > bCase ? 1 : (bCase > aCase ? -1 : 0); }); return [ udaApi.controller, ...devices ]; } catch(err) { // eslint-disable-next-line no-console console.log(err); // Return nothing if we error out for some reason. return []; } }); } // Register the getOptions() webUI server API endpoint. #registerGetOptions() { // Return the list of options configured for a given Protect device. this.onRequest("/getOptions", () => ({ categories: featureOptionCategories, options: featureOptions })); } } (() => new PluginUiServer())();