Skip to content

API Reference

The HOS server exposes four public communication surfaces: REST API (HTTP), Socket.IO (real-time client events), raw WebSocket (remote driver protocol), and SSE (server-sent events for live state). This page documents those surfaces plus the internal stdin/stdout protocol used by OS-local uploaded drivers.

Source of truth: apps/server/src/routes/ is the canonical source for REST endpoints. This wiki is a human-friendly summary. If something looks wrong, check the route files directly.


REST API — OS API

Base paths: /app/os, /api/os, /v1/os

Auth: Bearer token required (scope: os_api_admin). Pass as Authorization: Bearer <token>. Obtain a token via POST /auth/login.

Do not include actual tokens in requests from this docs page. Use <token> as a placeholder when sharing examples.

Auth

MethodPathAuthDescription
POST/auth/loginNoneLogin with credentials, returns bearer token
GET/auth/meRequiredAuthenticated principal info

Bootstrap and Preferences

MethodPathDescription
GET/bootstrapFull system bootstrap — devices, spaces, programs, media, and current state in one payload
GET/preferences/homeHome screen preferences
POST/preferences/homeUpdate home preferences
GET/design-profilesList available design profiles
POST/design-profiles/selectSelect the active design profile
GET/design/liveCurrent live design

Devices

MethodPathDescription
GET/devicesList all logical devices
GET/devices/:idDevice details
POST/devices/:id/commandDispatch a command (Standard or IR-mapped)

IR Device Properties

Devices using the GENERIC_IR driver include specific metadata in their properties object:

  • extenderIp: The target hardware bridge IP address.
  • irCommands: A dictionary of command keys to raw IR pulse objects.
    json
    {
      "turn_on": {
        "freq_khz": 38,
        "raw": [4500, 4500, 560, ...]
      }
    }

Spaces

MethodPathDescription
GET/spacesList all spaces
POST/spaces/saveCreate or update a space
POST/spaces/:id/removeRemove a space
GET/spaces/:id/devicesDevices assigned to a space
GET/spaces/:id/remote-sourcesRemote sources for a space
POST/spaces/:id/remote-sources/:sourceId/activateActivate a remote source
POST/spaces/:id/devices/assignAssign devices to a space

Programs

MethodPathDescription
GET/programsList all programs
POST/programs/saveCreate or update a program
POST/programs/:id/runExecute a program
POST/programs/:id/lighting/offTurn off program lighting
DELETE/programs/:idDelete a program

State Stream

MethodPathDescription
GET/state/snapshotCurrent device state snapshot (point-in-time)
GET/state/streamSSE live state stream — see SSE section below
GET/state/telemetry/:deviceIdTelemetry data for a specific device

Integration Releases

MethodPathDescription
GET/integration-releasesList integration releases
GET/integration-releases/:keyGet details for a specific release
GET/integration-releases/:key/submission-packageGet the submission package
POST/integration-releases/saveSave a release
POST/integration-releases/:key/submitSubmit a release
POST/integration-releases/:key/unsubmitUnsubmit a release
POST/integration-releases/:key/rollbackRoll back a release

Fleet Management (Phase 06)

These endpoints manage the HOS fleet and bridge connectivity.

MethodPathAuthDescription
GET/hos-fleet-devicesosApiAuthList HOS devices with their Fleet Release status
POST/hos-fleet-devices/releases/:key/statusosApiAuthUpdate Fleet Release status for a specific OS logical device
POST/device/hos/categoryappAuthCreate or update an HOS device category
POST/integration/hos/device/commandappAuthDispatch a command to a specific HOS device in the fleet
POST/bridge/devices/:fleetDeviceId/commandosBridgeAuthSend a command to a fleet device via the OS bridge

Bridge (Fleet)

Bridge endpoints serve two auth modes: osApiAuth (for HOS admin-level callers) and osBridgeAuth (for bridge/fleet peer callers).

MethodPathAuthDescription
GET/bridge/linkosApiAuthGet bridge link info
POST/bridge/link/saveosApiAuthSave bridge link
POST/bridge/tokenosApiAuthGet bridge token
GET/bridge/healthosBridgeAuthBridge health check
GET/bridge/capabilitiesosBridgeAuthBridge capabilities
GET/bridge/devicesosBridgeAuthList bridge devices
GET/bridge/devices/stateosBridgeAuthDevice states from bridge
POST/bridge/devices/registerosBridgeAuthRegister a bridge device
POST/bridge/devices/updateosBridgeAuthUpdate a bridge device
POST/bridge/devices/:fleetDeviceId/commandosBridgeAuthSend command to a fleet device

HomeKit

