<!-- Source: https://docs.captron.com/trms/seh/mqtt-interface -->

# MQTT Communication

SENSORhub SEH devices are controlled and monitored over MQTT. This page describes the MQTT topics and their message payloads. A Modbus TCP interface is available in parallel — see [Modbus Interface](./modbus-interface.md).

## Definitions

- `{product}` is the name of the product, e.g. `SEH101` or `SEH201`.
- `{device-id}` is the unique name of the device and consists of a randomly generated word combination such as `GroovySquareTongue` or `TinyHappyGroup`. This id is used to build the topics and is printed on the device.
- `{Content definition}` is the part of the topic after the `{device-id}`, e.g. `/Pub/MAM`.

All topics follow this pattern:

```text
captron.com/{product}/nd/{device-id}/{Content definition}
```

## Device Information

### Publish — `/Pub/MAM`

Direction: device publishes.

```json
{
  "Content": "/Pub/MAM",
  "BoardName": "lucky_python",
  "Manufacturer": "CAPTRON",
  "Model": "PYTHON-Head",
  "ProductCode": "123456789",
  "SoftwareVersion": "v0.0.1"
}
```

The device broadcasts data which is generic and individual to a device, the configuration which is given to the device during the onboarding process, and all methods which can be called.

### Subscribe — `/Get/MAM`

Direction: device subscribes. Payload: none.

Request device information. The device replies on the corresponding `/Pub/MAM` topic.

## Configuration

### Subscribe — `/Set/Config/MQTT`

Direction: device subscribes.

```json
{
  "Content": "/Set/Config/MQTT",
  "Vendor": "captron",
  "Port": 1883,
  "MQTTServer": "update.oneGrid.captron.com",
  "MQTTUsername": "Captron2022",
  "MQTTPassword": "qwxYT321!",
  "Encryption": false
}
```

Provide connection information specific to the owner of the application, such as the server configuration. If no login credentials are needed, use `null` as the value of `MQTTUsername` and `MQTTPassword`.

This message is used during the automatic onboarding process. Be aware that after a power cycle the device will request this information from the onboarding system again.

### Subscribe — `/Set/Config/LedStrip`

Direction: device subscribes.

```json
{
    "Content": "/Set/Config/LedStrip",
    "Demo": false,
    "LED_STRIP_1":{
        "ColorAlignment": {"Active": true, "R": 255, "G": 180, "B": 255}
    },
    "LED_STRIP_2":{
        "ColorAlignment": {"Active": true, "R": 255, "G": 180, "B": 255}
    },
    etc...
}
```

Use-case specific configuration of the LED strips (e.g. length as count of LEDs).

- For FW v0.2.10 and higher this message is no longer mandatory. The default used is 180 LEDs per strip.
- The boolean `Demo` enables/disables the demo mode. If enabled, the device plays different colors and effects on output 1 and 2. This setting is stored persistently in memory — if you enable the demo mode it is also active after a power cycle.
- From FW V0.3.10-13-G225F748 onward, color alignment is possible for each LED strip. Set the `Active` flag to `true` and set the corresponding RGB values in the range 0–255.

## Activate LED strip

### Subscribe — `/Set/Data/LedStrip`

Direction: device subscribes.

```json
{
  "Content": "/Set/Data/LedStrip",
  "LED_STRIP_1": {
    "Active": true,
    "Segments": [
      {
        "StartLED": 0,
        "StopLED": 30,
        "Speed": 190,
        "Effect": 1,
        "Colors": [
          {
            "R": 0,
            "G": 150,
            "B": 0
          },
          {
            "R": 0,
            "G": 150,
            "B": 0
          }
        ]
      }
    ]
  }
}
```

Light up the LEDs.

- Use the `Active` flag to switch the strip on or off.
- Effects:
  - 1: FX_MODE_STATIC
  - 2: FX_MODE_BLINK
  - 3: FX_MODE_FLASH
  - 4: FX_MODE_LEADING_LINES
  - 5: FX_MODE_LEADING_LINES_REVERSE
  - 6: FX_MODE_MULTIPICKER
  - 7: FX_MODE_PICK (needs min. FW version V0.3.7)
  - 8: FX_MODE_PLACE (needs min. FW version V0.3.7)
  - 200: FX_MODE_CUSTOM_KNIGHT_RIDER
- Speed from 1 (slow) to 250 (fast).
- Multiple colors apply only to some effects such as FX_MODE_MULTIPICKER. In that case the colors change between the RGB values specified in the `Colors` array. For all other effects only the first color in the array applies.
- 6 segments with different colors/effects can be set. Depending on the maximum MQTT message size, more segments can be set. The MQTT message size must be below 4k.
- This command can be ignored if a power limit is reached. In this case an error message is logged to inform the user.

