diff --git a/packages/server/src/server/daemon.e2e.test.ts b/packages/server/src/server/daemon.e2e.test.ts index 490daea34..19615b06b 100644 --- a/packages/server/src/server/daemon.e2e.test.ts +++ b/packages/server/src/server/daemon.e2e.test.ts @@ -1454,4 +1454,54 @@ describe("daemon E2E", () => { 60000 // 1 minute timeout ); }); + + describe("listProviderModels", () => { + test( + "returns model list for Codex provider", + async () => { + // List models for Codex provider - no agent needed + const result = await ctx.client.listProviderModels("codex"); + + // Verify response structure + expect(result.provider).toBe("codex"); + expect(result.error).toBeNull(); + expect(result.fetchedAt).toBeTruthy(); + + // Should return at least one model + expect(result.models).toBeTruthy(); + expect(result.models.length).toBeGreaterThan(0); + + // Verify model structure + const model = result.models[0]; + expect(model.provider).toBe("codex"); + expect(model.id).toBeTruthy(); + expect(model.label).toBeTruthy(); + }, + 60000 // 1 minute timeout + ); + + test( + "returns model list for Claude provider", + async () => { + // List models for Claude provider - no agent needed + const result = await ctx.client.listProviderModels("claude"); + + // Verify response structure + expect(result.provider).toBe("claude"); + expect(result.error).toBeNull(); + expect(result.fetchedAt).toBeTruthy(); + + // Should return at least one model + expect(result.models).toBeTruthy(); + expect(result.models.length).toBeGreaterThan(0); + + // Verify model structure + const model = result.models[0]; + expect(model.provider).toBe("claude"); + expect(model.id).toBeTruthy(); + expect(model.label).toBeTruthy(); + }, + 60000 // 1 minute timeout + ); + }); }); diff --git a/packages/server/src/server/test-utils/daemon-client.ts b/packages/server/src/server/test-utils/daemon-client.ts index b624babe4..b90f61545 100644 --- a/packages/server/src/server/test-utils/daemon-client.ts +++ b/packages/server/src/server/test-utils/daemon-client.ts @@ -8,6 +8,7 @@ import type { PersistedAgentDescriptorPayload, } from "../messages.js"; import type { + AgentModelDefinition, AgentPermissionRequest, AgentPermissionResponse, AgentPersistenceHandle, @@ -489,6 +490,47 @@ export class DaemonClient { ); } + // ============================================================================ + // Provider Models + // ============================================================================ + + async listProviderModels( + provider: AgentProvider, + options?: { cwd?: string } + ): Promise<{ + provider: AgentProvider; + models: AgentModelDefinition[]; + fetchedAt: string; + error: string | null; + }> { + const startPosition = this.messageQueue.length; + + this.send({ + type: "list_provider_models_request", + provider, + cwd: options?.cwd, + }); + + return this.waitFor( + (msg) => { + if ( + msg.type === "list_provider_models_response" && + msg.payload.provider === provider + ) { + return { + provider: msg.payload.provider, + models: msg.payload.models ?? [], + fetchedAt: msg.payload.fetchedAt, + error: msg.payload.error ?? null, + }; + } + return null; + }, + 30000, + { skipQueueBefore: startPosition } + ); + } + // ============================================================================ // Permissions // ============================================================================