MethodPathDescription
GET/homekit/statusHomeKit bridge status
GET/homekit/accessoriesList HomeKit accessories
GET/homekit/import-accessoriesList importable accessories
GET/homekit/pluginsList HomeKit plugins
GET/homekit/plugins/:pluginIdPlugin details
POST/homekit/plugins/:pluginId/installInstall a plugin
POST/homekit/plugins/:pluginId/uninstallUninstall a plugin
POST/homekit/plugins/:pluginId/enableEnable a plugin
POST/homekit/plugins/:pluginId/disableDisable a plugin
POST/homekit/plugins/:pluginId/configConfigure a plugin
POST/homekit/settingsUpdate HomeKit settings
POST/homekit/resyncResync HomeKit bridge
GET/homekit/plugin/bootstrapPlugin bridge bootstrap (plugin bridge auth)
GET/homekit/plugin/state/streamPlugin state stream SSE (plugin bridge auth)
POST/homekit/plugin/devices/:id/commandSend command via plugin bridge

AI

MethodPathDescription
GET/ai/statusGet AI service status (installed, running, modelReady, download progress)
GET/ai/healthCheck AI service health
GET/ai/suggestionsGet AI chat suggestions/prompts
GET/ai/modelsList available AI models
POST/ai/installInstall a specific AI model
POST/ai/startStart the AI service
POST/ai/stopStop the AI service
POST/ai/promptSend a prompt to the AI. Use ?sync=true for immediate response.
GET/ai/eventsSSE stream for AI events (generation progress, status updates)
DELETE/ai/uninstallUninstall the current AI model

REST API — App API

Base paths: /app, /api

Auth: appAuth middleware (session-based for the legacy app surface)

This is the legacy API surface consumed by earlier mobile client versions and the web admin panel. Key endpoint families:

