Reversteem: Using Steem Posts & Comments as a Game State Machine
Hey Steem devs! 👋
I've been working on a side project that started as a fun experiment and turned into something I think is worth sharing here: Reversteem, a fully on-chain Reversi (Othello) game built on Steem — with no smart contracts, no backend server, and no database.
I want to talk less about the game itself and more about the protocol design underneath it, because I think the pattern is reusable for any turn-based game on Steem.
The Core Idea: Blockchain as an Event Log
The key insight is simple: a Steem post thread is a perfectly good append-only event log.
- The root post declares the game and its parameters
- Each reply comment is a game event (join, move, timeout claim)
- Game state is never stored — it's derived by replaying those events in chronological order
Every client independently replays the same history and arrives at the same board state. No authority needed. No server to trust.
Root Post → game_start { black, timeoutMinutes, invites }
└── Reply → join { action: "join" }
└── Reply → move { action: "move", index: 28, moveNumber: 4 }
└── Reply → move { action: "move", index: 19, moveNumber: 5 }
└── Reply → timeout_claim { claimAgainst: "black", moveNumber: 6 }
The entire game protocol lives in json_metadata. Only comments with app starting with "reversteem/" are processed — everything else is treated as spectator chat.
Deterministic Replay
This is where it gets interesting. Game state is computed by a pure function:
deriveGameState(rootPost, replies) → gameState
The replay engine:
- Sorts all replies by
createdtimestamp (appendingZto force UTC — Steem timestamps omit it) - Processes each event in order, validating strictly:
moveNumbermust equalappliedMoves— no gaps, no duplicates, no replays- Author must match the expected player for the current turn
- Move must flip at least one disc (standard Reversi rule)
- Silently skips any invalid event — malformed moves leave no trace in the derived state
Because the function is pure and the blockchain is immutable, the output is always identical regardless of who runs it or when. No consensus mechanism needed beyond what Steem already provides.
No Smart Contracts. No Backend. Seriously.
There is genuinely no server involved. The whole app is four static JavaScript files loaded from GitHub Pages.
| Layer | Solution |
|---|---|
| State storage | Steem blockchain (posts + comments) |
| State derivation | Pure JS replay function in the browser |
| Write access | Steem Keychain browser extension |
| Hosting | GitHub Pages (static files only) |
| RPC resilience | Auto-fallback across 4 public Steem nodes |
The tradeoff is latency — moves take a few seconds to confirm on-chain. But for a turn-based game, that's completely fine. And you get immutability and verifiability for free.
Solving Edge Cases with Protocol Design
A few interesting problems that came up:
Timeout enforcement — Rather than a server-side timer, timeout is claimable. The opponent posts a timeout_claim comment. The replay engine validates it: did enough time pass between lastMoveTime and claim.created? If yes, the game ends. Once the threshold is exceeded, further moves by the timed-out player are rejected in replay — preventing race conditions between a late move and a racing claim.
Double-move prevention — The moveNumber field in move metadata must exactly equal appliedMoves at replay time. Even if a user somehow submits two moves simultaneously, only the first will have the correct moveNumber — the second is silently discarded.
Invite-only games — The invites array in the root post restricts who may join. Crucially, this is always re-read from the root post at replay time and never trusted from the local cache — preventing cache-poisoning bypasses.
What This Pattern Could Be Used For
Reversteem is Reversi, but the protocol is generic. Any turn-based game that can be expressed as:
- an initial state
- a sequence of validated events
- a deterministic transition function
...could be built this way on Steem. Chess, checkers, Go, card games — the pattern holds as long as the state space fits in a comment thread and move latency is acceptable.
Links
- 🔗 Live demo: https://puncakbukit.github.io/reversteem/
- 📂 Source code: https://github.com/puncakbukit/reversteem
- 📄 White paper:
https://github.com/puncakbukit/reversteem/blob/main/Reversteem_WhitePaper_v0.1.pdf
Would love to hear thoughts from the dev community — especially if you've explored similar patterns on Steem or other blockchains. What would you build with an on-chain event log? 🤔
Assisted by https://claude.ai/.
See also:
- By eliminating downvotes, Blurt ensures users are rewarded based on positive consensus, not through whale punishment. Please join through this link or this link with the invite code "puncakbukit."
- @steem.amal: Charity At Your Fingertips
- Maximize curation rewards: follow our trail! Maksimalkan reward kurasi: ikuti trail kami! トレイルをフォローし、キユレーション報酬を最大化!



Upvoted! Thank you for supporting witness @jswit.