🌳
pt0/gamesapp/testsF/testTypesF.mts
1/** Shared types for gamesapp test harnesses and scenarios */
3export type GameAction = {
4 sessId: string
5 playerAction: string
6 actionAtMs?: number
7 playerAlias?: string
8 descriptionText?: string
9 finishedTrails?: object[]
10 assignedStackName?: string
11 isAiGenerated?: boolean
12 [key: string]: unknown
15// eslint-disable-next-line @typescript-eslint/no-explicit-any
16export type ApplyActionResult = { ok: boolean, gameState?: any, error?: unknown }
18export type GameState = {
19 id?: string
20 isGameFin?: boolean
21 isEphemeralGame?: boolean
22 gameActionHistA?: GameAction[]
23 pendingAiActionHistA?: GameAction[]
24 playerStates?: Record<string, PlayerState>
25 hiddenState?: { paperStacks?: Record<string, PaperStack> }
26 settings?: GameSettings
27 needsAiDrawings?: boolean
28 [key: string]: unknown
31export type PlayerState = {
32 publicState?: {
33 playerAlias?: string
34 myTaskName?: string
35 gameActiveAt?: number
36 }
37 assignedStackName?: string
38 hasBeenKicked?: boolean
39 [key: string]: unknown
42export type PaperStack = {
43 responses: StackResponse[]
46export type StackResponse = {
47 playerAlias?: string
48 lastDescription?: string
49 lastFinishedTrails?: object[]
50 lastImageDataUrl?: string
51 lastIpfsCid?: string
52 isAiGenerated?: boolean
53 [key: string]: unknown
56export type GameSettings = {
57 maxHumPlayers?: number
58 aiDescriptEnabled?: boolean
59 aiDrawEnabled?: boolean
60 aiDrawingAfterFirstHumanDescript?: boolean
61 aiDrawerUsername?: string | null
62 blockedIps?: string[]
65export type TestHarness = {
66 applyAction: (action: GameAction) => Promise<ApplyActionResult>
67 getState: () => GameState
68 getActivePlayers: () => Array<{ sessId: string } & PlayerState>
69 getPlayer: (sessId: string) => PlayerState | undefined
70 getPaperStacks: () => Record<string, PaperStack>
71 setGameActiveAt: (sessId: string, gameActiveAtMs: number) => void
72 triggerTimeoutCheck: (sessId: string) => Promise<{ kicked: boolean, overdueSec?: number, remainingSec?: number }>
73 setPlayerIp: (sessId: string, ip: string) => void
74 resetBlockedIps: () => void
75 cleanup?: () => Promise<void>
78export type TestAgent = {
79 sessId: string
80 playerAlias: string
81 chooseAction: (gameState: GameState) => GameAction | null
84export type CreateHarnessOpts = {
85 seed?: string
86 gameRoom?: string
87 fakeIp?: string
88 playerCount?: number
89 baseUrl?: string
92// eslint-disable-next-line @typescript-eslint/no-explicit-any
93export type CreateHarnessFn = (opts?: CreateHarnessOpts) => any
95export type RunAgentsOpts = {
96 harness: TestHarness
97 agents: TestAgent[]
98 maxRounds?: number
99 onRound?: (info: { round: number, actionsThisRound: number, isGameFin?: boolean }) => void
102export type RunAgentsResult = {
103 rounds: number
104 isGameFin?: boolean
105 gameIdChanged?: boolean
106 reachedMaxRounds: boolean
109export type OnRoundFn = (info: { round: number, actionsThisRound: number, isGameFin?: boolean }) => void
111export type ScenarioOpts = {
112 createHarness?: CreateHarnessFn
113 onRound?: OnRoundFn
114 isLive?: boolean
117export type TestResult = { passed: boolean, message: string, details?: unknown }