Files
template-app/modules/agent/__tests__/isolation.ts
T
2026-11-14 09:56:45 +00:00

52 lines
2.7 KiB
TypeScript

// What the generated tenant-isolation suite needs of this module: seeds and one fixture per
// tenant-scoped procedure, built from the OTHER tenant's ids.
import type { TransportCaller } from "@conusai-kit/core"
import type { IsolationFixture, IsolationTenant } from "@conusai-kit/testing"
export interface ModuleIsolation {
seed(
call: TransportCaller,
inProject: { org: string; workspace: string; project: string },
): Promise<Record<string, string>>
fixtures: Record<string, IsolationFixture>
}
const NOWHERE = "00000000-0000-0000-0000-000000000000"
const inWorkspaceOf = (t: IsolationTenant) => ({ org: t.orgSlug, workspace: t.workspaceSlug })
const inProjectOf = (t: IsolationTenant) => ({ ...inWorkspaceOf(t), project: t.projectSlug })
const runOf = (t: IsolationTenant) => t.extra.agentRunId ?? NOWHERE
const PLAN = [{ key: "read", label: "Read", tool: "documents.read", args: {} }]
export const isolation: ModuleIsolation = {
async seed(call, inProject) {
const started = (await call.callByName("agent.run.start", { ...inProject, goal: "Seed run", plan: PLAN })) as {
runId: string
}
return { agentRunId: started.runId }
},
fixtures: {
"agent.run.start": { input: (t) => ({ ...inProjectOf(t), goal: "Intruder", plan: PLAN }) },
"agent.run.status": { input: (t) => ({ ...inProjectOf(t), runId: runOf(t) }) },
"agent.run.events": { input: (t) => ({ ...inProjectOf(t), runId: runOf(t) }) },
"agent.run.cancel": { input: (t) => ({ ...inProjectOf(t), runId: runOf(t) }) },
"agent.run.list": { input: (t) => inProjectOf(t) },
// The live collection's read-back: another tenant's run id answers nothing.
"agent.run.getMany": { input: (t) => ({ ...inProjectOf(t), ids: [runOf(t)] }) },
"agent.approval.list": { input: (t) => inProjectOf(t) },
"agent.approval.review": {
input: (t) => ({ ...inProjectOf(t), runId: runOf(t), stepKey: "read", decision: "approve" }),
},
// The conversation behind the Agent in the right panel (kit-agent's assistant module, mounted by this one).
"assistant.turn.send": { input: (t) => ({ ...inProjectOf(t), turnId: NOWHERE, message: "Intruder" }) },
"assistant.conversation.list": { input: (t) => inProjectOf(t) },
"assistant.rootAction.reconcile": { input: (t) => ({ ...inProjectOf(t), conversationId: NOWHERE }) },
"assistant.conversation.get": { input: (t) => ({ ...inProjectOf(t), conversationId: NOWHERE }) },
"assistant.receipt.list": { input: (t) => inProjectOf(t) },
// The Agent's own workspace reads, offered to a turn with no project open.
"assistant.workspace.projects": { input: (t) => inWorkspaceOf(t) },
"assistant.workspace.openProject": { input: (t) => ({ ...inWorkspaceOf(t), slug: t.projectSlug }) },
},
}