Version 5.7 | Indigo 2025.2+ | Python 3.13+
Creates companion plugin devices alongside your existing Indigo Z-Wave devices, exposing sensor values that Indigo does not capture natively — temperature, humidity, luminance, contact state, lock state, scene controller events, and more.
When you include a Z-Wave sensor in Indigo, Indigo creates a native device for it based on what it recognises. That works well for the Devices Indigo knows about. But many new Devices that are not supported by Indigo can now be included with this plugin until it becomes included into Indigo.
This plugin fills that gap. You select the existing native Indigo device, choose the sensor type you want to capture, and the plugin creates a properly-typed Indigo device that works in triggers, control pages, and action groups exactly like any native device.
The plugin also provides a Simulate Z-Wave Report tool — useful for sending raw Z-Wave byte captures to Matt and Jay (Indigo's authors) when a sensor is behaving unexpectedly, so they can add or improve native support.
- Select from your existing Indigo devices — dropdown lists all native Z-Wave devices; node ID is read automatically
- Multiple plugin devices per node — one physical multi-sensor creates separate plugin devices per reading type (motion, temperature, luminance), each assigned the appropriate sensor type
- Multi-channel / endpoint support — optional endpoint ID per device for multi-channel sensors (e.g. Aeotec 6-in-1)
- Eleven device types — motion, contact, temperature, humidity, luminance, energy monitor, battery, lock, scene controller, plug/relay, generic
- Correct icons — thermometer, light sensor, motion, power, lock, and generic sensor icons set automatically
- displayStatus — device list shows meaningful values:
detected / clear,open / closed,21.5 degC,450 lux,locked / unlocked,S1 pressed, etc. - Temperature unit preference — store and display all temperatures in degC or degF regardless of what the sensor reports; conversion applied automatically
- Battery sensor type — dedicated battery device with
batteryLowflag; all device types also carrybatteryLevelandbatteryLowstates - Lock support — DOOR_LOCK_OPERATION_REPORT decodes lock mode, bolt state, latch state, and last user ID; NOTIFICATION ACCESS_CONTROL events for keypad/RF/manual lock and unlock
- Scene controller — CENTRAL_SCENE_NOTIFICATION decodes scene number, key action (pressed/released/held/repeated), and timestamp
- Stale device detection — configurable threshold (4–72 h); logs a warning and sets
deviceOnline=Falsewhen a device goes silent; clears automatically when any report arrives - Wake-up interval tracking — WAKE_UP_INTERVAL_REPORT stores the interval in the
wakeUpIntervalstate; wake-up notifications mark the device as alive - Simulate Z-Wave Report — menu item lets you feed raw hex bytes to any plugin device for end-to-end testing; dialog stays open for iterative testing
- Generate Indigo Support Report — one-click menu item dumps manufacturer ID, product type/ID, supported command classes, all device properties and states to the Indigo log; formatted for pasting into the Indigo forum to request native device support
- Debug logging — toggleable; logs raw Z-Wave bytes and all state updates
- Mock test suite — full test coverage without needing an Indigo server
| Sensor type | Primary state | Additional states |
|---|---|---|
| Motion | onOffState (bool) |
motion, tamper, displayStatus |
| Contact | onOffState (bool) |
contact, displayStatus |
| Temperature | temperature (float, degC or degF) |
displayStatus |
| Humidity | humidity (float, %) |
displayStatus |
| Luminance | luminance (float, lux) |
displayStatus |
| Energy | watts (float, W) |
kwh, voltage, current, displayStatus |
| Battery | battery (int, %) |
batteryLow, onOffState, displayStatus |
| Plug / Relay | onOffState (bool) |
switchState, watts, kwh, voltage, current, deviceOnline, displayStatus |
| Lock | lockState (bool) |
lockMode, boltState, latchState, lastUser, onOffState, displayStatus |
| Scene Controller | lastScene (int) |
lastSceneAction, sceneTimestamp, onOffState, displayStatus |
| Generic | onOffState (bool) |
switchState, dimLevel, displayStatus |
All sensor device types also carry: battery, batteryLow, waterLeak, smoke, coAlarm, co2Level, uvIndex, pressure, noise, velocity, airFlow, voc, soilMoisture, gasCubicMeters, waterCubicMeters, lastUpdate, deviceOnline, wakeUpInterval, rawLastReport
Plug/Relay devices carry only: switchState, watts, kwh, voltage, current, lastUpdate, deviceOnline, rawLastReport (no battery or wake-up states — mains-powered)
| Hex | Class | What it decodes |
|---|---|---|
0x31 |
SENSOR_MULTILEVEL | Temperature, humidity, luminance, CO2, UV, pressure, noise, velocity, power (W), voltage (V), current (A), air flow, VOC, soil moisture |
0x30 |
SENSOR_BINARY | Motion, water, smoke, CO, tamper, door/window |
0x71 |
NOTIFICATION v4+ | Motion, tamper, intrusion, glass break, door/window, water, smoke, CO, lock/unlock ops (manual/RF/keypad/auto) |
0x62 |
DOOR_LOCK | Lock mode, bolt state, latch state (v2+), last user |
0x5B |
CENTRAL_SCENE | Scene number, key action (pressed/released/held/repeated), sequence number |
0x25 |
SWITCH_BINARY | On/off relay |
0x26 |
SWITCH_MULTILEVEL | Dimmers (0–99%) |
0x32 |
METER | Power (W), energy (kWh/kVAh), voltage (V, Scale2), current (A, Scale2), gas (m3/ft3/ccf), water (m3/ft3/gallons) |
0x80 |
BATTERY | Battery level %; 0xFF low warning |
0x20 |
BASIC | Legacy on/off |
0x60 |
MULTI_CHANNEL | Endpoint encapsulation — unwrapped transparently |
0x84 |
WAKE_UP | Notification touches lastUpdate; interval stored in wakeUpInterval |
- Go to the Releases page and download
UniversalZWaveSensor.indigoPlugin.zip - Unzip the downloaded file — you will get
UniversalZWaveSensor.indigoPlugin - Double-click
UniversalZWaveSensor.indigoPlugin— Indigo will install it automatically - Enable the plugin from the Indigo Plugins menu
Existing plugin devices upgrade automatically. When Indigo loads the new plugin, it calls device.stateListOrDisplayStateIdChanged() on each device, which adds any new states with default values. No manual steps are needed. Your existing triggers and action groups continue to work unchanged.
- Devices → New Device
- Set Type to Universal Z-Wave Sensor, Model to Universal Z-Wave Sensor
- Click Edit Device Settings
- Select the Native Indigo Z-Wave Device from the dropdown — the node ID is read automatically
- Choose the Sensor Type for the value you want to capture (e.g. Temperature Sensor)
- (Optional) Enter an Endpoint ID for multi-channel devices
For a multi-sensor (e.g. door sensor that also sends temperature and humidity), create one plugin device per sensor type and select the same native device for each.
Naming tip: Name plugin devices to reflect what they add, e.g.
Bathroom Door (Temp)orHall PIR (Humidity). When Indigo adds native support for those values, delete the plugin devices and update any triggers or action groups — a one-time job.
| Setting | Default | Description |
|---|---|---|
| Enable debug logging | Off | Logs raw Z-Wave byte sequences and all state updates |
| Log unknown command classes | On | Writes unrecognised report bytes to rawLastReport state and Indigo log |
| Temperature unit | degC | Choose degC or degF — all temperature reports are converted to this unit before storing, regardless of what the sensor reports |
| Enable stale device detection | On | Warns when a device has not reported within the threshold |
| Stale threshold | 24 hours | How long without a report before a device is considered offline |
Plugins → Universal Z-Wave Sensor → Simulate Z-Wave Report...
Select a plugin device, enter space-separated hex bytes, and click Send. The bytes are fed directly into the parser as if real hardware had sent them. The dialog stays open so you can send multiple sequences without reopening it.
| Byte sequence | What it simulates |
|---|---|
31 05 01 22 00 D7 |
Temperature 21.5 degC |
31 05 03 0A 01 C2 |
Luminance 450 lux |
31 05 05 01 41 |
Humidity 65% |
71 05 00 00 00 FF 07 07 00 |
Motion detected (NOTIFICATION) |
71 05 00 00 00 FF 07 08 00 |
Motion cleared |
71 05 00 00 00 FF 06 16 00 |
Door opened |
71 05 00 00 00 FF 06 17 00 |
Door closed |
71 05 00 00 00 FF 06 01 01 00 |
Manual lock (user 0) |
71 05 00 00 00 FF 06 06 02 05 |
Keypad lock (user 5) |
62 03 FF 00 00 FE |
Door lock — locked (v2, bolt locked, latch closed) |
62 03 00 00 00 FD |
Door lock — unlocked (v2, bolt unlocked, latch open) |
5B 03 01 00 01 |
Scene 1, key pressed |
5B 03 02 01 01 |
Scene 1, key released |
5B 03 03 02 02 |
Scene 2, key held |
80 03 55 |
Battery 85% |
80 03 FF |
Battery LOW warning |
84 07 |
Wake-up notification |
84 06 00 01 2C 6F |
Wake-up interval = 300 s (5 min) |
60 0D 00 01 31 05 01 22 00 D7 |
Multi-channel ep 1: temperature 21.5 degC |
Plugins → Universal Z-Wave Sensor → Generate Indigo Support Report...
Select a plugin device and click Generate Report. A formatted block is written to the Indigo log containing everything Matt and Jay (Indigo's authors) need to add native support for the device:
| Section | What it contains |
|---|---|
| Plugin Device | Name, type, node ID, endpoint, last update, raw last report bytes |
| Plugin Device States | All current state values |
| Native Z-Wave Device | Name, model, sub-model, description, protocol, Indigo ID |
| Native Device Z-Wave Properties | ownerProps — manufacturer ID, product type ID, product ID, supported command classes with versions |
| Native Device States | All states Indigo currently tracks for the native device |
| Native Device Global Props | All plugin-stored properties across every plugin |
Copy the entire block from the Indigo log and paste it into a post on the Indigo forum.
The plugin checks all plugin devices every 60 seconds. If a device's lastUpdate is older than the configured threshold:
- A warning is logged:
Sensor: No report for 26.3h (threshold 24h) — may be offline or out of range deviceOnlinestate is set toFalse(uiValueoffline)- The warning is only logged once — no repeated entries
When any Z-Wave report arrives from the device, deviceOnline is immediately restored to True and Back online (report received) is logged.
Tip: Battery devices typically report every few hours to days. Set the threshold generously — 48 or 72 hours is reasonable for weekly-reporting sensors.
Some multi-sensors (e.g. Aeotec MultiSensor 6) use Z-Wave multi-channel addressing: each sensor type is exposed as a separate endpoint on the same node.
Setup for a 3-in-1 sensor (motion ep 1, temperature ep 2, luminance ep 3) on node 42:
| Plugin device | Sensor Type | Endpoint ID |
|---|---|---|
| Hall Motion | Motion Sensor | 1 |
| Hall Temperature | Temperature Sensor | 2 |
| Hall Luminance | Luminance Sensor | 3 |
Leave Endpoint ID blank (or set to 0) to accept reports from all endpoints on the node.
| Item | Notes |
|---|---|
| Battery devices | Only report on state change or wake-up — cannot be polled on demand |
| METER_REPORT v3+ | Voltage (V) and current (A) parsed using the Scale2 bit (byte 2 bit 7); power factor and other higher scale values not decoded |
| S2 security | Indigo decrypts S2 before delivery — transparent to the plugin |
| Proprietary command classes | 0xF0+ manufacturer-specific bytes logged raw but not decoded |
cd "UniversalZWaveSensor.indigoPlugin/Contents/Server Plugin"
python3 test_plugin.py -vNo Indigo installation required — indigo is fully mocked. All tests should pass.
Every log line is prefixed with a millisecond timestamp [HH:MM:SS.mmm] so
events can be correlated tightly with other CliveS plugins (Device Activity
Monitor uses the same convention).
To turn the prefix off (or back on) at any time:
Plugins → Universal Z-Wave Sensor → Toggle Timestamps in Log (on/off)
The setting is stored in pluginPrefs (timestampEnabled) and persists across
restarts. Defaults to ON.
| Version | Date | Changes |
|---|---|---|
| 5.7 | 23-May-2026 | Millisecond timestamp [HH:MM:SS.mmm] prefix on every self.logger line via plugin_utils.install_timestamp_filter(); new "Toggle Timestamps in Log" menu item |
| 5.5 | 04-May-2026 | Fix displayStatus state-not-defined error on Plug/Relay devices — all displayStatus writes now route through _safe_update and silently skip device types that do not define that state |
| 5.4 | 04-May-2026 | Generate Indigo Support Report menu item — dumps manufacturer ID, product type/ID, supported command classes, owner props, and all device states to the Indigo log, formatted for pasting into the Indigo forum; Show Plugin Info menu item added |
| 5.3 | 04-May-2026 | Removed battery/batteryLow/wakeUpInterval states from Plug/Relay device type (mains-powered, irrelevant) |
| 5.2 | 04-May-2026 | Plug/Relay device type (zwaveSensorPlug) — on/off control via actionControlDevice, energy monitoring (W/kWh/V/A), state sync at startup from native device; fix batteryLevel→battery (batteryLevel is a reserved Indigo native property — custom state silently dropped; use battery/Integer instead); Z-Wave protocol filter on native device picker; deviceStartComm re-entry guard (_devices_starting set) fixes maximum recursion depth error when stateListOrDisplayStateIdChanged() re-triggers startup |
| 5.1 | 04-May-2026 | Per-type state lists in Devices.xml — states now declared per device type rather than shared; battery state forced visible via _ensure_states_visible() on startup |
| 5.0 | 03-May-2026 | DOOR_LOCK (CC 0x62) — lock mode, bolt/latch state (v2 door condition bitmask), last user; CENTRAL_SCENE (CC 0x5B) — scene number, key action (pressed/released/held/repeated), timestamp; NOTIFICATION ACCESS_CONTROL extended — manual/RF/keypad/auto lock and unlock ops with user ID extraction; NOTIFICATION HOME_SECURITY extended — intrusion (0x01/0x02) and glass break (0x05/0x06); METER gas (m3/ft3/ccf) and water (m3/ft3/gallons) meter types; SENSOR_MULTILEVEL extended — velocity, watts, voltage, current, air flow, VOC, soil moisture; Battery sensor type — dedicated sensorType with displayStatus and batteryLow flag; batteryLow state on all device types (True if ≤20% or 0xFF sentinel); 10 sensor types; 41 device states |
| 4.0 | 22-Mar-2026 | METER_REPORT v3 voltage (V) and current (A) — Scale2 bit (byte 2 bit 7) now extracted and combined with 2-bit scale to form full 3-bit scale value |
| 3.9 | 22-Mar-2026 | Startup banner in __init__() using raw constructor params; Info.plist standardised (PluginVersion key added — fixes blank version, IwsApiVersion, CFBundleURLTypes, GithubInfo) |
| 3.8 | 22-Mar-2026 | SENSOR_BINARY (CC 0x30) logging moved to DEBUG always — NOTIFICATION is the primary INFO source for motion events |
| 3.7 | 22-Mar-2026 | Log verbosity reduced — INFO only for report types matching device sensorType; secondary fan-out and HS_IDLE moved to DEBUG |
| 3.6 | 22-Mar-2026 | Startup displayStatus initialisation — _init_display_status() called in deviceStartComm(); corrects stale values (e.g. "detected" on Temperature device) immediately on plugin reload |
| 3.5 | 22-Mar-2026 | displayStatus guard per sensorType — motion/NOTIFICATION/SENSOR_BINARY reports no longer overwrite displayStatus on Temperature or Lux devices sharing the same node |
| 3.4 | 22-Mar-2026 | NOTIFICATION event 0x08 = motion DETECTED (not cleared); SENSOR_BINARY type 0x0C added to lookup table |
| 3.3 | 22-Mar-2026 | Fixed serial API frame unwrapping — subscribeToIncoming() delivers full Z-Wave serial frame; _extract_node_and_bytes() now strips SOF+header to expose command payload |
| 3.2 | 22-Mar-2026 | Simplified to single-path UI — always select native Indigo device from dropdown; manual node ID entry removed |
| 3.1 | 22-Mar-2026 | indigo.zwave.subscribeToIncoming() at startup so all Z-Wave bytes received regardless of node ownership; NOTIFICATION byte order auto-detection; native device picker added |
| 3.0 | 21-Mar-2026 | Multi-channel endpoint routing; stale device detection; temperature unit preference (degC/degF); wake-up interval tracking; simulate dialog stays open |
| 2.0 | 21-Mar-2026 | Removed known-device mirror path; plugin now uses raw Z-Wave bytes only |
| 1.0 | 20-Mar-2026 | Initial release |
MIT — free to use, modify, and distribute.