Repository navigation
feat(mcp): serve the Lore tools over Streamable HTTP - #165
Merged
Merged
Conversation
An Agent connects with the same Authorization and x-lore-workspace-id headers as the API. The tools call the API in process through the SDK, so every tool call keeps its normal admission, authorization, and RLS. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…ackage Document the Streamable HTTP endpoint beside the stdio adapter. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… package Bun and Wrangler resolved @corespeed/lore-sdk through the workspace link to its built dist, which the database and build CI jobs do not build. packages/mcp/tsconfig.json now maps the SDK to its source; the package build uses tsconfig.build.json against the built SDK. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
bun audit now flags undici < 7.30.1 (GHSA-xjj6-f33q-929c, via Wrangler and openai), zod < 4.6.6 (GHSA-mrhx-c7xc-m3w5, a direct dependency), and body-parser < 2.4.0 (GHSA-27r3-jxmh-p828, via @opennextjs/cloudflare). main fails the audit too. typecheck, next build, smoke:next, the OpenNext build, wrangler deploy --dry-run, packages:smoke, and the integration and package tests pass. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The SDK's stateless legacy fallback streams SSE, so the response returned before the tool call finished. On Workers the request then closed its database and the tool failed with internal_error. 2025-era requests now go to a stateless transport in JSON mode, which resolves only with every result. The tests close the request's database when the handler returns, as fetchCloudflareApi does; both MCP tests fail against the old handler. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The handler is stateless, so it has no session stream to open or end. The Lore route already answered 405; another host using the handler got an SSE stream for GET. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
There was a problem hiding this comment.
Approved after four review rounds. No findings remain.
The fixes resolve SDK imports from a clean checkout and keep legacy tool execution within the request lifetime. The standalone HTTP handler also rejects unsupported methods.
Verification:
- Reviewed the changes from merge base e8e1be9 through this head, including each fix.
- Targeted local checks pass for SDK resolution, legacy request completion, HTTP integration, and unsupported methods.
- All six required CI checks pass on 99c20bb: static, tests, database, packages, build, and the aggregate gate.
- CI evidence: https://github.com/corespeed-io/lore/actions/runs/40155356909
The PR description records the product decisions and transport limits.
Reviewer session: e96a2399-e3cb-4a42-a095-eae005bb0c6d.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What changes
The Lore server now serves the MCP tools over Streamable HTTP at
POST /api/v1/mcp. The stdiolore-mcpadapter still works.Authorization: Bearer lore_agent_…and the Workspace inx-lore-workspace-id. These are the same headers as the API.createLoreMcpHttpHandlerwith the app's ownfetch). Each tool call is admitted, authorized, and scoped by RLS like any other Agent request. The tool code does not change.Decisions for the PM
check-import-boundaries.tsnow lets the server-composition layer import the MCP package. MCP still reaches Lore only through the SDK.Other changes
packages/mcpimports its version module with.tsand setsrewriteRelativeImportExtensions, as the SDK package does. Turbopack could not resolve./generated/version.jsonce the server bundled the package.packages/mcp/tsconfig.jsonmaps@corespeed/lore-sdkto the SDK source. Bun and Wrangler bundle the MCP source from the server, and the CI jobs do not build the SDKdist. The published package builds withtsconfig.build.jsonagainst the built SDK.fix(deps):bun auditnow fails onmaintoo, with three new high advisories. This PR raisesundicito 7.30.1 (override),zodto 4.6.7, andbody-parserto 2.4.0 (override).docs/agent-conventions.md,docs/architecture.md,docs/developer-integration.md,packages/mcp/README.md.Verification
tests/integration/mcp-http.test.tsconnects a real MCP client over Streamable HTTP throughapp.request. It covers writes recorded as the Agent, RLS on another User's private Memory, no credential, an unknown token, a foreign Workspace, a revoked grant, and a human credential.architecture:check,next build,smoke:next, the OpenNext Cloudflare build,wrangler deploy --dry-run, andpackages:smokepass. The full suite passes excepttests/modules/code/code-index.test.ts, which also fails onmainin this sandbox because of a global Git ignore file. It passes withXDG_CONFIG_HOME=/nonexistent.🤖 Generated with Claude Code