PrefixPurpose
/auth/*App login, register, logout
/devices/*Device listing and commands
/entity/*Entity-level operations
/room/*Room/space operations (legacy)
/integration/*Integration management
/programs/*Program CRUD and execution
/sequences/*Sequence operations
/zonesZone listing
/action-mapsAction map listing
/media-services/*Media service status and commands

REST API — Other Route Families

PrefixAuthPurpose
/remote, /v1/remoteremoteAuthRemote-controller API for pairing and command dispatch
/adminAdmin authAdmin panel routes
/osSessionServer-rendered EJS web UI (the OS frontend)
/devNone (dev only)Debug routes — available in development only

Socket.IO Events

Connection path: /socket.io (default Socket.IO path)

The server exposes multiple Socket.IO namespaces. Each namespace handles a specific concern.

Namespaces and Events

NamespaceEventDirectionPayload
/socket/device-statedevice:state:updateserver → client{ deviceId: string, state: object }
/socket/device-statedevice:state:snapshotserver → client{ deviceId: string, state: object }
/socket/haptique-protocolhaptique:commandclient → server{ command: string, payload: object }
/socket/haptique-protocolhaptique:responseserver → client{ command: string, data: unknown, ok: boolean }
/socket/haptique-protocolhaptique:eventserver → clientHaptiqueProtocolEvent
/socket/remote-connectremote:pairingclient → serverPairing request payload
/socket/remote-connectremote:pairing:statusserver → clientPairing result
/socket/designerdesigner:publishedserver → clientDesign payload
/socket/designerdesigner:refreshserver → clientRefresh signal
/socket/device-ir-testir:dataserver → clientIR signal data

Haptique Protocol Commands

Commands are sent client → server via the haptique:command event on the /socket/haptique-protocol namespace. Format: { command: "<COMMAND_NAME>", payload: { ... } }.

CommandDescription
GET_PROTOCOL_CAPABILITIESList capabilities supported by the protocol hub
LIST_EVENTSList available protocol event types
SYSTEM_SNAPSHOTFull system state snapshot
LIST_INTEGRATIONSList all loaded integrations
LIST_CONNECTIONSList active integration connections
LIST_SCENESList all scenes
SCENE_RUNExecute a scene by ID
LIST_ENTITY_DOMAINSList entity domains (lighting, climate, etc.)
LIST_ENTITIESList all entities
GET_ENTITYGet a single entity by ID
ENTITY_ACTIONPerform an action on an entity
LIST_STATESList all device states
GET_DEVICE_STATEGet state for a specific device
LIST_SENSORSList sensor entities
LIST_PROGRAMSList all programs
LIST_AUTOMATIONSList all automations
LIST_ACTION_MAPSList action maps
LIST_ZONESList zones
LIST_DRIVERSList active drivers
LIST_DEVICESList all devices (protocol-level)
LIST_DEVICE_COMMANDSList commands available for a device
GET_DEVICE_COMMANDGet a specific device command definition
EXECUTE_DEVICE_COMMANDExecute a device command
GET_HOME_GRAPHGet the home graph structure
LIST_CAPABILITY_MODELList the capability model definitions
LIST_PROGRAM_SEMANTICSList program semantic definitions
UPSERT_PROGRAM_SEMANTICCreate or update a program semantic
DELETE_PROGRAM_SEMANTICDelete a program semantic
GET_CONTEXT_SNAPSHOTGet contextual system snapshot
INTENT_PARSEParse a natural language intent
INTENT_EXECUTEExecute a parsed intent
PROGRAM_RUNRun a program by ID
AUTOMATION_RUNRun an automation by ID
ACTION_MAP_TRIGGERTrigger an action map
DEVICE_ACTIONDispatch a raw device action
DRIVER_MESSAGEForward a message to a driver

Remote Driver WebSocket Protocol

Transport: Raw WebSocket (ws library — NOT Socket.IO)

Path: /driver on DRIVER_WS_PORT (defaults to the same port as PORT if DRIVER_WS_PORT is not set)

This protocol is for external SDK-style driver processes only. Mobile clients and external callers should use the Socket.IO or REST surfaces above. OS-local uploaded Python, Lua, and JavaScript drivers use the local process protocol described below instead of opening this WebSocket.

For comprehensive driver protocol documentation with full message schemas, connection lifecycle diagrams, and driver authoring guidance, see the sdk/docs/ directory. The SDK has detailed protocol guides for driver authors.

Registration Handshake

When a driver WebSocket connection is established, the driver must immediately send a registration message:

json
{
  "method": "driver.register",
  "driverKey": "MY_DRIVER",
  "instanceId": "my-driver-001",
  "protocolVersion": 1
}
FieldTypeDescription
method"driver.register"Must be exactly this string
driverKeystringUnique identifier for the driver type (e.g., "HUE", "DENON")
instanceIdstringUnique identifier for this driver instance
protocolVersionnumberProtocol version — use 1

Driver → Server Event Types

After registration, drivers send events using the following types:

Event TypePurpose
DEVICE_DISCOVEREDNotify server of a new device found by this driver
DEVICE_UPDATEDNotify server that device metadata has changed
DEVICE_REMOVEDNotify server that a device is no longer available
STATE_UPDATEPush a device state update to the server
ACTION_RESULTReport the result of a command execution requested by the server
METRIC_UPDATEPush telemetry/metric data for a device

Server → Driver Messages

Message TypePurpose
ACTIONServer instructs driver to execute a command on a device
DRIVER_STATUSServer sends a status notification to the driver

Local Driver Process Protocol

OS-local drivers uploaded through Integration Manager are launched by DriverManager from a *.driver.json manifest. They communicate with HOS over newline-delimited JSON on stdin/stdout.

Supported local upload runtimes:

Manifest driverTypeFile extension
python.py
javascript.js
lua.lua

Runtime rules:

  • The manifest supplies driverKey, driverFile, setup properties, commands, io, and envMap.
  • HOS writes one command JSON object per stdin line.
  • Drivers write one event JSON object per stdout line.
  • JavaScript drivers are plain Node-compatible .js; TypeScript must be compiled before upload.
  • JavaScript should prefer Node 20+ built-ins (fetch, net, dgram, readline) and only include package.json when external dependencies are required.

Common local incoming messages:

Message TypePurpose
ACTIONExecute a user, automation, or mapped device action
COMMAND_EXECUTEExecute a command-catalog action
PINGOptional runtime health probe

Common local outgoing events match the WebSocket protocol event names: DEVICE_DISCOVERED, DEVICE_UPDATED, DEVICE_REMOVED, STATE_UPDATE, ACTION_RESULT, and optional METRIC_UPDATE.


SSE Stream

Endpoint: GET /app/os/state/stream

Auth: Bearer token passed as a query parameter: ?accessToken=<token>

The SSE stream delivers real-time device state changes and protocol events to any HTTP client that supports server-sent events.

Events

EventPayloadWhen
ready{}Sent immediately on connection established
snapshotFull device state map (all devices)Sent immediately after ready
state{ deviceId: string, state: object }Sent on every device state change
eventHaptiqueProtocolEventSent on protocol hub events
ping{}Periodic heartbeat to keep connection alive

Example SSE consumer (Node.js)

typescript
const EventSource = require('eventsource');
const es = new EventSource('http://localhost:8080/app/os/state/stream?accessToken=<token>');

es.addEventListener('snapshot', (e) => {
  const allState = JSON.parse(e.data);
  console.log('Initial state:', allState);
});

es.addEventListener('state', (e) => {
  const { deviceId, state } = JSON.parse(e.data);
  console.log(`${deviceId} updated:`, state);
});

Cross-References