feat(api): world/system/crew snapshots expose the active + pending task queue (#44)

This commit is contained in:
2026-10-02 19:42:19 +00:00
parent 178de6e4fb
commit 84d1aa8122
7 changed files with 212 additions and 24 deletions
+23 -3
View File
@@ -120,10 +120,20 @@ describe('OpenAPI spec', () => {
expect(get.responses['400'].content['application/json'].schema.$ref).toBe('#/components/schemas/Error');
});
it('describes /api/crew as an array of CrewMember and crewFound on ExploreResult', () => {
it('describes /api/crew as the CrewState { crew, tasks } object and crewFound on ExploreResult', () => {
const crew = openApiSpec.paths['/api/crew'].get.responses[200].content['application/json'].schema;
expect(crew.type).toBe('array');
expect((crew.items as { $ref: string }).$ref).toBe('#/components/schemas/CrewMember');
expect(crew.$ref).toBe('#/components/schemas/CrewState');
const crewState = openApiSpec.components.schemas.CrewState as { properties: Record<string, unknown>; required: string[] };
expect(Object.keys(crewState.properties)).toEqual(['crew', 'tasks']);
expect(crewState.required).toEqual(['crew', 'tasks']);
expect((crewState.properties.crew as { items: { $ref: string } }).items.$ref).toBe('#/components/schemas/CrewMember');
expect((crewState.properties.tasks as { items: { $ref: string } }).items.$ref).toBe('#/components/schemas/TaskDto');
const taskDto = openApiSpec.components.schemas.TaskDto as { properties: Record<string, unknown>; required: string[] };
expect(Object.keys(taskDto.properties)).toEqual(['id', 'type', 'targetLabel', 'leadName', 'helperNames', 'remaining']);
expect(taskDto.required).toEqual(['id', 'type', 'targetLabel', 'leadName', 'helperNames', 'remaining']);
expect((taskDto.properties.type as { enum: string[] }).enum).toEqual(['JUMP', 'EXPLORE', 'SHIP_UPGRADE', 'SHIP_EXPAND', 'SHIP_BUILD', 'RESEARCH']);
const member = openApiSpec.components.schemas.CrewMember.properties;
expect(Object.keys(member)).toEqual(['id', 'name', 'role', 'trait_good', 'trait_bad', 'origin']);
@@ -137,6 +147,11 @@ describe('OpenAPI spec', () => {
const system = openApiSpec.paths['/api/system'].get.responses[200].content['application/json'].schema;
expect(system.$ref).toBe('#/components/schemas/SystemState');
// The snapshot carries the active + pending task queue.
const systemState = openApiSpec.components.schemas.SystemState as { properties: Record<string, unknown>; required: string[] };
expect(systemState.required).toEqual(['systemId', 'systemName', 'planets', 'inventory', 'turn', 'tasks']);
expect((systemState.properties.tasks as { items: { $ref: string } }).items.$ref).toBe('#/components/schemas/TaskDto');
const explore = openApiSpec.paths['/api/explore'].post;
expect(explore.requestBody.content['application/json'].schema.$ref).toBe('#/components/schemas/ExploreRequest');
expect(explore.responses[200].content['application/json'].schema.$ref).toBe('#/components/schemas/ExploreResult');
@@ -158,6 +173,11 @@ describe('OpenAPI spec', () => {
const world = openApiSpec.paths['/api/world'].get.responses[200].content['application/json'].schema;
expect(world.$ref).toBe('#/components/schemas/WorldState');
// The snapshot carries the active + pending task queue.
const worldState = openApiSpec.components.schemas.WorldState as { properties: Record<string, unknown>; required: string[] };
expect(worldState.required).toEqual(['systems', 'edges', 'turn', 'tasks']);
expect((worldState.properties.tasks as { items: { $ref: string } }).items.$ref).toBe('#/components/schemas/TaskDto');
const jump = openApiSpec.paths['/api/jump'].post;
expect(jump.requestBody.content['application/json'].schema.$ref).toBe('#/components/schemas/JumpRequest');
expect(jump.responses[200].content['application/json'].schema.$ref).toBe('#/components/schemas/WorldState');