Skip to content

Tournament · Modules

3 modules · 24 exports · 4 repositories · 23 e2e tests · 12 routes

Who imports who · hover a node
Depends onTournament modulesUsed byProgressiontournament-br…PendingCheckIns.serverStandings11 exportsTeamPick10 exportsActions3 filesOther7 filesLoaders3 filesRoutes3 filesBrackettournament-bracketRoundRobinBrackettourna…SwissBrackettournament-b…Scripts1 fileRepositories2 filesTournamenttournament-brac…Components1 file

PendingCheckIns

serverapp/features/tournament/core/PendingCheckIns.server.ts

No overview comment at the top of the file.

Imports
no other modules
Used by
2 actions1 other

Types

interface

PendingCheckIn

no JSDoc:9
export interface PendingCheckIn {
	tournamentId: number;
	logoUrl: string;
}
Only used inside the module

Functions & values

function

byUserId

:20

The tournament the user has to check in to right now, null when none has check-in open. Cached site-wide rather than resolved per user: the header asks on every page load, while the answer only moves as tournaments approach their start.

export async function byUserId(userId: number): Promise<PendingCheckIn | null>
function

clearCache

:25

Drops the cache so a team checking in (or out) shows in the header without waiting out the TTL.

export function clearCache()

Standings

app/features/tournament/core/Standings.ts

No overview comment at the top of the file.

Imports
Progression
Used by
3 loaders1 action2 routes3 modules1 script2 other

Types

type

TournamentStandingsResult

no JSDoc:10
export type TournamentStandingsResult =
	| { type: "single"; standings: Standing[] }
	| {
			type: "multi";
			standings: Array<{
				div: string;
				standings: Standing[];
			}>;
	  };
type

MatchPlayed

no JSDoc:108
export type MatchPlayed = {
	id: number;
	vsSeed: number;
	result: "win" | "loss";
	/** Maps won by the team and by its opponent. */
	score: [team: number, opponent: number];
	bracketIdx: number;
};
Only used inside the module
type

TeamRecord

no JSDoc:117
export type TeamRecord = {
	setWins: number;
	setLosses: number;
	mapWins: number;
	mapLosses: number;
};

Functions & values

function

flattenStandings

:21

Converts tournament standings from single or multi-division format into a flat array

export function flattenStandings(
	standingsResult: TournamentStandingsResult,
): Standing[]
function

winners

:33

Teams sharing 1st place of the top division (the only one when the tournament isn't split into divisions). Several when the tournament ends with co-winners.

export function winners(
	standingsResult: TournamentStandingsResult,
): Standing[]
Unit tests (4)
function

reNumberPlacements

:48

Re-numbers placements of sorted standings keeping ties grouped ([1, 1, 3, 3, 5]), for after filtering or merging. offset shifts every placement down, for appending below another bracket's standings.

export function reNumberPlacements<T extends { placement: number }>(
	standings: T[],
	offset = 0,
): T[]
Unit tests (6)
function

sprByTeamId

:72

SPR (Seed Performance Rating) of every team in the standings, keyed by tournament team id. Seeds are ranked among the given standings only, so a division's standings are compared to its own seed order. See https://web.archive.org/web/20250513034545/https://www.pgstats.com/articles/introducing-spr-and-uf

export function sprByTeamId(standings: Standing[]): Map<number, number>
Unit tests (5)
function

matchesPlayedByTeamId

:128

Every match each team played, in the order they were played in, keyed by tournament team id. Teams that played no match are absent from the map.

export function matchesPlayedByTeamId(
	tournament: Tournament,
): Map<number, MatchPlayed[]>
Unit tests (2)
function

recordByTeamId

:182

Set and map record of every team over the matches it played, keyed by tournament team id. Teams that played no match are absent.

export function recordByTeamId(
	tournament: Tournament,
): Map<number, TeamRecord>
Unit tests (2)
function

standingsFromPersistedResults

:223

Standings of a finalized tournament from the per-user results persisted at finalization. Null when those can't back the standings (no rows, a team no longer in the tournament, a division label the progression no longer produces) so the caller can fall back to {@link tournamentStandings}.

export function standingsFromPersistedResults({
	tournament,
	results,
}: {
	tournament: Tournament;
	results: PersistedResultRow[];
}): TournamentStandingsResult | null
function

tournamentStandings

:282

Standings aggregated across brackets: e.g. in RR → SE the top teams come from the SE bracket and the teams that missed it are ordered by their group performance. Type single with overall standings for one starting bracket, multi with standings per division for several.

export function tournamentStandings(
	tournament: Tournament,
): TournamentStandingsResult
Unit tests (13)

TeamPick

app/features/tournament/core/TeamPick.ts

No overview comment at the top of the file.

Imports
no other modules
Used by
1 action1 route2 repositories1 module1 component4 other

Types

type

TeamPoolValidationStatus

no JSDoc:15
export type TeamPoolValidationStatus =
	| "PICKING"
	| "VALID"
	| "TOO_MUCH_STAGE_REPEAT"
	| "STAGE_REPEAT_IN_SAME_MODE"
	| "NOT_IN_POOL";

Functions & values

function

defaultCount

:29

How many maps a team picks per mode by default: 6 for one mode, 4 for two, 3 for three and 2 for more.

  • @example

    defaultCount(1); // 6 defaultCount(4); // 2

export function defaultCount(modeCount: number)
Unit tests (1)
function

defaultSettings

:34

Team pick settings for the given modes with the default count for each and the SendouQ pool.

export function defaultSettings(modes: ModeShort[]): TeamPickSettings
Unit tests (1)
function

sortModes

:44

Modes in the fixed in-game order, duplicates dropped.

export function sortModes(modes: ModeShort[])
function

pickedModes

:49

Modes teams pick maps for.

export function pickedModes(teamPick: TeamPickSettings)
function

effectivePool

:57

Pool the teams pick their maps from, limited to the picked modes. customPool is the organizer's pool, only read for the "CUSTOM" pool option.

export function effectivePool(
	teamPick: TeamPickSettings,
	customPool: Array<{ mode: ModeShort; stageId: StageId }>,
): MapPool
Unit tests (3)
function

maxCount

:84

Most maps a team can pick in a mode, one less than the pool has so the random neutral map always has a stage to draw from.

export function maxCount(pool: MapPool, mode: ModeShort)
Unit tests (1)
function

poolShortfalls

:92

Picked modes whose pool has fewer stages than the count plus one, with how many stages they need. Empty for a pool the teams can pick from.

export function poolShortfalls(teamPick: TeamPickSettings, pool: MapPool)
Unit tests (1)
function

stageRepeatCap

:111

In how many modes one stage may appear in a team's picks. Grows from 2 as the pool gets tight relative to the picks and turns off (equals the mode count) when it can't be satisfied.

  • @example

    // 4 modes × 2 picks from the SendouQ pool (25 distinct stages) stageRepeatCap({ teamPick, pool }); // 2 // 4 modes × 4 picks from 8 stages stageRepeatCap({ teamPick, pool }); // 3

export function stageRepeatCap({
	teamPick,
	pool,
}: {
	teamPick: TeamPickSettings;
	pool: MapPool;
})
Unit tests (1)
function

validateTeamPool

:133

Validates a team's picks against the tournament's team pick settings and effective pool. Statuses with an explanation come before "PICKING" so a mistake shows while still picking.

export function validateTeamPool({
	mapPool,
	teamPick,
	pool,
}: {
	mapPool: MapPool;
	teamPick: TeamPickSettings;
	pool: MapPool;
}): TeamPoolValidationStatus
Unit tests (2)