downlink.ino
A LoRaWAN node is steered remotely: this MKR WAN 1310 listens on port 8 and changes its own reporting period when the server sends it one byte. The remote-configuration pattern that avoids physically retrieving a rooftop node.
Hardware
An Arduino MKR WAN 1310 (SAMD21 microcontroller, LoRa modem driven by an onboard ESP32 that also exposes Wi-Fi, LoRa antenna and Wi-Fi antenna). Joined MKR WAN 1310, LoRaWAN server able to send a downlink (TTN console, ChirpStack downlink queue).
Wiring
No wiring; the downlink arrives in the RX1/RX2 windows after an uplink (class A).
How it works
parseIncoming() pops the decrypted downlink queue; getDataPort/getData/getDataSize expose the application payload. The new period applies immediately.
Running it
Install Arduino SAMD Boards and the MKRWAN 2.x library (MKRWAN1310), select the board, upload. The 1310 is driven through AT commands over its internal ESP32; for LoRa, plan a second LoRa board on the other end.
Variants
Add a port 9 for factory reset (key wipe), or encode several parameters in a field-bitmask buffer.
downlink.ino
// Downlinks port 8 (MKR WAN 1310) : l'octet recu = periode (min).
#include <MKRWiSOLAR.h>
const uint8_t DEVICE_EUI[] = {0xDE,0xAD,0xBE,0xEF,0xFE,0xED,0xC0,0xFF};
const uint8_t APP_EUI[] = {0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00};
const uint8_t APP_KEY[16] = {0}; // a provisionner cote serveur
LoRaWAN lora;
unsigned long periode = 600000, dernier = 0;
void setup() {
Serial.begin(9600);
lora.setDeviceEui(DEVICE_EUI);
lora.setAppEui(APP_EUI);
lora.setAppKey(APP_KEY);
lora.setRegion(EU_863_870_R1);
if (lora.join(OTAA, MODEL_TYPE_A, 30000, 8) == 0) while (true);
}
void loop() {
lora.run();
if (lora.parseIncoming()) { // downlink en attente ?
uint8_t port = lora.getDataPort();
uint8_t *buf = lora.getData();
uint8_t len = lora.getDataSize();
if (port == 8 && len >= 1) {
periode = (unsigned long)buf[0] * 60000UL;
Serial.println("periode : " + String(buf[0]) + " min");
}
}
if (millis() - dernier >= periode) {
dernier = millis();
uint8_t t[1] = { (uint8_t)(analogRead(A1) >> 2) };
lora.sendBuffer(t, 1, 2, 0);
}
}