multiplayer-prompting
Val Town is a collaborative website to build and scale JavaScript apps.
Deploy APIs, crons, & store data โ all from the browser, and deployed in milliseconds.
Viewing readonly version of main branch: v42View latest version
SQLite database layer for session persistence.
Tracks game sessions:
id(TEXT PRIMARY KEY): Unique session identifiercreated_at(INTEGER): Unix timestampcurrent_turn(INTEGER): Index of current playermax_players(INTEGER): Max active players (default 10)status(TEXT): waiting | active | completed
Tracks players in each session:
id(INTEGER PRIMARY KEY AUTOINCREMENT)session_id(TEXT): Foreign key to sessionsname(TEXT): Player display nameavatar(TEXT): Emoji avataris_active(INTEGER): 1 for active player, 0 for spectatorturn_order(INTEGER): Turn sequence numberlast_seen(INTEGER): Heartbeat timestamp
Stores played cards:
id(INTEGER PRIMARY KEY AUTOINCREMENT)session_id(TEXT): Foreign key to sessionsplayer_name(TEXT): Who played the cardcard_type(TEXT): role | tone | token-limit | custom | image | removecontent(TEXT): Card instruction/contentimage_url(TEXT): Optional blob storage URLtimestamp(INTEGER): When card was played
Stores AI-generated responses:
id(INTEGER PRIMARY KEY AUTOINCREMENT)session_id(TEXT): Foreign key to sessionsprompt(TEXT): Full system promptresponse(TEXT): AI responsetoken_count(INTEGER): Tokens usedtimestamp(INTEGER): When generated
All database operations are in queries.ts:
createSession(id): Create new sessiongetSession(id): Fetch session by IDupdateSessionTurn(id, turn): Advance turnupdateSessionStatus(id, status): Change status
addPlayer(sessionId, name, avatar, turnOrder): Add playergetPlayers(sessionId): Get all playersgetActivePlayers(sessionId): Get active players onlyupdatePlayerHeartbeat(sessionId, name): Update last_seen
playCard(sessionId, playerName, type, content, imageUrl?): Add card to stackgetPromptStack(sessionId): Get all played cardsremoveLastCard(sessionId): Undo last cardremoveCardsByType(sessionId, type): Clear specific card type
saveVibeResult(sessionId, prompt, response, tokens): Save AI outputgetLatestVibeResult(sessionId): Get most recent result
Tables are versioned (e.g., sessions_v1). To change schema:
- Update
VERSIONconstant in schema.ts - Old data remains in old tables
- New tables created automatically
- No migration needed (Val Town pattern)
import { initDatabase } from "./database/schema.ts";
import * as db from "./database/queries.ts";
// Initialize tables
await initDatabase();
// Create session
const session = await db.createSession("my-game-123");
// Add player
const player = await db.addPlayer("my-game-123", "Alice", "๐จ", 0);
// Play card
await db.playCard("my-game-123", "Alice", "role", "Act as a Rust expert");
// Get stack
const stack = await db.getPromptStack("my-game-123");