🛠 Publier en MQTT sur le réseau GPRS
Objectives
Connect the MKR GSM 1400 to an MQTT broker by stacking PubSubClient on top of GSMClient: since the MKRGSM client class mimics Arduino's Client class, PubSubClient works without modification. This is a typical pattern for field sensors (Irriduo irrigation, water monitoring): periodic reading, QoS 1 publication, and robust reconnection after radio outages.
Hardware
- Arduino MKR GSM 1400 board + U.FL antenna + LiPo battery ≥ 1500 mAh
- Data micro-SIM (PIN code disabled), known APN
- An MQTT broker accessible via TCP 1883 (personal server or test broker)
- Libraries: MKRGSM, PubSubClient
Complete Code
#include <MKRGSM.h>
#include <PubSubClient.h>
#include "arduino_secrets.h"
const char PINNUMBER[] = SECRET_PINNUMBER;
const char GPRS_APN[] = SECRET_GPRS_APN;
const char GPRS_LOGIN[] = SECRET_GPRS_LOGIN;
const char GPRS_PASSWORD[] = SECRET_GPRS_PASSWORD;
const char MQTT_BROKER[] = "broker.example.org";
GSMClient netClient;
GPRS gprs;
GSM gsmAccess;
PubSubClient mqtt(netClient);
uint32_t dernierePub = 0;
void connexion {
while (gsmAccess.begin(PINNUMBER) != GSM_READY) delay(2000);
while (gprs.attachGPRS(GPRS_APN, GPRS_LOGIN, GPRS_PASSWORD) != GPRS_READY)
delay(2000);
mqtt.setServer(MQTT_BROKER, 1883);
mqtt.setBufferSize(256);
while (!mqtt.connect("mkr1400-capteur")) {
Serial.print("MQTT rc="); Serial.println(mqtt.state);
delay(5000);
}
Serial.println("MQTT connecte");
}
void setup {
Serial.begin(9600);
while (!Serial) {}
connexion;
}
void loop {
if (!mqtt.connected || !gprs) { // coupure radio ou broker
Serial.println("Reconnexion...");
gsmAccess.shutdown;
connexion;
}
mqtt.loop; // indispensable : trafic + keepalive
if (millis - dernierePub > 60000UL) {
dernierePub = millis;
int v = analogRead(A1); // exemple : capteur analogique
char trame[48];
snprintf(trame, sizeof trame, "{\"a1\":%d}", v);
mqtt.publish("maison/mkr1400/a1", trame, true); // retain
}
delay(100);
}
Expected Verification
mosquitto_sub -t 'maison/mkr1400/a1' (or your broker's client) receives a JSON frame every minute, even after moving the board to an area without network coverage: the reconnection loop resumes automatically. mqtt.loop must be called frequently — its absence causes keepalive disconnections and unprocessed incoming messages.
Common Errors
- PubSubClient buffer too small:
MQTT_PACKET_SIZE_EXCEEDEDduring publication; usesetBufferSizeand recompile withMQTT_MAX_PACKET_SIZEif necessary. - Forgetting
mqtt.loopinloop: the broker disconnects the client after the keepalive timeout. - TLS: port 8883 with plain
GSMClientwill not work; useGSMSSLClientorBearSSLClient(ECC508), and an MQTT library compatible with TLS clients. - Publishing during an outage: messages are lost without a queue — buffer them in RAM (only 32 KB available) or accept the loss.
- MQTT password in the sketch: the board's flash is readable via bossac even with the security bit enabled (ArduinoCore-samd #570); use the Secrets tab and credentials with limited scope.
- 2G throughput: keep frames small and frequency low (minutes, not seconds).
Other tutorials for this board
Code examples for this board
gsm-connexion.inoArduinoenvoi-sms.inoArduinohttp-get.inoArduinohttp-post-capteur.inoArduinoheure-gsm.inoArduinoappels.inoArduino