Contexte
Transformer le vibe-coding en jeu social
Les outils IA permettent de produire une petite web app rapidement. Mais construire seul ne crée ni tension, ni comparaison, ni verdict.
BuildBattle reprend la mécanique d’une battle créative : tous les joueurs reçoivent le même brief, construisent sous contrainte de temps, découvrent les résultats ensemble puis votent.
Problème
La compétition n’existe que si l’état est partagé
Une battle doit synchroniser le lobby, le brief, les participants, le timer, les builds, le reveal, les votes et le classement. Si chaque navigateur décide de l’heure ou de la phase, le jeu n’est plus équitable.
Il fallait aussi empêcher les joueurs de voir un build adverse avant le reveal, interdire le vote pour soi-même et exécuter du HTML généré sans exposer la session du joueur.
Mon rôle
Du concept au système jouable
J’ai cadré la boucle produit, défini les invariants de jeu et construit l’expérience de bout en bout : interface React, protocole temps réel, moteur de bataille, persistance et système de classement.
Le travail a surtout consisté à arbitrer : ce qui devait être autoritaire côté serveur, ce qui pouvait rester local, et ce qu’il fallait retirer du MVP pour livrer une boucle complète.
Solution
Une battle pilotée par le serveur
Chaque partie repose sur un Durable Object qui porte une machine à états stricte : lobby, construction, showcase, vote, résultats. Le serveur fixe les échéances et les clients ne font qu’afficher le compte à rebours.
Pendant la construction, chaque joueur utilise l’éditeur intégré, prévisualise son HTML dans une sandbox puis publie. Les builds restent masqués jusqu’au reveal simultané. Les pairs votent ensuite, et le mode ranked applique le classement ELO.
Choix clés
Quatre arbitrages qui tiennent le jeu
Une autorité serveur unique
Un Durable Object par battle contrôle les phases, le timer, les soumissions et les votes. Une reconnexion récupère l’état réel au lieu de reconstruire une partie depuis le navigateur.
Le même terrain de jeu pour tous
En mode ranked, le serveur choisit le brief au démarrage. Il attribue aussi le même compagnon IA à tous les participants d’une battle : aucun joueur ne peut sélectionner son propre modèle.
Réduire le périmètre pour livrer
Le pipeline de captures automatiques a été mis en attente. Le MVP produit un seul fichier HTML dans l’app, avec un générateur local déterministe si aucune clé IA n’est disponible.
Traiter chaque build comme du code non fiable
Le HTML publié est limité, stocké dans le Durable Object et servi avec une politique CSP restrictive. La preview tourne dans une iframe sandboxée, sans cookies, stockage ni appels réseau sortants.
Résultat & apprentissage
Une boucle complète, testable de bout en bout
Le MVP est accessible en ligne. La démo locale permet aussi de parcourir les cinq phases seul contre deux bots, tandis que le smoke test pilote trois joueurs et trois builds sur de vrais WebSockets jusqu’aux résultats.
L’apprentissage principal : dans un produit multijoueur, l’équité n’est pas une contrainte technique ajoutée après coup. Le timer serveur, le modèle commun, le reveal simultané et les scores masqués font partie de l’expérience.
Aucun volume de parties, utilisateur actif ou taux de rétention n’est documenté à ce stade. La preuve publiable porte sur le produit livré et son fonctionnement, pas sur une adoption non mesurée.
Stack & méthodes
Un système temps réel, testé par couches
- React + Vite
- Cloudflare Workers
- Durable Objects + WebSockets
- Supabase Postgres, Auth et RLS
- Machine à états fonctionnelle
- ELO
- Vitest + smoke test WebSocket
- CSP et iframe sandboxée