## Control of SMC buttons (SEH20x/SEH11 devices)

Control of SMC buttons (SENSORswitches) is available on SEH11 and SEH201. The SMC buttons connected to the hub are controlled through a single topic. The Modbus interface offers the same SMC control in parallel — see [Modbus Interface](./modbus-interface.md).

Implemented in FW V0.2.5.

### Subscribe — `/Set/Data/Smc`

Direction: device subscribes.

```json
{
  "Content": "/Set/Data/Smc",
  "Address": "{Button address, HUB or ALL_SENSORS}",
  "CommandType": "{Command Type}",
  "Offset": "{Offset}",
  "Payload": "{Payload}"
}
```

- **Address** — a specific button address, `HUB` (the SEH itself), or `ALL_SENSORS` (broadcast to all buttons).
- **CommandType** and **Offset** together select which command is executed and how the `Payload` string is interpreted.

The following commands are available:

<table>
  <colgroup>
    <col style={{ minWidth: '160px' }} />
    <col />
    <col />
    <col />
  </colgroup>
  <thead>
    <tr>
      <th>Command</th>
      <th>CommandType</th>
      <th>Offset</th>
      <th>Payload</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Set LED ring and display</td>
      <td>SET_PARAMETER</td>
      <td>PRE_BUTTON_MODE or POST_BUTTON_MODE</td>
      <td><code>&#123;ENABLED, DISABLED or LONGPRESS_ENABLED&#125;/&#123;Quantity&#125;/&#123;LED ring color&#125;/&#123;LED ring effect&#125;/&#123;Display text&#125;</code></td>
    </tr>
    <tr>
      <td>Set button rotation</td>
      <td>SET_PARAMETER</td>
      <td>BUTTON_ROTATE</td>
      <td><code>BUTTON_ROTATION_NORMAL</code> or <code>BUTTON_ROTATION_UPSIDEDOWN</code></td>
    </tr>
    <tr>
      <td>Set longpress time</td>
      <td>SET_PARAMETER</td>
      <td>LONGPRESS_TIME</td>
      <td>Milliseconds divided by 10 (max. 2.55 seconds)</td>
    </tr>
    <tr>
      <td>Assign button address</td>
      <td>SET_STATUS</td>
      <td>ADDRESS_TO_BE_ASSIGNED</td>
      <td>Number to assign</td>
    </tr>
    <tr>
      <td>Special commands (switch Pre/Post state, reboot, etc.)</td>
      <td>SET_STATUS</td>
      <td>SPECIAL_COMMANDS</td>
      <td><code>PRE_PRESSED_STATE</code>, <code>POST_PRESSED_STATE</code>, <code>REBOOT</code>, <code>SHOW_CURRENT_ADDRESS</code> or <code>LONG_PRESSED_STATE</code></td>
    </tr>
    <tr>
      <td>Polling function (Address = HUB)</td>
      <td>SET_PARAMETER</td>
      <td>(none)</td>
      <td>Polling addresses separated by <code>/</code> (up to 6), e.g. <code>1002/1003/1004</code>; <code>0000</code> switches polling off</td>
    </tr>
  </tbody>
</table>

**Special commands** (Offset `SPECIAL_COMMANDS`):

- `PRE_PRESSED_STATE` — set to pre state
- `POST_PRESSED_STATE` — set to post state
- `REBOOT` — restart button
- `SHOW_CURRENT_ADDRESS` — show button address
- `LONG_PRESSED_STATE` — set to longpress state (needs min. SEH firmware V0.2.27-3)

:::note
Older firmware versions do not apply the **button rotation** setting after a power cycle. In that case the command must be resent after each power cycle of the SMC button.<br/>
The **longpress time** command needs min. firmware V5.3.9 on the SMC button.
:::

### Publish — `/Pub/Data/Smc`

Direction: device publishes.

When polling is active for a button address, a button touch is reported on this topic:

```json
{
  "Content": "/Pub/Data/Smc",
  "Address": "{touched button address}",
  "CommandType": "SET_STATUS",
  "Payload": "POST_PRESSED_STATE"
}
```

### Setting LED ring and display

For the **Set LED ring and display** command (CommandType `SET_PARAMETER`, Offset `PRE_BUTTON_MODE` or `POST_BUTTON_MODE`), the `Payload` is a `/`-separated string:

```text
{ENABLED, DISABLED or LONGPRESS_ENABLED}/{Quantity}/{LED ring color}/{LED ring effect}/{Display text}
```

**Button mode** (first field):

