1
0

Building but users still not listing

This commit is contained in:
James Ketr 2025-10-07 18:26:31 -07:00
parent abdd6bca83
commit 1e16bb0ef6
4 changed files with 63 additions and 28 deletions

View File

@ -4,8 +4,7 @@
* without requiring immediate refactoring of all game logic
*/
import type { GameRoom, GameSession, GameSessionMetadata } from './gameMetadata';
import type { Session } from '../room/types';
import type { GameRoom, GameSession, GameSessionMetadata } from "./gameMetadata";
/**
* Proxy handler for Session objects
@ -15,13 +14,13 @@ import type { Session } from '../room/types';
const sessionProxyHandler: ProxyHandler<GameSession> = {
get(target: GameSession, prop: string | symbol): any {
// Direct properties take precedence
if (prop in target && prop !== 'metadata') {
if (prop in target && prop !== "metadata") {
return (target as any)[prop];
}
// Map game-specific properties to metadata
if (typeof prop === 'string') {
const gameProps = ['color', 'player', 'resources'];
if (typeof prop === "string") {
const gameProps = ["color", "player", "resources"];
if (gameProps.includes(prop)) {
return target.metadata?.[prop as keyof GameSessionMetadata];
}
@ -33,20 +32,33 @@ const sessionProxyHandler: ProxyHandler<GameSession> = {
set(target: GameSession, prop: string | symbol, value: any): boolean {
// Direct properties
const directProps = [
'id', 'userId', 'name', 'ws', 'live', 'lastActive', 'keepAlive',
'connected', 'has_media', 'protected', 'bot_run_id', 'bot_provider_id',
'bot_instance_id', '_initialSnapshotSent', '_getBatch', '_pendingMessage',
'_pendingTimeout'
"id",
"userId",
"name",
"ws",
"live",
"lastActive",
"keepAlive",
"connected",
"has_media",
"protected",
"bot_run_id",
"bot_provider_id",
"bot_instance_id",
"_initialSnapshotSent",
"_getBatch",
"_pendingMessage",
"_pendingTimeout",
];
if (typeof prop === 'string' && directProps.includes(prop)) {
if (typeof prop === "string" && directProps.includes(prop)) {
(target as any)[prop] = value;
return true;
}
// Game-specific properties go to metadata
if (typeof prop === 'string') {
const gameProps = ['color', 'player', 'resources'];
if (typeof prop === "string") {
const gameProps = ["color", "player", "resources"];
if (gameProps.includes(prop)) {
if (!target.metadata) {
target.metadata = {};
@ -63,8 +75,8 @@ const sessionProxyHandler: ProxyHandler<GameSession> = {
has(target: GameSession, prop: string | symbol): boolean {
if (prop in target) return true;
if (typeof prop === 'string') {
const gameProps = ['color', 'player', 'resources'];
if (typeof prop === "string") {
const gameProps = ["color", "player", "resources"];
return gameProps.includes(prop) && target.metadata !== undefined;
}
return false;
@ -78,13 +90,13 @@ const sessionProxyHandler: ProxyHandler<GameSession> = {
const gameProxyHandler: ProxyHandler<GameRoom> = {
get(target: GameRoom, prop: string | symbol): any {
// Direct room properties
const roomProps = ['id', 'name', 'sessions', 'state', 'created', 'lastActivity', 'private'];
if (typeof prop === 'string' && roomProps.includes(prop)) {
const roomProps = ["id", "name", "sessions", "state", "created", "lastActivity", "private"];
if (typeof prop === "string" && roomProps.includes(prop)) {
return (target as any)[prop];
}
// Game properties from metadata
if (typeof prop === 'string' && target.metadata) {
if (typeof prop === "string" && target.metadata) {
if (prop in target.metadata) {
return (target.metadata as any)[prop];
}
@ -95,14 +107,14 @@ const gameProxyHandler: ProxyHandler<GameRoom> = {
set(target: GameRoom, prop: string | symbol, value: any): boolean {
// Direct room properties
const roomProps = ['id', 'name', 'sessions', 'state', 'created', 'lastActivity', 'private'];
if (typeof prop === 'string' && roomProps.includes(prop)) {
const roomProps = ["id", "name", "sessions", "state", "created", "lastActivity", "private"];
if (typeof prop === "string" && roomProps.includes(prop)) {
(target as any)[prop] = value;
return true;
}
// Game properties to metadata
if (typeof prop === 'string') {
if (typeof prop === "string") {
if (!target.metadata) {
target.metadata = {} as any;
}
@ -115,8 +127,8 @@ const gameProxyHandler: ProxyHandler<GameRoom> = {
},
has(target: GameRoom, prop: string | symbol): boolean {
const roomProps = ['id', 'name', 'sessions', 'state', 'created', 'lastActivity', 'private'];
if (typeof prop === 'string') {
const roomProps = ["id", "name", "sessions", "state", "created", "lastActivity", "private"];
if (typeof prop === "string") {
if (roomProps.includes(prop)) return true;
if (target.metadata && prop in target.metadata) return true;
}
@ -147,7 +159,9 @@ export function wrapGameSessions(game: GameRoom): GameRoom {
// Wrap each session
const wrappedSessions: Record<string, GameSession> = {};
for (const id in game.sessions) {
wrappedSessions[id] = wrapSession(game.sessions[id]);
if (game.sessions[id]) {
wrappedSessions[id] = wrapSession(game.sessions[id]);
}
}
wrappedGame.sessions = wrappedSessions;

View File

@ -3,7 +3,7 @@
* These extend the base Room/Session types with Settlers of Catan specific data
*/
import type { Player, Turn, Placements, DevelopmentCard } from './types';
import type { Player, Turn, Placements, DevelopmentCard } from "./types";
/**
* Game-specific session metadata
@ -163,7 +163,7 @@ export function migrateGameToRoomFormat(oldGame: any): GameRoom {
id: oldGame.id,
name: oldGame.id, // Game ID is the room name
sessions: newSessions,
state: oldGame.state || 'lobby',
state: oldGame.state || "lobby",
created: Date.now(),
lastActivity: Date.now(),
private: false,
@ -180,7 +180,9 @@ export function migrateRoomToGameFormat(room: GameRoom): any {
// Convert sessions back
const oldSessions: Record<string, any> = {};
for (const sessionId in sessions) {
oldSessions[sessionId] = migrateSessionToOldFormat(sessions[sessionId]);
if (sessions[sessionId]) {
oldSessions[sessionId] = migrateSessionToOldFormat(sessions[sessionId]);
}
}
return {

View File

@ -167,3 +167,22 @@ export const setForSettlementPlacement = (game: Game, limits: number[] | undefin
game.turn.actions = ["place-settlement"];
game.turn.limits = { corners: limits };
};
// Adjust a player's resource counts by a deltas map. Deltas may be negative.
export const adjustResources = (player: Player, deltas: Partial<Record<string, number>>): void => {
if (!player) return;
let total = player.resources || 0;
const keys = Object.keys(deltas || {});
keys.forEach((k) => {
const v = deltas[k] || 0;
// update named resource slot if present
try {
const current = (player as any)[k] || 0;
(player as any)[k] = current + v;
total += v;
} catch (e) {
// ignore unexpected keys
}
});
player.resources = total;
};

View File

@ -1,6 +1,6 @@
export type ResourceKey = "wood" | "brick" | "sheep" | "wheat" | "stone";
export type ResourceMap = Partial<Record<ResourceKey, number>> & { [k: string]: any };
export type ResourceMap = Partial<Record<ResourceKey, number>>;
export interface Player {
name?: string;
@ -124,7 +124,7 @@ export interface Game {
turn: Turn;
pipOrder?: number[];
tileOrder?: number[];
borderOrder?: number[];
resources?: number;
tiles?: any[];
pips?: any[];
dice?: number[];