Since June I have been running a game show on a radio network where one message tops out at 200 bytes, takes up to about two and a half seconds to send, and may never arrive. My trivia bot asks a question every hour on a LoRa mesh. Players answer by tapping an emoji reaction, and at the end of each month the bot crowns a champion.
A LoRa mesh is a network of small radios that pass short text messages along for each other. It is slow: on the default long-range setting, throughput is about 0.98 kbps. I treated its limits the way I would treat a venue's power budget or the size of its loading door. You don't argue with them. You design the show to fit.
The airtime math decided how often the game could speak. A question once an hour is about 0.07% of the hour on air. A question every 90 seconds, the pace of a normal quiz game, would be about 2.2%, roughly thirty times more. The EU's 1% duty-cycle ceiling, where it applies, is the usual yardstick. The hourly game sits far under it.
A question goes out with four numbered options. You answer by reacting to the message with 1️⃣, 2️⃣, 3️⃣ or 4️⃣. Typing the number works too. Only your first reaction counts, so there is no waiting to see what everyone else picked and then switching.
Scoring borrows from the old chat-room trivia bots, which rewarded speed. A right answer earns 10 points, plus up to 5 more for answering fast, plus 3 for being the first person right. A wrong answer costs nothing. I wanted the game friendly enough that guessing is always worth it.
There are two ways to play. Anyone can start a full game: 12 questions, 90 seconds each. Then there is the hourly question, which fires at an odd minute past the hour so it stays clear of the top-of-the-hour slot where scheduled mesh traffic piles up.
Two rules are about the audience more than the game.
The anti-grind guard. If three rounds in a row get one answer or none, the game stops itself and says it needs more than one player. Its job is to stop one person farming the leaderboard alone.
The monthly champion. At the end of each month the bot counts correct answers from both the full games and the hourly question, names the winner, archives the standings and resets the board. The whole ceremony is capped at three messages a month, and only two of those go to the main channel. The first one ran on August 1.
A playable mock, with made-up players and questions:
Every deploy wiped the scores. I caught it in July: the leaderboard went back to zero on every update. The fix was to keep the game's state in a folder on the host that survives a rebuild.
Too much math. More than four out of five questions in the bank were math. Arithmetic is the one category you can generate in bulk with a provably correct answer. Players don't want that much arithmetic, though. Now a cap holds games and the hourly question to about 18% math, and in July I added 130 curated non-math questions.
More than one right answer. On a radio mesh you can't argue with the host, so a question with two right answers is a broken question. A check at build time now fails on that shape of question unless a person has written down why there is exactly one answer. I seeded 80 of those explanations and fixed 6 questions.
The restart that replayed two weeks. After one restart the bot read about a thousand old messages, two weeks of commands, as if they were new. The server it reads from had ignored the "since" filter on the request. The fix doesn't trust the filter: after any downtime, the bot ignores anything older than five minutes.
Wrong answers were met with silence. Right answers were celebrated at the reveal. A wrong guess got nothing, which looks exactly like a guess that never arrived. On a lossy network those are different things, and players couldn't tell which one had happened. Now a wrong guess gets one short reply that says the guess was seen and never says what the right answer was. Right answers still stay quiet until the reveal, so nobody gives the answer away while others are still guessing.
Deployed is not committed. Two changes lived only on the Raspberry Pi running the bot for more than six weeks.
I spent years in live events, and the core instinct there is to read the room. You watch faces, hear the energy drop, and change the pace. A radio mesh takes all of that away. I can't see the players. I get reactions, late, some of the time.
So the game has to read the room for me, in the only signals it has. Three quiet rounds in a row means the room is empty, so stop. A guess with no reply makes a player feel unheard, so acknowledge every guess. The hourly question is the house music between sets. The monthly champion is the moment the whole crowd hears about, and you only get a few of those before people tune out, which is part of why it is capped.
The silence bug taught me the most. In a room, a host can nod at someone who guessed wrong. On a mesh, no nod is indistinguishable from a lost packet. Any feedback you don't send, the player assumes didn't happen.
I reported the score wipe in July; until then it had happened on every deploy. The stranded changes were the kind of problem only a person goes looking for, because the bot was working and nothing looked wrong.
What it does: a trivia host for a LoRa text mesh, with tap-to-answer reactions, speed scoring, an hourly question, and a monthly champion. The parts:
How the pieces fit: the bot polls the API every few seconds, matches reactions to the question they answer, scores the first reaction from each player, and posts through a single sender that enforces the byte limit and the send pacing. Game state and scores live in a file in a folder outside the container. The work ran from June to mid-September.
If you run a mesh and want a game on it, or you have a better trick for answering on a network that drops messages, I am easy to reach.
NoteWritten October 2026, about work from June to September 2026.