- `ENABLED` — button can be confirmed; LED ring and display can be controlled.
- `DISABLED` — button can NOT be confirmed; LED ring and display can be controlled.
- `LONGPRESS_ENABLED` — button goes to the longpress state after keeping the touch for a certain time (default 2 seconds); the LED ring and display for that state are set using the `POST_BUTTON_MODE` offset.

**Quantity** — a number from 1 to 9999. It is automatically aligned in the middle of the display.

**LED ring color:**

- `COLOFF`
- `COLRED`
- `COLGREEN`
- `COLBLUE`
- `COLYELLOW`
- `COLMAGENTA`
- `COLCYAN`
- `COLWHITE`

**LED ring effect:**

- `SOLID_RING`
- `FLASH_RING`
- `CONFIRM`
- `POINT_ANIMATED_CLOCK`
- `CIRCLE_ANIMATED_CLOCK`
- `SOLID_ARROW_UP`, `SOLID_ARROW_DOWN`, `SOLID_ARROW_LEFT`, `SOLID_ARROW_RIGHT`
- `FLASH_ARROW_UP`, `FLASH_ARROW_DOWN`, `FLASH_ARROW_LEFT`, `FLASH_ARROW_RIGHT`
- `ANIMATED_ARROW_UP`, `ANIMATED_ARROW_DOWN`, `ANIMATED_ARROW_LEFT`, `ANIMATED_ARROW_RIGHT`
- Diagonal arrows: `SOLID_ARROW_UP_LEFT`, `SOLID_ARROW_UP_RIGHT`, `SOLID_ARROW_DOWN_LEFT`, `SOLID_ARROW_DOWN_RIGHT`, `FLASH_ARROW_UP_LEFT`, `FLASH_ARROW_UP_RIGHT`, `FLASH_ARROW_DOWN_LEFT`, `FLASH_ARROW_DOWN_RIGHT`

:::note
The diagonal arrow effects need min. firmware V5.3.7 on the SMC button.
:::

**Display text** — max. 4 characters. Some characters cannot be displayed due to 7-segment restrictions. Use `@` as a space character (examples: `@Go@`, `donE`).

If both **Quantity** and **Display text** are defined, **Quantity** is used. When **Display text** is used, no automatic alignment is done — the user must take care of it (e.g. a left-aligned number as `42@@`, a right-aligned number as `@@42`). If **Quantity** is used, the alignment is done automatically.

### Examples

Sending to the SMC button with address `1000`.

Set LED ring color to green (flashing) and display a quantity of `42`:

```json
{
  "Content": "/Set/Data/Smc",
  "Address": "1000",
  "CommandType": "SET_PARAMETER",
  "Offset": "PRE_BUTTON_MODE",
  "Payload": "ENABLED/42/COLGREEN/FLASH_RING"
}
```

Set LED ring color to blue and display `donE` in the post-pressed / longpress state:

```json
{
  "Content": "/Set/Data/Smc",
  "Address": "1000",
  "CommandType": "SET_PARAMETER",
  "Offset": "POST_BUTTON_MODE",
  "Payload": "ENABLED//COLBLUE/SOLID_RING/donE"
}
```

Switch the button to the pre-pressed state:

```json
{
  "Content": "/Set/Data/Smc",
  "Address": "1000",
  "CommandType": "SET_STATUS",
  "Offset": "SPECIAL_COMMANDS",
  "Payload": "PRE_PRESSED_STATE"
}
```

Set the longpress time to 1 second:

```json
{
  "Content": "/Set/Data/Smc",
  "Address": "1000",
  "CommandType": "SET_PARAMETER",
  "Offset": "LONGPRESS_TIME",
  "Payload": "100"
}
```

Sending to all connected SMC buttons — switch all buttons to the pre-pressed state:

```json
{
  "Content": "/Set/Data/Smc",
  "Address": "ALL_SENSORS",
  "CommandType": "SET_STATUS",
  "Offset": "SPECIAL_COMMANDS",
  "Payload": "PRE_PRESSED_STATE"
}
```

## Health and Status

### Publish — `/Pub/Health/LedStrip`

Direction: device publishes.

```json
{
  "Content": "/Pub/Health/LedStrip",
  "Firmware": "V0.1.0",
  "LED_STRIP_1": {
    "Length": 42,
    "Active": true,
    "CheckPassed": true
  },
  "LED_STRIP_2": {
    "Length": 42,
    "Active": false,
    "CheckPassed": true
  },
  "LED_STRIP_3": {
    "Length": 42,
    "Active": false,
    "CheckPassed": true
  },
  "LED_STRIP_4": {
    "Length": 0,
    "Active": false,
    "CheckPassed": true
  },
  "LED_STRIP_5": {
    "Length": 0,
    "Active": false,
    "CheckPassed": true
  }
}
```

