import { expect } from "vitest"; import { createAndSelectWorkspace, denFetch, evalIn, fill, go, readAvailableModels, selectModel, sendComposerMessage, waitFor, waitForAssistantReply, } from "@openwork/behaviors"; import type { DenSession, ModelFacts } from "@openwork/behaviors"; import { screenshot, validate } from "@openwork/test-evidence"; import { desktop as launchDesktop } from "@openwork/hosts"; import { eventually, liteLlm, needs, server, SkipError, test, unmetNeeds, } from "@openwork/testkit"; import type { TestNeeds } from "@openwork/testkit"; const ORGANIZATION_NAME = "Den Lab"; const PROVIDER_NAME = "LiteLLM Gateway"; const PROVIDER_KEY = "openwork-litellm-witness"; const MODEL_ID = "openwork-litellm-witness-model"; const MODEL_NAME = "Witness Model"; const PROVIDER_ENV = "LITELLM_WITNESS_API_KEY"; const REPLY = "The deterministic LiteLLM route is working."; const REQUEST_TIMEOUT_MS = 10_000; const TEST_CONNECTION_TIMEOUT_MS = 60_000; const placementCommand = process.env.OPENWORK_EVAL_DAYTONA?.trim() === "1" ? "daytona" : "docker"; const requirements: TestNeeds = { optIn: ["OPENWORK_EVAL_E2E_TESTS"], commands: [placementCommand] }; const missingRequirements = unmetNeeds(requirements, process.env); const title = missingRequirements.length > 0 ? `Den LiteLLM provider route skipped — needs: ${missingRequirements.join(", ")}` : "a Den provider syncs to desktop and reaches its upstream through LiteLLM"; function isRecord(value: unknown): value is Record { return typeof value === "object" && value !== null && !Array.isArray(value); } function auth(session: DenSession): Record { return { authorization: `Bearer ${session.token}` }; } async function organizationId(session: DenSession): Promise { const result = await denFetch(session, "/v1/me/orgs", { headers: auth(session), signal: AbortSignal.timeout(REQUEST_TIMEOUT_MS), }); const organizations = isRecord(result.body) && Array.isArray(result.body.orgs) ? result.body.orgs.filter(isRecord) : []; const organization = organizations.find((entry) => entry.name === ORGANIZATION_NAME); const id = organization && typeof organization.id === "string" ? organization.id : ""; if (!result.response.ok || !id) { throw new Error(`Finding the test organization failed: HTTP ${result.response.status} ${result.text.slice(0, 500)}`); } return id; } async function testConnection(admin: DenSession, orgId: string, baseUrl: string, apiKey: string): Promise> { const response = await denFetch(admin, "/v1/llm-providers/test-connection", { method: "POST", headers: { ...auth(admin), "x-openwork-org-id": orgId }, body: JSON.stringify({ api: baseUrl, apiKey, modelIds: [MODEL_ID] }), signal: AbortSignal.timeout(TEST_CONNECTION_TIMEOUT_MS), }); if (!response.response.ok || !isRecord(response.body)) { throw new Error(`Testing the LiteLLM connection failed: HTTP ${response.response.status} ${response.text.slice(0, 500)}`); } return response.body; } async function createProvider(admin: DenSession, orgId: string, baseUrl: string, apiKey: string): Promise { const result = await denFetch(admin, "/v1/llm-providers", { method: "POST", headers: { ...auth(admin), "x-openwork-org-id": orgId }, body: JSON.stringify({ name: PROVIDER_NAME, source: "custom", customConfig: { id: PROVIDER_KEY, name: PROVIDER_NAME, npm: "@ai-sdk/openai-compatible", env: [PROVIDER_ENV], api: baseUrl, models: [{ id: MODEL_ID, name: MODEL_NAME }], }, apiKey, allMembers: true, memberIds: [], teamIds: [], }), signal: AbortSignal.timeout(REQUEST_TIMEOUT_MS), }); const provider = isRecord(result.body) && isRecord(result.body.llmProvider) ? result.body.llmProvider : null; const id = provider && typeof provider.id === "string" ? provider.id : ""; if (result.response.status !== 201 || !id) { throw new Error(`Creating the LiteLLM provider failed: HTTP ${result.response.status} ${result.text.slice(0, 500)}`); } return id; } async function deleteProvider(admin: DenSession, orgId: string, providerId: string): Promise { await denFetch(admin, `/v1/llm-providers/${encodeURIComponent(providerId)}`, { method: "DELETE", headers: { ...auth(admin), "x-openwork-org-id": orgId }, signal: AbortSignal.timeout(REQUEST_TIMEOUT_MS), }); } interface SyncFacts { lastRunStatus: string; lastRunMessage: string; providerIds: string[]; skippedProviders: unknown[]; raw: Record; } async function readSyncStatus(desktop: Parameters[0]): Promise { const value = await evalIn(desktop, `(async () => { const port = localStorage.getItem("openwork.server.port"); const token = localStorage.getItem("openwork.server.token"); if (!port || !token) return { error: "missing local server credentials" }; const response = await fetch("http://127.0.0.1:" + port + "/cloud-provider-sync/status", { headers: { Authorization: "Bearer " + token }, signal: AbortSignal.timeout(10000), }); if (!response.ok) return { error: "HTTP " + response.status }; return await response.json(); })()`, { awaitPromise: true, timeoutMs: 15_000 }); if (!isRecord(value) || typeof value.error === "string") { throw new Error(`Reading cloud provider sync status failed: ${JSON.stringify(value)}`); } const lastRun = isRecord(value.lastRun) ? value.lastRun : {}; const providers = Array.isArray(value.providers) ? value.providers.filter(isRecord) : []; return { lastRunStatus: typeof lastRun.status === "string" ? lastRun.status : "", lastRunMessage: typeof lastRun.message === "string" ? lastRun.message : "", providerIds: providers.flatMap((provider) => typeof provider.cloudProviderId === "string" ? [provider.cloudProviderId] : []), skippedProviders: Array.isArray(value.skippedProviders) ? value.skippedProviders : [], raw: value, }; } async function runDirectProviderSync( desktop: Parameters[0], input: { baseUrl: string; token: string; orgId: string }, ): Promise> { const value = await evalIn(desktop, `(async () => { const info = await window.__OPENWORK_ELECTRON__?.invokeDesktop?.("openworkServerInfo"); if (!info?.running || !info.baseUrl || !info.hostToken) return { error: "local_server_unavailable" }; const request = async (path, method, body) => { const response = await fetch(String(info.baseUrl).replace(/\\/+$/, "") + path, { method, headers: { Authorization: "Bearer " + String(info.hostToken), "Content-Type": "application/json", "x-openwork-host-token": String(info.hostToken), }, body: JSON.stringify(body), }); const text = await response.text(); let payload = text; try { payload = text ? JSON.parse(text) : null; } catch {} return { status: response.status, body: payload }; }; const session = await request("/den-session", "PUT", ${JSON.stringify(input)}); if (session.status !== 204) return { error: "den_session_failed", session }; const sync = await request("/cloud-provider-sync/run", "POST", { reason: "eval_litellm_provider" }); if (sync.status !== 200) return { error: "sync_run_failed", sync }; return sync.body; })()`, { awaitPromise: true, timeoutMs: 30_000 }); if (!isRecord(value) || typeof value.error === "string") { throw new Error(`Triggering direct provider sync failed: ${JSON.stringify(value)}`); } return value; } async function seedRendererDenSession( desktop: Parameters[0], input: { token: string; orgId: string; webUrl: string }, ): Promise { const value = await evalIn(desktop, `(async () => { const { seedDenDesktopConfigConnectPolicy, writeDenSettings } = await import("/src/app/lib/den.ts"); const { dispatchDenSessionUpdated } = await import("/src/app/lib/den-session-events.ts"); writeDenSettings({ baseUrl: ${JSON.stringify(input.webUrl)}, authToken: ${JSON.stringify(input.token)}, activeOrgId: ${JSON.stringify(input.orgId)}, activeOrgSlug: null, activeOrgName: ${JSON.stringify(ORGANIZATION_NAME)}, }); seedDenDesktopConfigConnectPolicy({ organizationId: ${JSON.stringify(input.orgId)}, connectEnabled: true, }); dispatchDenSessionUpdated({ status: "success", baseUrl: ${JSON.stringify(input.webUrl)}, token: ${JSON.stringify(input.token)}, user: null, email: null, }); return { ok: true }; })()`, { awaitPromise: true, timeoutMs: 60_000 }); if (!isRecord(value) || value.ok !== true) { throw new Error(`Seeding the renderer Den session failed: ${JSON.stringify(value)}`); } await waitFor(desktop, "Boolean((localStorage.getItem('openwork.den.authToken') ?? '').trim())", { timeoutMs: 45_000, label: "persisted Den auth token after session seed", }); } test.skipIf(missingRequirements.length > 0)(title, { timeout: 30 * 60_000 }, async ({ evidence, place }) => { needs(requirements); if (process.env.OPENWORK_EVAL_DEN_API_URL?.trim()) { throw new SkipError("The LiteLLM provider proof requires a cold managed Den"); } await using gateway = await liteLlm({ place, modelId: MODEL_ID, reply: REPLY }); await using den = await server({ place, org: { name: ORGANIZATION_NAME, admin: { name: "Provider Admin" }, members: { member: { name: "Provider Member" } }, }, }); const member = den.members.member; if (!member) throw new Error("The cold managed Den did not provision the member."); const orgId = await organizationId(den.admin); const probeCheckpoint = await gateway.checkpoint(); const probeResponse = await testConnection(den.admin, orgId, gateway.baseUrl, gateway.apiKey); const probeResult = isRecord(probeResponse.result) ? probeResponse.result : {}; const discoveredModels = Array.isArray(probeResult.models) ? probeResult.models.filter(isRecord) : []; const verifications = Array.isArray(probeResponse.verifications) ? probeResponse.verifications.filter(isRecord) : []; const verification = verifications.find((entry) => entry.id === MODEL_ID); expect(probeResult.ok).toBe(true); expect(discoveredModels.some((entry) => entry.id === MODEL_ID)).toBe(true); expect(verification?.status).toBe("ok"); const probeRequest = await gateway.waitForUpstreamRequest({ after: probeCheckpoint, model: MODEL_ID, key: gateway.upstreamKey, timeoutMs: 120_000, }); const probeRequests = await gateway.upstreamRequests({ after: probeCheckpoint }); const probeUsedUpstreamKey = probeRequest.tokenId === gateway.tokenId(gateway.upstreamKey); const probeMasterKeyReachedUpstream = probeRequests .some((request) => request.tokenId === gateway.tokenId(gateway.apiKey)); evidence.recordAssertionEvidence( "Den verified the discovered LiteLLM model through the deterministic upstream", `The endpoint probe discovered ${MODEL_ID}, verification was ${String(verification?.status)}, and upstream sequence ${probeRequest.sequence} carried only the rewritten token fingerprint.`, probeResult.ok === true && discoveredModels.some((entry) => entry.id === MODEL_ID) && verification?.status === "ok" && probeUsedUpstreamKey && !probeMasterKeyReachedUpstream, ); expect(probeUsedUpstreamKey).toBe(true); expect(probeMasterKeyReachedUpstream).toBe(false); const cloudProviderId = await createProvider(den.admin, orgId, gateway.baseUrl, gateway.apiKey); await using publishedProvider = { async [Symbol.asyncDispose]() { await deleteProvider(den.admin, orgId, cloudProviderId).catch(() => undefined); }, }; await using desktop = await launchDesktop({ name: "den-litellm-provider", host: place.host(), bootstrap: { baseUrl: den.ref.webUrl, requireSignin: false, }, }); await seedRendererDenSession(desktop, { token: member.token, orgId, webUrl: den.ref.webUrl, }); await runDirectProviderSync(desktop, { baseUrl: den.ref.apiUrl, token: member.token, orgId }); const sync = await eventually(() => readSyncStatus(desktop), { within: 120_000, intervalMs: 2_000, label: "terminal LiteLLM provider sync", until: (status) => status.lastRunStatus === "failed" || (status.providerIds.includes(cloudProviderId) && (status.lastRunStatus === "applied" || status.lastRunStatus === "noop")), }); const synced = sync.providerIds.includes(cloudProviderId) && (sync.lastRunStatus === "applied" || sync.lastRunStatus === "noop"); evidence.recordAssertionEvidence( "Den's custom provider reached a terminal desktop sync outcome", `Provider appeared in sync status with lastRun=${sync.lastRunStatus}; payload: ${JSON.stringify(sync.raw)}`, synced, ); expect(synced, `Cloud provider sync failed: ${sync.lastRunMessage || "no message"}; skipped: ${JSON.stringify(sync.skippedProviders)}; payload: ${JSON.stringify(sync.raw)}`).toBe(true); const { workspaceId } = await createAndSelectWorkspace(desktop, { path: "/tmp/litellm-demo" }); await desktop.client.send("Emulation.setDeviceMetricsOverride", { width: 1440, height: 900, deviceScaleFactor: 1, mobile: false, }); await go(desktop, `/workspace/${workspaceId}/session`); await waitFor(desktop, "Boolean(window.__openworkControl)", { timeoutMs: 120_000, label: "desktop session control", }); const models = await eventually(() => readAvailableModels(desktop), { within: 60_000, intervalMs: 2_000, label: "selectable LiteLLM witness model", until: (available) => available.some((model) => model.selectable && (model.id === MODEL_ID || model.id.endsWith(`/${MODEL_ID}`))), }); const model = models.find((candidate) => candidate.selectable && (candidate.id === MODEL_ID || candidate.id.endsWith(`/${MODEL_ID}`))); const modelAvailable = model !== undefined; evidence.recordAssertionEvidence( "The synced provider's model became selectable in the desktop", `Selectable model ids: ${JSON.stringify(models.filter((candidate) => candidate.selectable).map((candidate) => candidate.id))}`, modelAvailable, ); expect(modelAvailable).toBe(true); if (!model) throw new Error("The LiteLLM witness model was not selectable."); await fill(desktop, 'input[placeholder="Search providers and models..."]', MODEL_NAME); await waitFor(desktop, `(() => { const dialog = document.querySelector('[data-slot="dialog-content"]'); return Boolean(dialog && dialog.innerText.includes(${JSON.stringify(PROVIDER_NAME)}) && dialog.innerText.includes(${JSON.stringify(MODEL_NAME)})); })()`, { timeoutMs: 30_000, label: "LiteLLM provider and model in picker" }); const pickerLayout = await evalIn(desktop, `(() => { const dialog = document.querySelector('[data-slot="dialog-content"]'); const model = [...(dialog?.querySelectorAll("button") ?? [])].find((element) => (element.textContent ?? "").includes(${JSON.stringify(MODEL_NAME)})); const rect = model?.getBoundingClientRect(); return { dialogVisible: Boolean(dialog && dialog.getBoundingClientRect().height > 100), modelVisible: Boolean(rect && rect.width > 0 && rect.height > 0 && rect.top >= 0 && rect.bottom <= window.innerHeight), }; })()`); const pickerReady = isRecord(pickerLayout) && pickerLayout.dialogVisible === true && pickerLayout.modelVisible === true; evidence.recordAssertionEvidence( "The Den-managed LiteLLM model is structurally visible in the model picker", `Model picker layout probe: ${JSON.stringify(pickerLayout)}`, pickerReady, ); expect(pickerReady).toBe(true); const pickerShot = await screenshot(desktop); const pickerSeen = await validate(pickerShot, [ `The model picker visibly shows provider ${PROVIDER_NAME} and model ${MODEL_NAME}`, "The LiteLLM model is presented as selectable, without unavailable, credential, syncing, or error text", "The model picker is polished and legible with no overlap, clipping, blank panel, or stray overlay", ]); expect(pickerSeen.ok, pickerSeen.why).toBe(true); const selected: ModelFacts = await selectModel(desktop, model.id); expect(selected.selected).toBe(true); const prompt = "Please answer with one short sentence confirming this test route works."; expect(prompt).not.toContain(PROVIDER_KEY); expect(prompt).not.toContain(MODEL_ID); expect(prompt).not.toContain(orgId); const desktopCheckpoint = await gateway.checkpoint(); await sendComposerMessage(desktop, prompt); const upstreamRequest = await gateway.waitForUpstreamRequest({ after: desktopCheckpoint, model: MODEL_ID, key: gateway.upstreamKey, timeoutMs: 120_000, }); const requestUsedUpstreamKey = upstreamRequest.tokenId === gateway.tokenId(gateway.upstreamKey); const requestContainsPrompt = upstreamRequest.bodyText.includes(prompt); const masterKeyReachedUpstream = (await gateway.upstreamRequests({ after: desktopCheckpoint })) .some((request) => request.tokenId === gateway.tokenId(gateway.apiKey)); evidence.recordAssertionEvidence( "The desktop request traversed LiteLLM and LiteLLM rewrote the bearer key for the deterministic upstream", `Upstream saw model ${upstreamRequest.model}, token fingerprint ${upstreamRequest.tokenId}, and no master-key fingerprint after submission.`, requestUsedUpstreamKey && requestContainsPrompt && !masterKeyReachedUpstream, ); expect(requestContainsPrompt).toBe(true); expect(requestUsedUpstreamKey).toBe(true); expect(masterKeyReachedUpstream).toBe(false); await waitFor(desktop, `([...document.querySelectorAll('[data-message-role="assistant"]')] .some((message) => (message.innerText ?? "").includes(${JSON.stringify(REPLY)})))`, { timeoutMs: 120_000, label: "complete deterministic LiteLLM reply", }); const assistant = await waitForAssistantReply(desktop, { timeoutMs: 10_000 }); const rendered = assistant.text.includes(REPLY); evidence.recordAssertionEvidence( "The deterministic upstream reply rendered in the desktop conversation", `Latest assistant message contained ${JSON.stringify(REPLY)}.`, rendered, ); expect(rendered).toBe(true); });