Solidus
Real-time multiplayer Bingo on Expo and Supabase — ranked auto-matchmaking, private rooms and bot practice, with a leaderboard tracking wins and win rate.
- Services
- Product DesignEngineeringApp Development
- Industries
- MobileRealtime
- Tools
- ExpoReact NativeSupabase
- Highlight
- A sideloaded app can still be updated.
- Live
- Not deployed
A sideloaded app can still be updated
Ship an Android app outside a store and you gain everything except the one thing the store was quietly doing for you: Android will never update anyone automatically. Every install is frozen at the version it arrived as, on a device you cannot reach, belonging to someone who will not reinstall.
That is fine until the backend moves. And the backend always moves.
Two mechanisms, because one cannot cover it
OTA updates carry JavaScript-only changes: publish a new bundle and installed apps pick it up in the background, applying on next launch with no reinstall. That handles most of what changes in a React Native app and it handles none of what changes in the native shell.
So there is a second, blunter path: a `min_supported_version` gate. An APK below the floor gets an update required screen instead of a game. It is not elegant and it is the only thing that works when the shape of the data has changed underneath everybody.
A backend change can break every old install without touching their phones — the Supabase project is shared by every version that has ever shipped.
- Game
- Ranked auto-matchmakingPrivate roomsBot practice
- Realtime
- Supabase RealtimeDerived state via hooksEdge Functions
- Client
- Expo / React NativeExpo RouterZustandTypeScript
- Delivery
- EAS BuildAndroid APK / AABOTA + version floor
What it cost
The version floor has to be raised deliberately and rarely. It is the only lever that can force a reinstall, and every use of it costs some fraction of the players who will not bother — so it is reserved for changes that genuinely cannot be carried over the air, and everything else is shaped to fit through OTA.
That constraint runs backwards into the design: schema changes get planned as additive first, because "add a column" is an OTA-compatible change and "rename a column" is a forced reinstall.
Where it does not work yet
The matchmaking is auto-matchmaking without much of an opinion — it pairs whoever is waiting, and a real ladder eventually needs rating bands, or the top of the leaderboard is decided by who plays at quiet hours.
And the honest structural risk is the one already quoted: one Supabase project serves every version that has ever been installed. There is no staging boundary between a change and the oldest APK in the wild, and that is a thing to fix before it fixes itself loudly.