MQTT¶
The ingest path: everything a hive measures enters the system here. Two processes that only make sense together โ a broker that accepts what the nodes publish, and a handler that decodes those messages and hands them to the core library to be stored.
The broker¶
Mosquitto, the entry point for sensor data. It is an off-the-shelf eclipse-mosquitto:2.0 image,
so mosquitto/ in meshbee-server holds no application code โ only configuration and runtime
state, bind-mounted into the container.
| Ports | 1883 MQTT (used) ยท 9001 WebSockets (configured but unused) |
| Config | config/mosquitto.conf โ the only tracked source file |
| Credentials | config/passwd, bcrypt-hashed, generated by make mqtt-passwd. Gitignored |
| Logs | stdout, rotated by Docker |
The broker will not start without config/passwd
It runs with allow_anonymous false. A missing password file is the single most common cause of
a failing stack. make setup generates it on a fresh clone; regenerate it with
make mqtt-passwd whenever MQTT_PASSWORD changes, since the file holds a hash and does not
follow the variable.
The broker stores nothing of ours โ readings live in PostgreSQL, so clearing data/ costs at
most undelivered messages. There are no ACLs today and every node shares one credential, so a
compromised node cannot be revoked individually.
The handler¶
A headless subscriber: no HTTP surface, no port, no clients. It is a loop between Mosquitto and
meshbee_core that decodes each payload, validates it, and hands it over to be stored.
It writes no SQL of its own. It opens a transaction and calls one service โ
meshbee_core.services.ingest โ and the core library owns every query from there. That is the
layer rule the whole server is built on, and it is why a reading arriving over MQTT produces the
same database row as one posted to POST /api/admin/letture.
- Subscribes to
beehive/+/data; nodes publish tobeehive/<id_nodo>/data. - Enforces the measurement ranges โ temperature โ50โฆ100 ยฐC, humidity 0โฆ100 %, weight โฅ 0 kg.
- Auto-provisions: a node that starts transmitting before anyone registers it gets registered,
and an unknown
id_sensorecreates a hive rather than losing the reading.
A rejected reading is dropped, not retried
The broker is acknowledged before the handler ever looks at the payload, so a message that fails
validation is logged as Lettura scartata and gone. There is no dead-letter queue.
Two failure modes worth knowing. + matches exactly one level, so a node publishing to
beehive/NODE001/sensors/data connects happily, gets no error, and is silently ignored โ check
this first when a node "works" but nothing lands in the database. And there is no hot reload:
editing a file changes nothing until docker-compose restart mqtt-handler.
The API never touches MQTT. It reads the same database but is not a broker client, so restarting the broker does not affect it.
Full documentation¶
- Broker โ https://github.com/fablab-imperia/meshbee-server/blob/main/mosquitto/README.md
- Handler โ https://github.com/fablab-imperia/meshbee-server/blob/main/mqtt_handler/README.md
Related¶
- Firmware โ what publishes to the broker.
- MQTT payload โ the payload format in detail.
- Core & database โ where the reading is actually written.