# Local hardware plugin API v1 The monitor and plugins are separate applications. The monitor has no hardware library dependency. Plugins alone own their hardware. Installing or discovering a plugin does not connect it or start another service. ## Transport and authorization HTTP/1.0 or HTTP/1.1 over `/run/pigway-plugins//api.sock`. No TCP listener. The parent directory is root-owned, mode 0750, and the socket is 0660 with group `pigway-hardware`. Root and deliberately enrolled group members may control the plugin. The monitor Web API authenticates mutations with its existing bearer token before proxying local requests. Remote machine operations require that machine's token too. API v1 clients reject incompatible descriptor versions. ## Endpoints - `GET /v1/descriptor`: `api_version`, `id`, `name`, `version`, `capabilities`, `schema`. - `GET /v1/status`: availability, connection state and capability-specific actual or commanded state. A missing tachometer must never be presented as measured RPM. - `GET /v1/config`: `config` plus `schema`. - `PUT /v1/config`: `{"updates":{"section":{"key":"value"}}}`; validate the complete candidate before persisting or applying anything. Does not restart the monitor. - `PUT /v1/state`: replace the complete monitoring snapshot, never append commands. - `DELETE /v1/state`: release a lease. Publisher passes `source` and `session`; authorized local administration may use `{}` to detach the current source. Example snapshot: ```json { "api_version": 1, "source": "raspberrypi", "session": "a-new-uuid-for-each-monitor-process", "revision": 1, "ttl_seconds": 10, "system": {"cpu_percent": 12, "temperature_c": 50, "memory_percent": 20, "disk_percent": 30}, "network": {"kind": "WIF", "metric": "-60", "ip_label": "IP4", "ip": "192.168.1.2"}, "alerts": [{"id":"SERVICE_DOWN|APP","category":"service","severity":2,"priority":60, "title":"SERVICE DOWN","l2":"APP","l3":"CHECK SERVICE","l4":"CRITICAL"}] } ``` Alert categories: `cpu`, `power`, `memory`, `storage`, `network`, `service`. The producer sends only current alerts, never historical power flags. Empty `alerts` clears all previous alerts. A source/session owns its lease until release or expiry; a competing source and repeated/out-of-order revisions are rejected. Leases use the receiving process's monotonic clock, 3–30 seconds. A new monitor session retries until the old lease expires if the old process could not release it. Each plugin has an independent bounded-time publisher and one replaceable latest snapshot, so an offline plugin cannot queue stale frames or block monitoring or other plugins. ## Capability-driven UI `fan` declares levels or PWM, RPM availability, autonomous operation and ownership. `display` declares dimensions and pages. `rgb` declares modes, preset colors and experimental custom flashing. Absent capability means absent controls. A plugin with only a fan does not imply a screen or lighting device. New hardware needs its own driver; I2C, PWM GPIO and power-only fans are not interchangeable. `schema` groups fields by section. Each field provides bilingual `label`, `type` (`number`/`enum`), numeric limits or choices, unit and optional visibility rules. Optional `color_group` and `channel` (`r`/`g`/`b`) associate three numeric fields with a color picker. Plugins remain authoritative for all validation. ## Failures and independent cooling Monitoring continues without installed or reachable plugins. Hardware plugins continue local temperature control without the monitor. Expired snapshots must not keep showing stale alerts as live faults. The Yahboom implementation returns to its locally sampled home and configured normal RGB mode on expiry or detach. It samples CPU, memory, disk, temperature and primary network independently. API v1 system/network fields remain accepted for compatibility but never override local telemetry. Monitor connectivity only supplies additional alerts. Its thermal read failure and service shutdown request full fan speed as a cooling fallback; actual execution still depends on functioning hardware. Stopping a monitor, pausing its link, or unlinking a plugin does not stop the plugin service. No API/Web service has a systemd Wants dependency that starts the other application. Do not run two drivers for the same MCU, GPIO or fan. ## Optional listeners Agent network API defaults to disabled (`[api] enabled=false`) and has no Web UI. When enabled, every request requires a device bearer token. Hardware plugin integration defaults to disabled (`[integration] enabled=false`): no Unix API socket is created, while local telemetry and hardware workers continue. Change integration locally and restart the plugin. Monitor-to-plugin linkage does not require the Agent network API. The independent Web Manager stores registered device addresses and tokens; it is not implicitly a monitored device.