Fork Horse repository, listed by its owner. Publisher snapshot.
packages/forkhorse-mcp/__tests__/fixtures.ts
Snapshot at 34e3175
1import { createCoreClient } from "../src/core";
2import type { AgentIdentity, ClaimBinding, CoreClient } from "../src/core";
3
4/** In-process, labeled FH-003/FH-005 fixture. It performs no provider calls. */
5export class FixtureCore {
6 tokens = new Map<string, AgentIdentity>([
7 ["api_fixture_builder", { project: "demo", agent: "builder" }],
8 ]);
9 claims: ClaimBinding[] = [{ packet: "FH-004", agent: "builder", repoName: "demo--builder-1" }];
10 work: unknown[] = [];
11 requests: Pick<Request, "url" | "method" | "headers" | "json">[] = [];
12 enrollments = 0;
13 forks = 1;
14 failure: number | undefined;
15 payload: unknown;
16 client: CoreClient = createCoreClient({
17 authenticate: async (token) => this.tokens.get(token) ?? null,
18 enrollAgent: async (_owner, project, agent) => {
19 this.enrollments++;
20 const apiToken = `api_fixture_oauth_${this.enrollments}`;
21 this.tokens.set(apiToken, { project, agent });
22 return { apiToken, project, agent };
23 },
24 fetch: async (request) => {
25 this.requests.push(request.clone());
26 if (this.failure)
27 return Response.json(
28 { secret: "provider_fixture_exception_do_not_echo" },
29 { status: this.failure },
30 );
31 if (this.payload !== undefined) return Response.json(this.payload);
32 const path = new URL(request.url).pathname;
33 if (path.endsWith("/me")) return Response.json({ work: this.work });
34 if (path.endsWith("/state")) return Response.json({ claims: this.claims, fixture: true });
35 if (path.endsWith("/join"))
36 return Response.json({ repoName: `demo--builder-${++this.forks}`, fixture: true });
37 if (path.endsWith("/claim")) {
38 const input = (await request.json()) as { repoName?: string };
39 const binding = {
40 packet: "FH-004",
41 agent: "builder",
42 repoName: input.repoName ?? `demo--builder-${this.forks}`,
43 };
44 this.claims = [binding];
45 return Response.json(binding);
46 }
47 return Response.json({ fixture: true, sha: "a".repeat(40) });
48 },
49 });
50}
51
52/** Minimal in-memory KV semantics used by the real OAuth library in these Node tests. */
53export function fixtureKv(): KVNamespace {
54 const values = new Map<string, string>();
55 return {
56 async get(key: string, type?: string | { type?: string }) {
57 const value = values.get(key);
58 if (value === undefined) return null;
59 return (typeof type === "string" ? type : type?.type) === "json" ? JSON.parse(value) : value;
60 },
61 async put(key: string, value: string) {
62 values.set(key, value);
63 },
64 async delete(key: string) {
65 values.delete(key);
66 },
67 async list(options?: { prefix?: string }) {
68 return {
69 keys: [...values.keys()]
70 .filter((key) => key.startsWith(options?.prefix ?? ""))
71 .map((name) => ({ name })),
72 list_complete: true,
73 cacheStatus: null,
74 };
75 },
76 } as unknown as KVNamespace;
77}
78export function fixtureContext(): ExecutionContext {
79 return { props: {}, waitUntil() {}, passThroughOnException() {} } as unknown as ExecutionContext;
80}
81