# Mount & Composition

Mount additional mock services onto a running LLMock server. All services share one port, one health endpoint, and one request journal — no port juggling, no service discovery.

## Mountable Interface

Any object that implements the `Mountable` interface can be mounted onto LLMock. The interface requires a single method:

Mountable interface typescript

    interface Mountable {
      /** Handle an incoming HTTP request. Return true if handled. */
      handleRequest(
        req: IncomingMessage,
        res: ServerResponse,
        pathname: string,
      ): Promise<boolean>;

      /** Optional: handle WebSocket upgrades. */
      handleUpgrade?(
        socket: Socket,
        head: Buffer,
        pathname: string,
      ): Promise<boolean>;

      /** Optional: health check. */
      health?(): { status: string; [key: string]: unknown };

      /** Optional: receive the shared journal instance. */
      setJournal?(journal: Journal): void;

      /** Optional: receive the base URL when mounted. */
      setBaseUrl?(url: string): void;
    }

## LLMock.mount()

Mount a `Mountable` service at a path prefix. Requests matching the prefix are forwarded to the service with the prefix stripped.

mount() API typescript

    const llm = new LLMock({ port: 5555 });

    llm.mount("/mcp", mcpMock);   // MCP tools at /mcp
    llm.mount("/a2a", a2aMock);   // A2A agents at /a2a

    await llm.start();
    // All protocols accessible on port 5555

### Path Stripping

When a request arrives at a mounted path, the prefix is stripped before the service sees it. For example, a request to `/mcp/tools/list` arrives at the MCP service with pathname `/tools/list`.

Incoming Request | Mount Prefix | Service Sees
--- | --- | ---
`POST /mcp/tools/list` | `/mcp` | `/tools/list`
`POST /a2a/agents/run` | `/a2a` | `/agents/run`
`GET /mcp` | `/mcp` | `/`

### WebSocket Upgrade Support

If a mounted service implements `handleUpgrade()`, WebSocket upgrade requests matching the mount prefix are forwarded to it. This enables WebSocket-based protocols like MCP over StreamableHTTP or custom agent protocols.

## Unified Health Endpoint

The `GET /health` endpoint aggregates health from all mounted services. Each service that implements `health()` is included in the response:

Health response json

    {
      "status": "ok",
      "services": {
        "llm": { "status": "ok", "fixtures": 5 },
        "mcp": { "status": "ok", "tools": 2, "resources": 1, "prompts": 0, "sessions": 0 },
        "a2a": { "status": "ok", "agents": 1, "tasks": 0 }
      }
    }

Each mounted service that implements `health()` contributes its status to the response. The health endpoint always returns HTTP 200.

## Shared Journal

All mounted services share the same request journal. Journal entries include a `service` field indicating which service handled the request:

Journal entry typescript

    const entries = mock.getRequests();
    // [
    //   { service: "llm", method: "POST", path: "/v1/chat/completions", ... },
    //   { service: "/mcp", method: "POST", path: "/tools/list", ... },
    // ]

## createMockSuite()

`createMockSuite()` provides a unified lifecycle for LLMock and all mounted services. It creates the server, mounts services, and returns `start()` / `stop()` / `reset()` methods that manage everything together.

createMockSuite() typescript

    import { createMockSuite } from "@copilotkit/aimock";

    const suite = await createMockSuite({
      llm: { port: 0 },
      mcp: {},    // enables MCPMock, mounted at /mcp
      a2a: {},    // enables A2AMock, mounted at /a2a
      vector: {}, // enables VectorMock, mounted at /vector
    });

    await suite.start();
    // suite.llm — the underlying LLMock instance
    // suite.mcp — MCPMock instance (if configured)
    // suite.a2a — A2AMock instance (if configured)
    // suite.vector — VectorMock instance (if configured)

    // In tests:
    afterEach(() => suite.reset());     // resets LLM fixtures + all service state
    afterAll(() => suite.stop());       // stops everything

## Built-in Services

aimock ships with first-party mock services that implement the `Mountable` interface:

- MCPMock — Mock MCP tool server with JSON-RPC dispatch, session management, and tool/resource/prompt support
- A2AMock — Mock A2A agent-to-agent protocol server with agent cards, message routing, and streaming
- VectorMock — Mock vector database with Pinecone, Qdrant, and ChromaDB endpoints

All implement the `Mountable` interface and work with `mount()`, `createMockSuite()`, and the aimock CLI.