five-on-it / apps/api/src/fleet
apps/api/src/fleet
The game servers the API opens rooms on (TECHNICAL_SPECS §7, §9.6): the ones it was given and the fleet's that registered (fleet-registry.ts). A room is opened on the reachable server with the most room to spare (its players over its capacity, then its rooms), by sending it the room's id and the URL of its artifact with the room secret; a server that takes no new room (503: full, too slow, draining) or cannot be reached is passed over for the next. A player joins with a URL to that server's room that carries a join token the API signs with the same secret. The API remembers which server holds which room, and asks the servers again when it does not know. A city that ships is played in its level's room (Fleet.playUrl): the fullest one with a place left, so players meet, else on the server with the most room, with a join token of the level's room for a player signed in. A room may be opened on a level that ships with its bundled game (bundled: a curated game's run) and for a run (runs.ts), whose seats' join tokens name the run, the seat and the team. A run's room goes only to a server whose release is known (the one it registered with, else the one its /health says) and of the run's release line or newer: an older one knows no runs and would open an ordinary room. The sweep of runs asks one server for its rooms (Fleet.roomsOn), telling a server that answered without a room from one that did not answer. A run's room skips a server at its cap of runs (the maxRuns its heartbeat said, against the run rooms it lists) without asking it; with no server to take a run (every one at its cap, or refusing a new room or run), the run is refused with the city busy (CITY_BUSY). An ordinary room is placed as ever. A room the API no longer wants (a lobby's run nobody will come to) is closed on its server (Fleet.close). A live run that takes players under way says its open seats in its room's status (open), and the API adds a seat to it for a player it placed (Fleet.addSeat).