SwitchBot Cloud
Cloud REST integration with SwitchBot devices via the SwitchBot v1.1 OpenAPI. One GEM device row represents a single SwitchBot account. Each zone is one physical device or one IR remote registered on a SwitchBot Hub Mini / Hub 2.
What this driver covers
| Product family | Read | Write |
|---|---|---|
| Bot (switch / press mode) | power, battery | turnOn, turnOff, toggle, press |
| Plug / Plug Mini US-JP | power | turnOn, turnOff |
| Curtain / Curtain 3 | slidePosition, battery, moving | open (turnOn), close (turnOff), setPosition |
| Blind Tilt | slidePosition | open, close, setPosition |
| Meter / Meter Plus / Outdoor Meter | temperature, humidity, battery | — read-only |
| CO2 Meter | temperature, humidity, CO2, battery | — read-only |
| Color Bulb / Strip Light / Ceiling Light | power, brightness, color, colorTemperature | turnOn, turnOff, setBrightness, setColor, setColorTemperature |
| Lock / Lock Pro | lockState, doorState | — (write intentionally out of scope, see below) |
| IR remotes (AC / TV / Fan / STB / Light) via Hub Mini / Hub 2 | — (one-way) | Any IR command name the remote defines |
Explicitly out of scope for this driver:
- SwitchBot Lock write commands (lock / unlock) — safety-critical, wired into a follow-up gated driver.
- The webhook push channel (
/v1.1/webhook) — the driver uses polling. Webhooks can be added later without breaking anything. - Non-cloud Bluetooth-direct control — a companion
switchbot_bledriver is a future item.
Prerequisites
- A SwitchBot account with the devices already paired in the SwitchBot mobile app.
- A SwitchBot Hub Mini or Hub 2 online. All Bluetooth-only SwitchBot devices (Bot, Curtain, Meter, Blind Tilt, Lock) reach the cloud through a Hub; without one, only the plugs and Wi-Fi bulbs work.
- Developer options unlocked in the mobile app:
- Open the SwitchBot app.
- Profile → Preferences.
- Tap App Version 10 times until Developer Options appears.
- Open Developer Options and copy the Token and Secret.
Setup steps
- Under System → Devices, click Add device and pick SwitchBot Cloud.
- Paste the developer Token into
token. - Paste the developer Secret into
api_secret. Both are stored encrypted. - Leave
api_baseon the default. - Save. The driver will call
/v1.1/devices, cache the inventory, and start polling.
Then, one zone per resource you want to control:
- Under System → Zones, click Add zone, pick your SwitchBot device, and set the address per the format below.
Attribute reference
Device attributes
| Name | Required | Description |
|---|---|---|
token | yes | SwitchBot developer token. Sent verbatim in the Authorization header on every call. Stored encrypted. |
api_secret | yes | SwitchBot developer secret. Used to HMAC-SHA256 sign each request; never sent in cleartext. Stored encrypted. |
api_base | no | Override for https://api.switch-bot.com. Leave on the default. |
status_interval | no | Per-zone status poll cadence in ms. Default 60 000, minimum 15 000. SwitchBot rate-limits at 10 000 calls / day / token — see below. |
request_timeout | no | Per-request HTTP timeout in ms. Default 15 000. |
Zone attributes
Zones do not require attributes besides address. Polled fields the driver writes automatically:
power, battery, temperature, humidity, co2, slide_position, brightness, color_temperature, color, device_type, device_name, hub_device_id, moving, lock_state, door_state, and a coarse state derived from power / slide_position / lock_state.
Zone address format
| Address | Refers to |
|---|---|
<deviceId> | A physical device (16 hex chars for Bluetooth devices, e.g. BE12345678AB). Look at deviceList in the get_devices response. |
remote:<deviceId> | An IR remote registered on a Hub. Look at infraredRemoteList in the get_devices response — the deviceId is numeric. |
Run get_devices after saving the device row to enumerate everything the account can see.
Commands
| Name | Args | Purpose |
|---|---|---|
get_devices | — | List physical devices AND IR remotes. |
get_status | address | Live status for a physical device. Not supported for IR remotes (one-way). |
on / off | address | Standard on/off. For Curtain and Blind Tilt, maps to open / close. |
toggle | address | Native for Bot in switch mode. Other zones resolve from cached power. |
press | address | Momentary press — Bot in press mode. |
set_level | address, level | Brightness 0–100 on bulbs / strips / ceiling lights. Position 0–100 on Curtain / Blind Tilt. |
set_color | address, r, g, b | RGB 0–255. |
set_ct | address, kelvin | 2700 – 6500 K for tunable-white bulbs. |
ir_command | address, action, parameter? | Any command name the IR remote defines (turnOn, channelAdd, volumeAdd, setAll, ...). |
raw_command | address, commandType, command, parameter? | Escape hatch for anything the driver does not name explicitly. |
Signing
Every request is signed. The signature covers Authorization + t + nonce — not the request body. The timestamp defends against replay:
sign = base64( HMAC_SHA256( api_secret, token + t + nonce ) )
t— current UNIX time in milliseconds, as a decimal string.nonce— a random UUIDv4.- All three, plus
sign, ride as request headers alongsideAuthorization: <token>.
If your system clock drifts more than a few minutes, SwitchBot returns 401. Confirm timedatectl shows an active NTP sync.
Known limitations
- Bluetooth reachability requires a Hub. Bot, Curtain, Meter, Blind Tilt, and Lock devices only reach the cloud through a Hub Mini or Hub 2. Confirm the Hub is online in the SwitchBot app before troubleshooting missing status.
- IR remotes are one-way. No feedback loop — a TV powered on by the physical remote will not update GEM's
state. - Rate limit is 10 000 calls / day / token. At 60 s polling that supports about seven polled zones with a small buffer for commands. Raise
status_intervalor skip polling on IR-only setups. - Lock write is out of scope. Reading
lockStateis fine; issuing a lock/unlock command would need a hardened confirmation path (safety-critical) that is not wired up yet. - Bulb color is a comma-separated tuple. The driver formats
r:g:bfor you; do not paste JSON intoraw_command. - Occasional 190 errors. SwitchBot's server-side firmware sometimes returns
statusCode: 190. It is usually transient; retry after a few seconds.
Troubleshooting
| Symptom | Likely cause / fix |
|---|---|
401 unauthorized on every call | Token / secret mismatch, or clock drift beyond a few minutes. Verify timedatectl. |
Empty status body | Bluetooth device but the Hub is offline. Check the SwitchBot app. |
statusCode: 161 | Device is unreachable (offline / out of BLE range of the Hub). |
statusCode: 190 | Server-side transient error. Retry. |
| IR command returns 100 OK but nothing happens | Remote was captured against the wrong appliance, or the IR line-of-sight is blocked. Re-teach in the mobile app. |
| Rate-limit errors | 10 000 / day / token exceeded. Raise status_interval. |
Related
- Govee Cloud — analogous "many product types, one cloud" integration.
- Meross Hub — another Wi-Fi / Bluetooth retrofit ecosystem.
- Tuya Cloud — largest of the multi-brand Wi-Fi ecosystems.