Crashout es un juego de carreras multijugador en vivo que construimos para eventos: una pantalla grande en el lugar, un anfitrión manejando todo desde una tablet, y los invitados manejando con el celular que ya tienen en el bolsillo. Está en vivo hoy en crashout.dizenz.com.

La idea nació de una restricción simple: el entretenimiento grupal en un evento real no tiene ninguno de los lujos que asume un juego multijugador normal. No podés pedirle a veinte invitados que instalen una app antes de que arranque la fiesta. No podés confiar en un wifi rápido y estable. Y quien esté a cargo tiene que poder arrancar, resetear y encadenar carrera tras carrera sin tocar nunca la TV.

Este caso de estudio cuenta cómo diseñamos alrededor de esa restricción: las decisiones de producto, y la ingeniería detrás de ellas.

01

El Desafío

La mayoría de los juegos multijugador asumen una audiencia cautiva y técnica: una app ya instalada, una conexión estable, jugadores que ya conocen los controles. Nada de eso se cumple en una fiesta corporativa, una activación de marca o una salida con amigos. El onboarding tiene que funcionar para un invitado que nunca vio el juego, con cualquier celular que tenga a mano, sobre el wifi que el lugar ofrezca.

Además, una sola persona tiene que poder manejar el evento de punta a punta —arrancar una carrera, resetearla, arrancar la siguiente— desde una tablet, sin acercarse nunca a la TV. Y cada pantalla en la sala, desde la pantalla grande hasta el celular de cada jugador, tiene que coincidir exactamente en qué está pasando en cada momento, o todo se desarma en vivo frente a la gente.

02

El Enfoque

Elegimos el onboarding más simple posible: un código QR en la pantalla grande, una pestaña del navegador en el propio celular del jugador, sin app, sin cuenta. Escanear, escribir un nombre, elegir un auto, arrancar a manejar. Esa única decisión determinó casi todo lo demás del producto.

01

Escanear

El invitado escanea el código QR de la pantalla grande.

02

Nombre

Escribe un nombre — nada más que completar.

03

Auto

Elige un auto del catálogo en vivo.

04

Manejar

Maneja con el celular que ya tiene en el bolsillo.

sin app · sin cuenta · solo el navegador

Del escaneo al volante — sin app, sin cuenta.

La otra decisión clave fue hacer que el servidor sea la única fuente de verdad para todo el juego. Ningún cliente —ni la pantalla grande, ni el celular de un jugador, ni el controller del anfitrión— puede decidir por su cuenta qué pasó en la carrera. Solo renderizan lo que el servidor les dice. Eso es lo que permite que una sala llena de celulares de desconocidos, sobre un wifi impredecible, coincidan todos en la misma carrera.

03

Un Servidor Autoritativo, Tres Pantallas Sincronizadas

El backend es un servidor en Go construido sobre el router HTTP de la librería estándar y una librería liviana de WebSocket, sin ningún framework web de por medio. Cada evento tiene su propia sala, y cada sala es dueña de su propia goroutine de simulación y su propio canal de entrada: las salas nunca comparten estado ni se bloquean entre sí, lo que mantiene simple razonar sobre un juego con decenas de eventos simultáneos.

La simulación corre a un tick interno de 60Hz, pero solo transmite un snapshot a los clientes 20 veces por segundo, y el cliente interpola entre snapshots para lograr movimiento fluido. Esa proporción no es arbitraria: originalmente corríamos el tick y el snapshot en una relación 30/20, que producía un patrón de transmisión irregular de 33/33/67 milisegundos y se notaba como un tartamudeo visible en la pantalla grande. Pasar a una relación 60/20, un múltiplo exacto, da una cadencia perfectamente uniforme de 50 milisegundos y lo solucionó. Es un buen ejemplo del tipo de detalle que solo se nota cuando estás viendo una carrera correr en una TV real.

Tick 30Hz / snapshot 20Hz
Transmisiones irregulares de 33/33/67ms — tartamudeo visible en la pantalla grande.
Tick 60Hz / snapshot 20Hz
Una cadencia perfectamente uniforme de 50ms.
Pasar de una relación 30/20Hz a un múltiplo exacto de 60/20Hz solucionó el tartamudeo.

Tres pantallas se conectan a ese mismo servidor: la pantalla grande renderiza la carrera y el QR del lobby en canvas, la página de joystick convierte el celular de un jugador en dirección y bocina, y el controller le da al anfitrión inicio, reset y configuración. Un cuarto modo, una carrera demo de un solo dispositivo, reutiliza exactamente el mismo protocolo: solo abre dos conexiones WebSocket desde un celular en vez de inventar un nuevo rol de cliente.