The health of the LED strips connected to the board. This message is published after powering on the device.

### Subscribe — `/Get/Health/LedStrip`

Direction: device subscribes. Payload: none.

Request LED strip health and information. The device replies on the corresponding `/Pub/Health/LedStrip` topic.

### Publish — `/Pub/Health/SysLog`

Direction: device publishes.

Payload: event logging (info, warn, error, etc.), version, uptime, IP address, etc.

The syslog of a device. This message is published every 6 h and also when the LED strip health is requested. Diagnosis messages (e.g. detected wiring errors, overloads, etc.) are also published on this topic — these messages are marked with `[DIAGNOSIS]`.

## Common settings

### Subscribe — `/Set/Config/Common`

Direction: device subscribes.

```json
{
    "Content": "/Set/Config/Common",
    "LogLevel": {1 to 6},
    "StartDiagnosis": true
}
```

**LogLevel** — sets the log level. The default setting is `3` (Warning). The following levels can be set:

- 1 – Fatal
- 2 – Error
- 3 – Warning (default)
- 4 – Notice (logs e.g. the response when an LED segment is activated)
- 5 – Info
- 6 – Trace

Log messages with the chosen and lower numbers (higher severity) are published on the syslog topic. E.g. setting the log level to 4 forces the device to publish log messages with the rankings Fatal, Error, Warning and Notice. The log level setting is not saved in flash — the device always starts with the default setting.

**StartDiagnosis** (only for devices SEH101 and SEH201) — starts diagnosis on the output clamps, checking for e.g. wiring faults. Possible errors are published on the syslog topic. Diagnosis is automatically run at startup; this flag triggers the functionality once.

## Firmware Update

### Subscribe — `/Call/FirmwareUpdate`

Direction: device subscribes.

```json
{
  "Content": "/Call/FirmwareUpdate",
  "Url": "http://onegrid-fwupd.germanywestcentral.cloudapp.azure.com:80/ota/firmware_V0.3.9-pythonhB.img"
}
```

Start the update process.

:::note
SEH201 uses firmware files named `firmware_V0.x.y-pythonhB_smc.img`.
:::

## Time distribution

### Subscribe — `/Set/Config/Time`

Direction: device subscribes. Topics:

```text
captron.com/Time
captron.com/{product}/nd/{device-id}/Set/Config/Time
```

```json
{
  "Content": "/Set/Config/Time",
  "DateTime": "%Y-%m-%d %H:%M:%S"
}
```

Distribute time to each device. String with the format `%Y-%m-%d %H:%M:%S`, e.g. `2023-02-28T11:18:30`.

## Status signalisation

At startup the device status is signaled by the connected LED strips. To help during installation (mapping strips to outputs), a different number of LEDs light up on each output: one LED lights up on output 1, two LEDs light up on output 2, etc. The signalisation colors are shown until the first `/Set/Data` command.

<table>
  <thead>
    <tr>
      <th>Color</th>
      <th>Status</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Red</td>
      <td>Ethernet/WiFi connection attempt, no Ethernet/WiFi connection</td>
    </tr>
    <tr>
      <td>Yellow</td>
      <td>MQTT connection attempt, no MQTT connection</td>
    </tr>
    <tr>
      <td>Blue</td>
      <td>Fallback mechanism active (planned from V0.2.33/V0.3.6), check configuration and/or network connection</td>
    </tr>
    <tr>
      <td>Cyan/Green-Blue</td>
      <td>Connection established — to the onboarding service (if no user MQTT is configured) or to the user MQTT (if it is configured)</td>
    </tr>
  </tbody>
</table>

## Diagnosis messages (for SEHx01 devices)

Diagnosis messages are published on the syslog topic.

<table>
  <thead>
    <tr>
      <th>Failure</th>
      <th>Message</th>
    </tr>
  </thead>
  <tbody>
    <tr>
      <td>Voltage for LEDs not in range (4.5 V – 5.5 V), e.g. weak USB power supply</td>
      <td><code>[DIAGNOSIS] led voltage outside range</code></td>
    </tr>
    <tr>
      <td>LED current below expected current for activated segments, e.g. LED strip damaged, LEDs activated outside of strip length</td>
      <td><code>[DIAGNOSIS] expected current not in range</code></td>
    </tr>
    <tr>
      <td>
        Wiring error or over current, details in ERROR_BITS:
        <ul>
          <li>1: wiring error on Data/GND pin</li>
          <li>2, 4: wiring error on Vled/GND pin</li>
          <li>32: LED power reached power supply limit</li>
        </ul>
      </td>
      <td><code>[DIAGNOSIS] failed: &#123;ERROR_BITS&#125;</code></td>
    </tr>
  </tbody>
</table>
