Add Prettier and ESLint tooling (Refs #77)
This commit is contained in:
+77
-20
@@ -9,7 +9,10 @@ import { mapTitle, serverTitle } from './ui/server-labels.js';
|
||||
export interface FleetServer {
|
||||
plutonium?: import('./plutonium.js').PlutoniumVersion;
|
||||
host_id?: string | null;
|
||||
host?: Pick<import('./hosts.js').Host, 'id' | 'name' | 'connectionState' | 'connected' | 'lastHeartbeat'> | null;
|
||||
host?: Pick<
|
||||
import('./hosts.js').Host,
|
||||
'id' | 'name' | 'connectionState' | 'connected' | 'lastHeartbeat'
|
||||
> | null;
|
||||
container_state?: string | null;
|
||||
container_checked_at?: string | null;
|
||||
last_checked_at?: string | null;
|
||||
@@ -56,49 +59,103 @@ export type FleetFilter = 'all' | 'occupied' | 'empty' | 'attention' | 'testing'
|
||||
export type FleetSort = 'name' | 'players' | 'round' | 'duration';
|
||||
|
||||
export function freshServer(server: FleetServer, now: number): boolean {
|
||||
return server.health === 'online' && !server.last_error && freshStatusTimestamp(server.last_seen_at, now);
|
||||
return (
|
||||
server.health === 'online' &&
|
||||
!server.last_error &&
|
||||
freshStatusTimestamp(server.last_seen_at, now)
|
||||
);
|
||||
}
|
||||
|
||||
export function fleetIdentity(server: FleetServer) {
|
||||
const parsed = parseServerName(server.name);
|
||||
const game = server.game ?? parsed?.game ?? '';
|
||||
const mode = server.game_mode ?? parsed?.gameMode;
|
||||
const selection = !mode || mode === 'zombie'
|
||||
? zombieMapBySlug(game, server.map_slug ?? parsed?.mapSlug ?? '') : undefined;
|
||||
const selection =
|
||||
!mode || mode === 'zombie'
|
||||
? zombieMapBySlug(game, server.map_slug ?? parsed?.mapSlug ?? '')
|
||||
: undefined;
|
||||
const map = server.last_map ?? server.map;
|
||||
// A live map change must not keep the registered map's launch shortcut.
|
||||
const matchingSelection = selection && (!map || selection.canonical === map) ? selection : undefined;
|
||||
const matchingSelection =
|
||||
selection && (!map || selection.canonical === map) ? selection : undefined;
|
||||
return {
|
||||
game,
|
||||
title: serverTitle(server.name),
|
||||
map: matchingSelection?.friendly ?? mapTitle(map),
|
||||
group: `${game}:${matchingSelection?.slug ?? map ?? 'unknown'}`,
|
||||
launch: matchingSelection && (game === 't5' || game === 't6')
|
||||
? { game: game as ZombieGame, slug: matchingSelection.slug } : null
|
||||
launch:
|
||||
matchingSelection && (game === 't5' || game === 't6')
|
||||
? { game: game as ZombieGame, slug: matchingSelection.slug }
|
||||
: null
|
||||
};
|
||||
}
|
||||
|
||||
export function currentRound(server: FleetServer, report: GameTelemetry | undefined, now: number): number | null {
|
||||
if (server.telemetry && (!report || Date.parse(server.telemetry.receivedAt) > Date.parse(report.receivedAt))) report = server.telemetry;
|
||||
if (!report || (report.event !== 'round_change' && report.event !== 'heartbeat') || !freshServer(server, now) || !server.active_since || !server.game_started_at
|
||||
|| server.game_ended_at || (server.last_players ?? 0) === 0) return null;
|
||||
export function currentRound(
|
||||
server: FleetServer,
|
||||
report: GameTelemetry | undefined,
|
||||
now: number
|
||||
): number | null {
|
||||
if (
|
||||
server.telemetry &&
|
||||
(!report || Date.parse(server.telemetry.receivedAt) > Date.parse(report.receivedAt))
|
||||
)
|
||||
report = server.telemetry;
|
||||
if (
|
||||
!report ||
|
||||
(report.event !== 'round_change' && report.event !== 'heartbeat') ||
|
||||
!freshServer(server, now) ||
|
||||
!server.active_since ||
|
||||
!server.game_started_at ||
|
||||
server.game_ended_at ||
|
||||
(server.last_players ?? 0) === 0
|
||||
)
|
||||
return null;
|
||||
const received = Date.parse(report.receivedAt);
|
||||
return freshTelemetry(report, now, server.telemetry_after) && received >= Date.parse(server.game_started_at)
|
||||
&& received >= Date.parse(server.active_since) ? report.round : null;
|
||||
return freshTelemetry(report, now, server.telemetry_after) &&
|
||||
received >= Date.parse(server.game_started_at) &&
|
||||
received >= Date.parse(server.active_since)
|
||||
? report.round
|
||||
: null;
|
||||
}
|
||||
|
||||
export function matchesFleet(server: FleetServer, query: string, filter: FleetFilter, game: string,
|
||||
pinned: readonly string[], operations: readonly FleetOperation[], now: number): boolean {
|
||||
export function matchesFleet(
|
||||
server: FleetServer,
|
||||
query: string,
|
||||
filter: FleetFilter,
|
||||
game: string,
|
||||
pinned: readonly string[],
|
||||
operations: readonly FleetOperation[],
|
||||
now: number
|
||||
): boolean {
|
||||
const identity = fleetIdentity(server);
|
||||
if (game && identity.game !== game) return false;
|
||||
const fresh = freshServer(server, now);
|
||||
if (filter === 'occupied' && !(fresh && (server.last_players ?? 0) > 0)) return false;
|
||||
if (filter === 'empty' && !(fresh && server.last_players === 0)) return false;
|
||||
if (filter === 'attention' && !(server.health === 'offline' || server.health === 'stale'
|
||||
|| (server.health === 'online' && !fresh) || operations.some(op => op.server === server.name && op.state === 'attention'))) return false;
|
||||
if (
|
||||
filter === 'attention' &&
|
||||
!(
|
||||
server.health === 'offline' ||
|
||||
server.health === 'stale' ||
|
||||
(server.health === 'online' && !fresh) ||
|
||||
operations.some((op) => op.server === server.name && op.state === 'attention')
|
||||
)
|
||||
)
|
||||
return false;
|
||||
if (filter === 'testing' && !server.held.length) return false;
|
||||
if (filter === 'pinned' && !pinned.includes(server.name)) return false;
|
||||
const text = [server.name, identity.title, identity.map, identity.game,
|
||||
...(server.roster ?? []).map(player => player.name)].join(' ').toLocaleLowerCase();
|
||||
return query.trim().toLocaleLowerCase().split(/\s+/).every(term => text.includes(term));
|
||||
const text = [
|
||||
server.name,
|
||||
identity.title,
|
||||
identity.map,
|
||||
identity.game,
|
||||
...(server.roster ?? []).map((player) => player.name)
|
||||
]
|
||||
.join(' ')
|
||||
.toLocaleLowerCase();
|
||||
return query
|
||||
.trim()
|
||||
.toLocaleLowerCase()
|
||||
.split(/\s+/)
|
||||
.every((term) => text.includes(term));
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user