homieiot/convention

Changes

Changes from v3.0.1 to v4.0.0

Commits

Differences


v3.0.1
v4.0.0
n2path: https://github.com/homieiot/convention/tree/v3.0.1n2path: https://github.com/homieiot/convention/tree/v4.0.0
3source: README.md3source: convention.md
4version: v3.0.14version: v4.0.0
5releasedate: 27. October 20185releasedate: 18. July 2019
n19 n
20Nodes can be **arrays**.
21For example, instead of creating two `lights` node to control front lights and back lights independently, we can set the `lights` node to be an array with two elements.
n30Properties can be **settable**.n
31For example, you don't want your `temperature` property to be settable in case of a temperature sensor (like the car example), but to be settable in case of a thermostat.
32
33Properties can be **retained**.
34A property is retained by default. A non-retained property would be useful for momentary events (door bell pressed).
35
36A combination of those flags compiles into this list:
37
38* **retained + non-settable**: The node publishes a property state (temperature sensor)
39* **retained + settable**: The node publishes a property state, and can receive commands for the property (by controller or other party) (lamp power)
40* **non-retained + non-settable**: The node publishes momentary events (door bell pressed)
41* **non-retained + settable**: The node publishes momentary events, and can receive commands for the property (by controller or other party) (brew coffee)
42
n50----n
51
52### Base Topic
53
54The base topic you will see in the following convention will be `homie/`.
55If this base topic does not suit your needs (in case of, e.g., a public broker), you can choose another.
56
57Be aware, that only the default base topic `homie/` is eligible for automatic discovery by third party controllers.
58
59----
60
n69When the MQTT connection to the broker is established or re-established, the device MUST send its attributes to the broker immediately.n
n71<table>n43The following device attributes are mandatory and MUST be send, even if it is just an empty string.
72 <tr>
73 <th>Topic</th>
74 <th>Direction</th>
75 <th>Description</th>
76 <th>Retained</th>
77 <th>Required</th>
78 </tr>
79 <tr>
80 <td>$homie</td>
81 <td>Device → Controller</td>
82 <td>Version of the Homie convention the device conforms to</td>
83 <td>Yes</td>
84 <td>Yes</td>
85 </tr>
86 <tr>
87 <td>$name</td>
88 <td>Device → Controller</td>
89 <td>Friendly name of the device</td>
90 <td>Yes</td>
91 <td>Yes</td>
92 </tr>
93 <tr>
94 <td>$state</td>
95 <td>Device → Controller</td>
96 <td>
97 See <a href="#device-behavior">Device behavior</a>
98 </td>
99 <td>Yes</td>
100 <td>Yes</td>
101 </tr>
102 <tr>
103 <td>$localip</td>
104 <td>Device → Controller</td>
105 <td>IP of the device on the local network</td>
106 <td>Yes</td>
107 <td>Yes</td>
108 </tr>
109 <tr>
110 <td>$mac</td>
111 <td>Device → Controller</td>
112 <td>Mac address of the device network interface. The format MUST be of the type <code>A1:B2:C3:D4:E5:F6</code></td>
113 <td>Yes</td>
114 <td>Yes</td>
115 </tr>
116 <tr>
117 <td>$fw/name</td>
118 <td>Device → Controller</td>
119 <td>Name of the firmware running on the device. Allowed characters are the same as the device ID</td>
120 <td>Yes</td>
121 <td>Yes</td>
122 </tr>
123 <tr>
124 <td>$fw/version</td>
125 <td>Device → Controller</td>
126 <td>Version of the firmware running on the device</td>
127 <td>Yes</td>
128 <td>Yes</td>
129 </tr>
130 <tr>
131 <td>$nodes</td>
132 <td>Device → Controller</td>
133 <td>
134 Nodes the device exposes, with format <code>id</code> separated by a <code>,</code> if there are multiple nodes.
135 To make a node an array, append <code>[]</code> to the ID.
136 </td>
137 <td>Yes</td>
138 <td>Yes</td>
139 </tr>
140 <tr>
141 <td>$implementation</td>
142 <td>Device → Controller</td>
143 <td>An identifier for the Homie implementation (example <code>esp8266</code>)</td>
144 <td>Yes</td>
145 <td>Yes</td>
146 </tr>
147 <tr>
148 <td>$implementation/#</td>
149 <td>Controller → Device or Device → Controller</td>
150 <td>You can use any subtopics of <code>$implementation</code> for anything related to your specific Homie implementation.</td>
151 <td>Yes or No, depending of your implementation</td>
152 <td>No</td>
153 </tr>
154 <tr>
155 <td>$stats</td>
156 <td>Device → Controller</td>
157 <td>Specify all optional stats that the device will announce, with format <code>stats</code> separated by a <code>,</code> if there are multiple stats. See next section for an example</td>
158 <td>Yes</td>
159 <td>Yes</td>
160 </tr>
161 <tr>
162 <td>$stats/interval</td>
163 <td>Device → Controller</td>
164 <td>Interval in seconds at which the device refreshes its <code>$stats/+</code>: See next section for details about statistical attributes</td>
165 <td>Yes</td>
166 <td>Yes</td>
167 </tr>
168</table>
nn45| Topic | Description |
46|-------------|--------------------------------------------------------------------------:|
47| $homie | The implemented Homie convention version |
48| $name | Friendly name of the device |
49| $state | See [Device Lifecycle](#device-lifecycle) |
50| $nodes | [Nodes](#nodes) the device exposes, separated by `,` for multiple ones. |
51| $extensions | Supported extensions, separated by `,` for multiple ones. |
52
53Optional topics include:
54
55| Topic | Description |
56|-----------------|-------------------------------|
57| $implementation | An identifier for the Homie implementation (example "esp8266") |
58
170For example, a device with an ID of `super-car` that comprises off a `wheels`, `engine` and a `lights` node would send:59For example, a device with an ID of `super-car` that comprises of a `wheels`, `engine` and a `lights` node would send:
n175homie/super-car/$localip → "192.168.0.10"n
176homie/super-car/$mac → "DE:AD:BE:EF:FE:ED"
177homie/super-car/$fw/name → "weatherstation-firmware"
178homie/super-car/$fw/version → "1.0.0"
n181homie/super-car/$stats/interval → "60"n
n185#### Device Behaviorn69#### Device Lifecycle
n187The `$state` device attribute represents, as the name suggests, the current state of the device.n71The `$state` device attribute represents the current state of the device.
n191This is the first message that must that must be sent.n75This state is optional, and may be sent if the device takes a long time to initialize, but wishes to announce to consumers that it is coming online.
192* **`ready`**: this is the state the device is in when it is connected to the MQTT broker, has sent all Homie messages and is ready to operate.76* **`ready`**: this is the state the device is in when it is connected to the MQTT broker, has sent all Homie messages and is ready to operate. A Homie Controller can assume default values for all optional topics.
193You have to send this message after all other announcements message have been sent.
n203#### Device Statisticsn
204
205* `homie` / `device ID` / `$stats`/ **`$device-statistic-attribute`**:
206The `$stats/` hierarchy allows to send device attributes that change over time. The device MUST send them every `$stats/interval` seconds.
207
208<table>
209 <tr>
210 <th>Topic</th>
211 <th>Direction</th>
212 <th>Description</th>
213 <th>Retained</th>
214 <th>Required</th>
215 </tr>
216 <tr>
217 <td>$stats/uptime</td>
218 <td>Device → Controller</td>
219 <td>Time elapsed in seconds since the boot of the device</td>
220 <td>Yes</td>
221 <td>Yes</td>
222 </tr>
223 <tr>
224 <td>$stats/signal</td>
225 <td>Device → Controller</td>
226 <td>Signal strength in %</td>
227 <td>Yes</td>
228 <td>No</td>
229 </tr>
230 <tr>
231 <td>$stats/cputemp</td>
232 <td>Device → Controller</td>
233 <td>CPU Temperature in °C</td>
234 <td>Yes</td>
235 <td>No</td>
236 </tr>
237 <tr>
238 <td>$stats/cpuload</td>
239 <td>Device → Controller</td>
240 <td>
241 CPU Load in %.
242 Average of last <code>$interval</code> including all CPUs
243 </td>
244 <td>Yes</td>
245 <td>No</td>
246 </tr>
247 <tr>
248 <td>$stats/battery</td>
249 <td>Device → Controller</td>
250 <td>Battery level in %</td>
251 <td>Yes</td>
252 <td>No</td>
253 </tr>
254 <tr>
255 <td>$stats/freeheap</td>
256 <td>Device → Controller</td>
257 <td>Free heap in bytes</td>
258 <td>Yes</td>
259 <td>No</td>
260 </tr>
261 <tr>
262 <td>$stats/supply</td>
263 <td>Device → Controller</td>
264 <td>Supply Voltage in V</td>
265 <td>Yes</td>
266 <td>No</td>
267 </tr>
268</table>
269
270For example, our `super-car` device with `$stats/interval` value "60" is supposed to send its current values every 60 seconds:
271
272```java
273homie/super-car/$stats → "uptime,cputemp,signal,battery"
274homie/super-car/$stats/uptime → "120"
275homie/super-car/$stats/cputemp → "48"
276homie/super-car/$stats/signal → "24"
277homie/super-car/$stats/battery → "80"
278```
279
280----
281
n290A node attribute MUST be one of these:n
n292<table>n95All listed attributes are **required**. A node attribute MUST be one of these:
293 <tr>96
294 <th>Topic</th>97| Topic | Description |
295 <th>Direction</th>98|-------------|-------------------------------------------------------------------------------------------|
296 <th>Description</th>99| $name | Friendly name of the Node |
297 <th>Retained</th>100| $type | Type of the node |
298 <th>Required</th>101| $properties | Exposed properties, separated by `,` for multiple ones. |
299 </tr>
300 <tr>
301 <td>$name</td>
302 <td>Device → Controller</td>
303 <td>Friendly name of the Node</td>
304 <td>Yes</td>
305 <td>Yes</td>
306 </tr>
307 <tr>
308 <td>$type</td>
309 <td>Device → Controller</td>
310 <td>Type of the node</td>
311 <td>Yes</td>
312 <td>Yes</td>
313 </tr>
314 <tr>
315 <td>$properties</td>
316 <td>Device → Controller</td>
317 <td>
318 Properties the node exposes, with format <code>id</code> separated by a <code>,</code> if there are multiple nodes.
319 </td>
320 <td>Yes</td>
321 <td>Yes</td>
322 </tr>
323 <tr>
324 <td>$array</td>
325 <td>Device → Controller</td>
326 <td>Range separated by a <code>-</code>. e.g. <code>0-2</code> for an array with the indexes <code>0</code>, <code>1</code> and <code>2</code></td>
327 <td>Yes</td>
328 <td>Yes, if the node is an array</td>
329 </tr>
330</table>
n340----n
341
n347* A property value (e.g. a sensor reading) is directly published to the property topic, e.g.:n116* A property payload (e.g. a sensor reading) is directly published to the property topic, e.g.:
nn120
121* Properties can be **settable**.
122 For example, you don't want your `temperature` property to be settable in case of a temperature sensor
123 (like the car example), but to be settable in case of a thermostat.
124
125* Properties can be **retained**.
126 A property is retained by default. A non-retained property would be useful for momentary events (door bell pressed).
127
128A combination of those flags compiles into this list:
129
130* **retained + non-settable**: The node publishes a property state (temperature sensor)
131* **retained + settable**: The node publishes a property state, and can receive commands for the property (by controller or other party) (lamp power)
132* **non-retained + non-settable**: The node publishes momentary events (door bell pressed)
133* **non-retained + settable**: The node publishes momentary events, and can receive commands for the property (by controller or other party) (brew coffee)
134
n355A property attribute MUST be one of these:n
n357<table>n140The following attributes are required:
358 <tr>141
359 <th>Topic</th>142| Topic | Description | Payload type |
360 <th>Direction</th>143|-----------|------------------------------------------------------|---------------------------------------------|
361 <th>Description</th>144| $name | Friendly name of the property. | String |
362 <th>Valid values</th>145| $datatype | The data type. See [Payloads](#payloads). | Enum: \[integer, float, boolean,string, enum, color\] |
363 <th>Retained</th>146
364 <th>Required (Default)</th>147The following attributes are optional:
365 </tr>148
366 <tr>149| Topic | Description | Payload type |
367 <td>$name</td>150|-----------|------------------------------------------------------|---------------------------------------------|
368 <td>Device → Controller</td>151| $format | Specifies restrictions or options for the given data type | See below |
369 <td>Friendly name of the property.</td>152| $settable | Settable (<code>true</code>). Default is read-only (<code>false</code>) | Boolean |
370 <td>Any String</td>153| $retained | Non-retained (<code>false</code>). Default is Retained (<code>true</code>). | Boolean |
371 <td>Yes</td>154| $unit | Optional unit of this property. See list below. | String |
372 <td>No ("")</td>
373 </tr>
374 <tr>
375 <td>$settable</td>
376 <td>Device → Controller</td>
377 <td>Specifies whether the property is settable (<code>true</code>) or readonly (<code>false</code>)</td>
378 <td><code>true</code> or <code>false</code></td>
379 <td>Yes</td>
380 <td>No (<code>false</code>)</td>
381 </tr>
382 <tr>
383 <td>$retained</td>
384 <td>Device → Controller</td>
385 <td>Specifies whether the property is retained (<code>true</code>) or non-retained (<code>false</code>). Publishing to a non-retained property topic MUST always happen with the MQTT 'retain' flag off.</td>
386 <td><code>true</code> or <code>false</code></td>
387 <td>Yes</td>
388 <td>No (<code>true</code>)</td>
389 </tr>
390 <tr>
391 <td>$unit</td>
392 <td>Device → Controller</td>
393 <td>
394 A string containing the unit of this property.
395 You are not limited to the recommended values, although they are the only well known ones that will have to be recognized by any Homie consumer.
396 </td>
397 <td>
398 Recommended:<br>
399 <code>°C</code> Degree Celsius<br>
400 <code>°F</code> Degree Fahrenheit<br>
401 <code>°</code> Degree<br>
402 <code>L</code> Liter<br>
403 <code>gal</code> Galon<br>
404 <code>V</code> Volts<br>
405 <code>W</code> Watt<br>
406 <code>A</code> Ampere<br>
407 <code>%</code> Percent<br>
408 <code>m</code> Meter<br>
409 <code>ft</code> Feet<br>
410 <code>Pa</code> Pascal<br>
411 <code>psi</code> PSI<br>
412 <code>#</code> Count or Amount
413 </td>
414 <td>Yes</td>
415        <td>No ("")</td>
416 </tr>
417 <tr>
418 <td>$datatype</td>
419 <td>Device → Controller</td>
420 <td>Describes the format of data.</td>
421 <td>
422 <code>integer</code>,
423 <code>float</code>,
424 <code>boolean</code>,
425 <code>string</code>,
426 <code>enum</code>,
427 <code>color</code>
428 </td>
429 <td>Yes</td>
430 <td>No (<code>string</code>)</td>
431 </tr>
432 <tr>
433 <td>$format</td>
434 <td>Device → Controller</td>
435 <td>
436 Describes what are valid values for this property.
437 </td>
438 <td>
439 <ul>
440 <li>
441 <code>from:to</code> Describes a range of values e.g. <code>10:15</code>.
442 <br>Valid for datatypes <code>integer</code>, <code>float</code>
443 </li>
444 <li>
445 <code>value,value,value</code> for enumerating all valid values.
446 Escape <code>,</code> by using <code>,,</code>. e.g. <code>A,B,C</code> or <code>ON,OFF,PAUSE</code>.
447 <br>Valid for datatypes <code>enum</code>
448 </li>
449 <li>
450 <code>rgb</code> to provide colors in RGB format e.g. <code>255,255,0</code> for yellow.
451 <code>hsv</code> to provide colors in HSV format e.g. <code>60,100,100</code> for yellow.
452 <br>Valid for datatype <code>color</code>
453 </li>
454 </ul>
455 </td>
456 <td>Yes</td>
457 <td>No for $datatype <code>string</code>,<code>integer</code>,<code>float</code>,<code>boolean</code>. Yes for <code>enum</code>,<code>color</code></td>
458 </tr>
459</table>
nn167Format:
168
169* For `integer` and `float`: Describes a range of payloads e.g. `10:15`
170* For `enum`: `payload,payload,payload` for enumerating all valid payloads.
171* For `color`:
172 - `rgb` to provide colors in RGB format e.g. `255,255,0` for yellow.
173 - `hsv` to provide colors in HSV format e.g. `60,100,100` for yellow.
174
175Recommended unit strings:
176
177* `°C`: Degree Celsius
178* `°F`: Degree Fahrenheit
179* `°`: Degree
180* `L`: Liter
181* `gal`: Galon
182* `V`: Volts
183* `W`: Watt
184* `A`: Ampere
185* `%`: Percent
186* `m`: Meter
187* `ft`: Feet
188* `Pa`: Pascal
189* `psi`: PSI
190* `#`: Count or Amount
191
192You are not limited to the recommended values, although they are the only well known ones that will have to be recognized by any Homie consumer.
193
194#### Property command topic
195
472* `homie` / `device ID` / `node ID` / `property ID` / **`set`**: the device can subscribe to this topic if the property is **settable** from the controller, in case of actuators.196* `homie` / `device ID` / `node ID` / `property ID` / **`set`**: The device must subscribe to this topic if the property is **settable** (in case of actuators for example).
n474Homie is state-based.n198A Homie controller publishes to the `set` command topic with non-retained messages only.
475You don't tell your smartlight to `turn on`, but you tell it to put its `power` state to `on`.
476This especially fits well with MQTT, because of retained message.
n478For example, a `kitchen-light` device exposing a `light` node would subscribe to `homie/kitchen-light/light/power/set` and it would receive:n200The assigned and processed payload must be reflected by the Homie device in the property topic `homie` / `device ID` / `node ID` / `property ID` as soon as possible.
201This property state update not only informs other devices about the change but closes the control loop for the commanding controller, important for deterministic interaction with the client device.
202
203To give an example: A `kitchen-light` device exposing the `light` node with a settable `power` property subscribes to the topic `homie/kitchen-light/light/power/set` for commands:
n484The device would then turn on the light, and update its `power` state.n209In response the device will turn on the light and upon success update its `power` property state accordingly:
485This provides pessimistic feedback, which is important for home automation.
n490 n
491### Arrays
492
493A node can be an array if you've added `[]` to its ID in the `$nodes` device attribute, and if its `$array` attribute is set to the range of the array.
494Let's consider we want to control independently the front lights and back lights of our `super-car`. Our `lights` node array would look like this. Note that the topic for an element of the array node is the name of the node followed by a `_` and the index getting updated:
495
496```java
497homie/super-car/$nodes → "lights[]"
498
499homie/super-car/lights/$name → "Lights"
500homie/super-car/lights/$properties → "intensity"
501homie/super-car/lights/$array → "0-1"
502
503homie/super-car/lights/intensity/$name → "Intensity"
504homie/super-car/lights/intensity/$settable → "true"
505homie/super-car/lights/intensity/$unit → "%"
506homie/super-car/lights/intensity/$datatype → "integer"
507homie/super-car/lights/intensity/$format → "0:100"
508
509homie/super-car/lights_0/$name → "Back lights"
510homie/super-car/lights_0/intensity → "0"
511homie/super-car/lights_1/$name → "Front lights"
512homie/super-car/lights_1/intensity → "100"
513```
514
515Note that you can name each element in your array individually ("Back lights", etc.).
516
517----
518
519### Broadcast Channel214## Broadcast Channel
n521Homie defines a broadcast channel, so a controller is able to broadcast a message to every Homie devices:n216Homie defines a broadcast channel, so a controller is able to broadcast a message to all Homie devices:
t535 t
536----
537----