Pantalla grande

Renderiza la carrera y el QR del lobby en canvas.

Celular del jugador

Página de joystick: dirección y bocina.

Tablet del anfitrión

Controller: inicio, reset y configuración.

Servidor Go

Una sala por evento, cada una con su propia goroutine de simulación y canal de entrada — sin estado compartido, sin locks.

net/httpWebSocketsin framework

El servidor es la única fuente de verdad — cada cliente solo renderiza lo que le dicen.

Un servidor Go autoritativo, tres pantallas de cliente sincronizadas.

Todo eso corre repartido entre dos proveedores. El frontend está en Vercel — cada una de las tres pantallas es simplemente una ruta de la misma app Next.js, que llega al backend por orígenes WebSocket y REST absolutos, fijados en tiempo de build. El backend es deliberadamente aburrido: una sola instancia EC2 en us-east-2, provisionada con Terraform. Sin contenedores, sin orquestador, sin balanceador de carga.

Caddy va adelante, terminando TLS para cada conexión WebSocket con certificados que él mismo emite y renueva contra Let's Encrypt — los puertos internos del backend nunca son accesibles desde afuera. Todo lo que tiene que sobrevivir a un proceso vive en PostgreSQL en una máquina aparte, con conexión por SSL y migraciones que corren al arrancar. Los deploys son lo único que hace GitHub Actions: lint, typecheck, tests y build corren localmente antes de cualquier push.

Vercel

App Next.jsLas tres pantallas son rutas de una misma app — pantalla grande, joystick, controller.

Next.js 16React 19crashout.dizenz.com
wss:// + REST

AWS · us-east-2

Caddy

Termina TLS, renueva sus propios certificados de Let's Encrypt y rutea al slot sano.

Una instancia EC2

Slot blueSlot green

PostgreSQL

Una máquina aparte, solo SSL. Ambos slots comparten una base — el único estado que un deploy traspasa.

Solo Caddy está expuesto — los puertos de los slots nunca son accesibles desde internet.

Dos proveedores: el frontend en Vercel, el backend y su base de datos en AWS.

Como Crashout corre en eventos en vivo, un deploy nunca puede interrumpir una carrera en curso. Corremos producción detrás de slots de deploy blue/green en la misma máquina, y una señal de apagado le indica al slot viejo que drene —termine las carreras que estén corriendo, rechace las nuevas— durante hasta tres horas en vez de cortar las conexiones de inmediato. Los clientes anclan sus reconexiones al slot en el que arrancaron, y un token de reanudación le permite a un jugador cuyo celular se cae en medio de una carrera volver a exactamente el auto que estaba manejando.

Slot nuevo · Activo

Acepta todas las carreras nuevas.

Slot viejo · Drenando, hasta 3h

Termina las carreras que ya están corriendo, rechaza las nuevas.

Las reconexiones se anclan al slot en el que arrancó el clienteUn token de reanudación vuelve a subir al mismo auto en plena carrera
Los slots de deploy blue/green dejan que una carrera en curso termine antes de que su slot desaparezca.
04

Lo Que Construimos

Más allá del loop de carrera principal, el producto creció hasta ser una herramienta completa de operación de eventos:

Catálogo de contenido

15 vehículos en 5 líneas de modelo, 8 tipos de obstáculos, y 4 fondos de carrera seleccionables

Salas configurables

De 2 hasta 40 jugadores, con carreras de eliminación y un límite de tiempo de 60 segundos

Tres idiomas, en vivo

Inglés, español y árabe, cambiables en vivo por el anfitrión —incluyendo soporte completo de layout de derecha a izquierda

Dos esquemas de control

Botones en pantalla o un joystick analógico, a elección de cada jugador

Leaderboards públicos

De solo lectura para cada evento, para compartir después de la carrera

Panel de administración

Protegido por contraseña: creación de eventos, códigos de seguridad, un catálogo en vivo de vehículos y fondos, y un registro de auditoría de autenticación

Soporte al anfitrión

Escala directo a un mensaje de WhatsApp pre-completado con el código del evento y el estado de la carrera

05

Resultados

Crashout lleva alrededor de cinco meses y medio de desarrollo continuo y activo, y lo construimos con el estándar de software de producción, no el de un prototipo de juego para fiestas:

478

commits desde el scaffold inicial (feb 2026)

~17.000

líneas de Go en el backend

~23.000

líneas de TypeScript en el frontend

400+

tests en Go

~1.900

tests de JS/TS

46

specs E2E de Playwright

Un gate completo antes de cada push

Corre localmente antes de que el código llegue a CI.

lint
typecheck
tests
build