From db46159c84abd5246a3d12c47a0ddc4ee576a449 Mon Sep 17 00:00:00 2001 From: Andrew Khadder <54488379+khandrew1@users.noreply.github.com> Date: Tue, 4 Aug 2026 11:26:22 -0700 Subject: [PATCH] v2 docs fixes (#2139) * Set V2 as the default documentation version * Reorganize documentation navigation and redirects * Remove deprecated repository content * Rename Manufact deployment guide --- docs/docs.json | 75 ++--- .../MCP_SERVER_MIGRATION_CHECKLIST.md | 16 +- .../typescript/getting-started/quickstart.mdx | 2 +- .../typescript/getting-started}/templates.mdx | 2 +- .../mcp-apps/content-security-policy.mdx | 6 +- .../typescript/server/deployment/google.mdx | 306 ------------------ .../typescript/server/deployment/mcp-use.mdx | 13 +- .../server/deployment/self-hosted.mdx | 99 ++++++ .../typescript/server/deployment/supabase.mdx | 288 ----------------- 9 files changed, 132 insertions(+), 675 deletions(-) rename docs/{home => v2/typescript/getting-started}/templates.mdx (98%) delete mode 100644 docs/v2/typescript/server/deployment/google.mdx create mode 100644 docs/v2/typescript/server/deployment/self-hosted.mdx delete mode 100644 docs/v2/typescript/server/deployment/supabase.mdx diff --git a/docs/docs.json b/docs/docs.json index f890db51a..98ff19c89 100644 --- a/docs/docs.json +++ b/docs/docs.json @@ -32,35 +32,6 @@ }, "navigation": { "products": [ - { - "product": "Home", - "description": "Home", - "icon": "/images/mcp_use.svg", - "groups": [ - { - "group": "Welcome", - "pages": [ - "home/index", - "home/mcp101" - ] - }, - { - "group": "Templates", - "icon": "layout-template", - "pages": [ - "home/templates" - ] - }, - { - "group": "Libraries", - "icon": "library", - "pages": [ - "home/redirects/python", - "home/redirects/typescript" - ] - } - ] - }, { "product": "TypeScript SDK", "description": "TypeScript SDK documentation for V1 and V2", @@ -68,7 +39,6 @@ "versions": [ { "version": "V1", - "default": true, "tabs": [ { "tab": "Docs", @@ -318,6 +288,7 @@ }, { "version": "V2", + "default": true, "tabs": [ { "tab": "Docs", @@ -327,7 +298,8 @@ "group": "Get Started", "pages": [ "v2/typescript/getting-started/welcome", - "v2/typescript/getting-started/quickstart" + "v2/typescript/getting-started/quickstart", + "v2/typescript/getting-started/templates" ] }, { @@ -372,8 +344,7 @@ "icon": "rocket", "pages": [ "v2/typescript/server/deployment/mcp-use", - "v2/typescript/server/deployment/google", - "v2/typescript/server/deployment/supabase" + "v2/typescript/server/deployment/self-hosted" ] }, "v2/typescript/server/proxy", @@ -865,32 +836,26 @@ ] } ] - }, - { - "product": "Inspector", - "description": "Debug and test MCP Apps & Servers", - "icon": "/images/inspector-logo.svg", - "href": "/inspector/index", - "groups": [ - { - "group": "Inspector", - "pages": [ - "inspector/index", - "inspector/cli", - "inspector/connection-settings", - "inspector/url-parameters", - "inspector/keyboard-shortcuts", - "inspector/command-palette", - "inspector/integration", - "inspector/self-hosting", - "inspector/debugging-chatgpt-apps" - ] - } - ] } ] }, "redirects": [ + { + "source": "/", + "destination": "/v2/typescript/getting-started/welcome" + }, + { + "source": "/home", + "destination": "/v2/typescript/getting-started/welcome" + }, + { + "source": "/home/index", + "destination": "/v2/typescript/getting-started/welcome" + }, + { + "source": "/home/templates", + "destination": "/v2/typescript/getting-started/templates" + }, { "source": "/v2/typescript/agent/llm-integration", "destination": "/v2/typescript/agent/llm-providers" diff --git a/docs/v2/typescript/MCP_SERVER_MIGRATION_CHECKLIST.md b/docs/v2/typescript/MCP_SERVER_MIGRATION_CHECKLIST.md index a1d33643e..e77e62d42 100644 --- a/docs/v2/typescript/MCP_SERVER_MIGRATION_CHECKLIST.md +++ b/docs/v2/typescript/MCP_SERVER_MIGRATION_CHECKLIST.md @@ -44,13 +44,8 @@ API-reference pages are also outside this migration checklist. - [x] Supply `createTokenVerifier(resource)`, full `oauthMetadata`, and `mapAuthInfo(authInfo)`. - [x] Map native user fields with `id` and return `{ user, payload, permissions }`. - [x] Explain that the verifier receives the resolved MCP resource and that fixed-client proxying is external. -- [x] [Google Cloud deployment](/v2/typescript/server/deployment/google) - - [x] Rebuild setup around `create-mcp-use-app@latest --template mcp-server` and its generated scripts. - - [x] Convert the zoo server to root imports, `inputSchema`/`outputSchema`, raw results, and a default server export. - - [x] Replace the legacy widget section with `views//view.tsx`, tool `view`, and `structuredContent`. - - [x] Bind to `0.0.0.0`, use Cloud Run's injected `PORT`, and preserve IAM flags on redeploys. - - [x] Materialize Google ID-token values instead of showing unexpanded shell variables in JSON. - - [x] Remove unsafe cleanup commands, dated model/log examples, and unsupported production-readiness or cost claims. +- [x] [Self-hosted deployment](/v2/typescript/server/deployment/self-hosted) + - [x] Document a production Docker image, a local container run command, and the required public listener host. - [x] [Sampling](/v2/typescript/server/sampling) - [x] Replace the premise: native stateless v2 exposes no server-side `ctx.sample()` API. - [x] Remove all sampling overload, capability-gate, timeout, progress, response, and failure examples. @@ -83,13 +78,6 @@ API-reference pages are also outside this migration checklist. - [x] Replace the flag catalog with the implemented v2 deploy flags. - [x] Remove unsupported `--watch-paths` and `--deploy-branches` guidance. - [x] Separate deploy creation from build-log following and verify all hosted URL examples. -- [x] [Supabase deployment](/v2/typescript/server/deployment/supabase) - - [x] Use `npm:mcp-use`, raw tool results, and the server's Web `fetch` handler instead of `listen()`. - - [x] Rebuild deployment around `.mcp-use/build/index.js`, not the stale `dist` artifact layout. - - [x] Replace widget paths with `/_mcp-use/views/` and public assets with `/_mcp-use/public/`. - - [x] Clarify build-time and runtime `MCP_ASSETS_URL`, `MCP_URL`, and CSP responsibilities. - - [x] Remove or revalidate the old automated deployment script and fix the missing example link. - - [x] Resolve endpoint-path inconsistencies and remove obsolete widget metadata and Zod troubleshooting. ## Slight v2 migrations — complete diff --git a/docs/v2/typescript/getting-started/quickstart.mdx b/docs/v2/typescript/getting-started/quickstart.mdx index f2249fdb0..cb3f84666 100644 --- a/docs/v2/typescript/getting-started/quickstart.mdx +++ b/docs/v2/typescript/getting-started/quickstart.mdx @@ -204,7 +204,7 @@ npx mcp-use client local tools list ## Deploy the project -Deploy the generated project to Manufact Cloud: +Deploy the generated project to Manufact: ```bash npm diff --git a/docs/home/templates.mdx b/docs/v2/typescript/getting-started/templates.mdx similarity index 98% rename from docs/home/templates.mdx rename to docs/v2/typescript/getting-started/templates.mdx index 08f559e6b..70cdd34ff 100644 --- a/docs/home/templates.mdx +++ b/docs/v2/typescript/getting-started/templates.mdx @@ -7,7 +7,7 @@ icon: "layout-template" Every template ships with a live demo, a public repo, and a one-click deploy button. Clone, customize, and ship. -Looking to scaffold a new project from scratch instead? Run `npx create-mcp-use-app@latest` - see the [Quickstart](/typescript/getting-started/quickstart). +Looking to scaffold a new project from scratch instead? Run `npx create-mcp-use-app@latest` - see the [Quickstart](/v2/typescript/getting-started/quickstart). ## Featured Templates diff --git a/docs/v2/typescript/mcp-apps/content-security-policy.mdx b/docs/v2/typescript/mcp-apps/content-security-policy.mdx index bb7b8f22f..ed5c811c1 100644 --- a/docs/v2/typescript/mcp-apps/content-security-policy.mdx +++ b/docs/v2/typescript/mcp-apps/content-security-policy.mdx @@ -76,7 +76,7 @@ CSP_FRAME_DOMAINS=https://embed.example.com CSP_BASE_URI_DOMAINS=https://myserver.com ``` -## Static deployments (Supabase / CDN) +## Static deployments When assets live on static storage and the MCP server runs elsewhere: @@ -86,8 +86,6 @@ MCP_ASSETS_URL=https://PROJECT.supabase.co/storage/v1/object/public/widgets CSP_URLS=https://PROJECT.supabase.co ``` -See [Supabase deployment](/v2/typescript/server/deployment/supabase) for the full workflow. - ## Verify CSP The mcp-use Inspector provides a **CSP Mode Toggle** for testing: @@ -103,4 +101,4 @@ The mcp-use Inspector provides a **CSP Mode Toggle** for testing: ## Next Steps - [MCP Apps](/v2/typescript/mcp-apps): View overview and routing -- [Supabase Deployment](/v2/typescript/server/deployment/supabase): Static deployment with CSP +- [Self hosted](/v2/typescript/server/deployment/self-hosted): Run an MCP server in Docker diff --git a/docs/v2/typescript/server/deployment/google.mdx b/docs/v2/typescript/server/deployment/google.mdx deleted file mode 100644 index 9c58ca74e..000000000 --- a/docs/v2/typescript/server/deployment/google.mdx +++ /dev/null @@ -1,306 +0,0 @@ ---- -title: "Google Cloud Run" -description: "Deploy an MCP server to Google Cloud Run" -icon: "google" ---- - -Cloud Run can run a `mcp-use` server as a long-lived Node process. The -generated CLI scripts build the default-exported server and own the HTTP -listener. - -Cloud Run requires the process to listen on `0.0.0.0` and injects the port in -`PORT`. The configuration below satisfies both parts of that container -contract. - -## Create the project - -Create the server from the beta template: - -```bash -npx create-mcp-use-app@latest zoo-cloud-run \ - --template mcp-server \ - --npm \ - --install \ - --no-skills -cd zoo-cloud-run -``` - -The generated `package.json` includes these scripts: - -```json -{ - "scripts": { - "build": "mcp-use build", - "dev": "mcp-use dev", - "start": "mcp-use start", - "deploy": "mcp-use deploy", - "typecheck": "mcp-use typecheck" - } -} -``` - -Replace `index.ts` with this small zoo server: - -```typescript -import { MCPServer } from "mcp-use"; -import { z } from "zod"; - -const animalSchema = z.object({ - name: z.string(), - species: z.string(), - age: z.number().int().nonnegative(), - enclosure: z.string(), -}); - -type Animal = z.infer; - -const animals: Animal[] = [ - { name: "Leo", species: "lion", age: 7, enclosure: "Big Cat Plains" }, - { name: "Nala", species: "lion", age: 6, enclosure: "Big Cat Plains" }, - { name: "Chilly", species: "penguin", age: 3, enclosure: "Arctic Exhibit" }, -]; - -const server = new MCPServer({ - name: "zoo-cloud-run", - version: "1.0.0", - description: "Look up animals at a fictional zoo", - host: "0.0.0.0", -}); - -server.tool( - { - name: "get-animals-by-species", - description: "Return all zoo animals of one species", - inputSchema: z.object({ species: z.string() }), - outputSchema: z.object({ animals: z.array(animalSchema) }), - }, - async ({ species }) => { - const matches = animals.filter( - (animal) => animal.species.toLowerCase() === species.toLowerCase(), - ); - const result = { animals: matches }; - return { - content: [{ type: "text", text: JSON.stringify(result) }], - structuredContent: result, - }; - }, -); - -server.tool( - { - name: "get-animal-details", - description: "Return one animal by name", - inputSchema: z.object({ name: z.string() }), - outputSchema: z.object({ animal: animalSchema.nullable() }), - view: { name: "animal-card" }, - }, - async ({ name }) => { - const animal = - animals.find( - (candidate) => candidate.name.toLowerCase() === name.toLowerCase(), - ) ?? null; - const result = { animal }; - return { - content: [ - { - type: "text", - text: - animal === null - ? `No animal named ${name}` - : JSON.stringify(animal), - }, - ], - structuredContent: result, - }; - }, -); - -export default server; -``` - -There is no top-level `listen()` call. `npm run dev` and `npm start` import the -default export and own the listener. At runtime, `mcp-use start` reads Cloud -Run's `PORT` before falling back to the server configuration. - -## Optional: add a View - -The `mcp-server` template intentionally has no React UI. Install the View -dependencies: - -```bash -npm install react react-dom -npm install --save-dev @types/react @types/react-dom -``` - -Create `views/animal-card/view.tsx`: - -```tsx -import { useToolContext } from "mcp-use/react"; - -export default function AnimalCard() { - const view = useToolContext<"get-animal-details">(); - - if (view.status === "pending") return

Loading animal…

; - if (view.status === "error") return

{view.error.message}

; - if (view.toolOutput.animal === null) return

Animal not found.

; - - const animal = view.toolOutput.animal; - return ( -
-

{animal.name}

-

- {animal.species}, age {animal.age} -

-

Enclosure: {animal.enclosure}

-
- ); -} -``` - -The tool's `view.name` matches the directory under `views/`. A view-bound tool -must declare `outputSchema` and return matching `structuredContent`; the View -reads that typed result through `useToolContext`. - -Validate the project locally: - -```bash -npm run typecheck -npm run build -PORT=8080 npm start -``` - -The local endpoint is `http://localhost:8080/mcp`. - -## Add a Dockerfile - -Create `Dockerfile`: - -```dockerfile -FROM node:22-slim - -WORKDIR /app -COPY package*.json ./ -RUN npm ci -COPY . . -RUN npm run typecheck && npm run build - -ENV NODE_ENV=production -CMD ["npm", "start"] -``` - -Create `.dockerignore`: - -```text -node_modules -.git -.env -.env.* -.mcp-use -``` - -`npm start` serves `.mcp-use/build/`, binds to the server's `0.0.0.0` -configuration, and uses the injected `PORT`. - -## Configure Google Cloud - -Select a project and enable the source-deployment services: - -```bash -gcloud config set project YOUR_PROJECT_ID -gcloud services enable \ - run.googleapis.com \ - artifactregistry.googleapis.com \ - cloudbuild.googleapis.com -``` - -Create a dedicated runtime service account: - -```bash -gcloud iam service-accounts create zoo-mcp-runtime \ - --display-name="Zoo MCP Cloud Run runtime" -``` - -Set the values used by every deploy: - -```bash -PROJECT_ID="$(gcloud config get-value project)" -REGION="us-central1" -RUNTIME_SA="zoo-mcp-runtime@${PROJECT_ID}.iam.gserviceaccount.com" -``` - -## Deploy a private service - -Deploy from source and require an authenticated Cloud Run invoker: - -```bash -gcloud run deploy zoo-mcp-server \ - --source=. \ - --region="${REGION}" \ - --service-account="${RUNTIME_SA}" \ - --no-allow-unauthenticated -``` - -For later revisions, run the same command with the same `--region`, -`--service-account`, and `--no-allow-unauthenticated` flags. Keeping the -security-sensitive flags in the repeatable deploy command makes the intended -IAM posture explicit. - -Grant your current Google identity permission to invoke the service: - -```bash -ACCOUNT="$(gcloud config get-value account)" -gcloud run services add-iam-policy-binding zoo-mcp-server \ - --region="${REGION}" \ - --member="user:${ACCOUNT}" \ - --role="roles/run.invoker" -``` - -## Connect with a materialized ID token - -Cloud Run ID tokens expire. Generate the settings file immediately before -starting the client rather than putting shell variable names inside JSON: - -```bash -SERVICE_URL="$( - gcloud run services describe zoo-mcp-server \ - --region="${REGION}" \ - --format="value(status.url)" -)" -ID_TOKEN="$(gcloud auth print-identity-token)" -mkdir -p "${HOME}/.gemini" -jq -n \ - --arg url "${SERVICE_URL}/mcp" \ - --arg token "${ID_TOKEN}" \ - '{ - mcpServers: { - "zoo-cloud-run": { - httpUrl: $url, - headers: { Authorization: ("Bearer " + $token) } - } - } - }' > "${HOME}/.gemini/settings.json" -``` - -`jq` writes the actual URL and token values. If the client later receives -`401 Unauthorized`, generate a fresh token and regenerate the file. - -## Verify - -Read recent service logs without relying on a fixed log format: - -```bash -gcloud run services logs read zoo-mcp-server \ - --region="${REGION}" \ - --limit=20 -``` - -For lifecycle or resource removal, use the Cloud Run and Google Cloud project -controls appropriate to your account. This guide intentionally does not run -broad cleanup commands. - -## Platform references - -- [Deploy Cloud Run services from source](https://cloud.google.com/run/docs/deploying-source-code) -- [Cloud Run container runtime contract](https://cloud.google.com/run/docs/container-contract) -- [Authenticate developers to private services](https://cloud.google.com/run/docs/authenticating/developers) -- [Bind a View to a tool](/v2/typescript/server/tools#bind-a-view) diff --git a/docs/v2/typescript/server/deployment/mcp-use.mdx b/docs/v2/typescript/server/deployment/mcp-use.mdx index 6784bc751..e0379cab5 100644 --- a/docs/v2/typescript/server/deployment/mcp-use.mdx +++ b/docs/v2/typescript/server/deployment/mcp-use.mdx @@ -1,12 +1,13 @@ --- -title: "Deploy to Manufact Cloud" -description: "Deploy an MCP server from GitHub to Manufact Cloud" +title: "Deploy to Manufact" +description: "Deploy an MCP server from GitHub with Manufact" icon: "/images/logo-mcp-use.svg" --- -Manufact Cloud deploys a GitHub-backed `mcp-use` server and provides its -hosted MCP URL, deployments, logs, environment variables, and client -connection settings. +Manufact deploys a GitHub-backed `mcp-use` server and provides its hosted MCP +URL, deployments, logs, environment variables, and client connection settings. +See the [Manufact dashboard documentation](https://docs.manufact.com/dashboard) +for service setup and dashboard workflows. ## Prerequisites @@ -185,7 +186,7 @@ npx mcp-use client production tools list Use that same exact URL in any other MCP client configuration. -## More cloud operations +## More Manufact operations - [Creating servers](https://docs.manufact.com/dashboard/servers) - [Deployments](https://docs.manufact.com/dashboard/deployments) diff --git a/docs/v2/typescript/server/deployment/self-hosted.mdx b/docs/v2/typescript/server/deployment/self-hosted.mdx new file mode 100644 index 000000000..03af05861 --- /dev/null +++ b/docs/v2/typescript/server/deployment/self-hosted.mdx @@ -0,0 +1,99 @@ +--- +title: "Self hosted" +description: "Run an MCP server in your own Docker environment" +icon: "docker" +--- + +Run a built `mcp-use` server in Docker when you want to operate the server on +your own infrastructure. Your platform is responsible for TLS, a public domain, +authentication, and routing requests to the container. + +## Prerequisites + +- Docker installed locally, or a container platform that can build and run a + Docker image. +- An `mcp-use` server that exports its `MCPServer` instance as the default + export. +- An npm lockfile (`package-lock.json`). + +The generated `mcp-server` template already has the required `build` and +`start` scripts. `mcp-use start` serves the production build at +`.mcp-use/build/`. + +## Create a Dockerfile + +Add this `Dockerfile` at the project root: + +```dockerfile +FROM node:22-slim AS build + +WORKDIR /app +COPY package.json package-lock.json ./ +RUN npm ci +COPY . . +RUN npm run typecheck && npm run build + +FROM node:22-slim + +WORKDIR /app +ENV NODE_ENV=production +ENV HOST=0.0.0.0 +ENV PORT=3000 + +COPY package.json package-lock.json ./ +RUN npm ci --omit=dev +COPY --from=build /app/.mcp-use ./.mcp-use + +EXPOSE 3000 +CMD ["npm", "start"] +``` + +`HOST=0.0.0.0` lets the container receive traffic through Docker's network. +`PORT` can be changed to the port required by your container platform. + +Add a `.dockerignore` so the build context excludes local and secret files: + +```text +node_modules +.git +.env +.env.* +.mcp-use +``` + +## Build and run locally + +Build the image and publish the container port locally: + +```bash +docker build --tag my-mcp-server . +docker run --rm --publish 3000:3000 --env-file .env my-mcp-server +``` + +The MCP endpoint is available at: + +```text +http://localhost:3000/mcp +``` + +Verify it with the bundled client: + +```bash +npx mcp-use client connect local http://localhost:3000/mcp +npx mcp-use client local tools list +``` + +## Deploy the image + +Push the image to your container registry, then configure your container +platform to run it. Set its public URL in `MCP_URL` and supply application +secrets through the platform's secret manager rather than baking them into the +image. + +```env +MCP_URL=https://mcp.example.com +``` + +Configure the platform's health check and reverse proxy to forward requests to +the same `/mcp` path. Terminate TLS at your platform or reverse proxy and use +the resulting HTTPS URL in every MCP client. diff --git a/docs/v2/typescript/server/deployment/supabase.mdx b/docs/v2/typescript/server/deployment/supabase.mdx deleted file mode 100644 index dc1f80070..000000000 --- a/docs/v2/typescript/server/deployment/supabase.mdx +++ /dev/null @@ -1,288 +0,0 @@ ---- -title: "Supabase" -description: "Deploy an MCP server on Supabase Edge Functions" -icon: "/images/icons/supabase.svg" ---- - -Supabase Edge Functions run on a Deno-compatible runtime. `MCPServer` exposes -the Web-standard `fetch(Request)` boundary needed by that runtime; an Edge -Function forwards requests to `server.fetch` and does not call `listen()`. - -This guide deploys the CLI build output at `.mcp-use/build/index.js`. - -## Prerequisites - -- A TypeScript MCP server built with `mcp-use`. -- The Supabase CLI, authenticated with `supabase login`. -- A Supabase project reference. -- Node.js 22.22.2 or later to run the `mcp-use` build. -- Docker only when you choose local Supabase bundling or local function - serving. Supabase can also bundle through its API. - -Initialize and link Supabase from the server project: - -```bash -supabase init -supabase login -supabase link --project-ref YOUR_PROJECT_REF -supabase functions new mcp-server -``` - -## Author the server - -The public Edge Function URL contains the gateway prefix -`/functions/v1/mcp-server`. Give the MCP server a matching full base path so -the request path seen by `server.fetch` and the client endpoint agree: - -```typescript -// index.ts -import { MCPServer } from "mcp-use"; -import { z } from "zod"; - -const server = new MCPServer({ - name: "supabase-edge-mcp", - version: "1.0.0", - basePath: "/functions/v1/mcp-server/mcp", -}); - -server.tool( - { - name: "get-city", - description: "Return the configured demo city", - outputSchema: z.object({ city: z.string() }), - }, - async () => { - const result = { city: "San Francisco" }; - return { - content: [{ type: "text", text: result.city }], - structuredContent: result, - }; - }, -); - -export default server; -``` - -The callback returns the raw MCP result envelope. The exported server is -mounted through `server.fetch` later in this guide. - - - If your gateway or custom domain rewrites the function prefix before the - request reaches the Edge Function, change `basePath` to the pathname the - handler actually receives and use that same pathname in the client URL. - - -## Build for the Edge Function - -The build creates: - -```text -.mcp-use/build/ -├── index.js -├── manifest.json -└── views/ - ├── /... - └── public/... -``` - -If the server has no Views, build normally: - -```bash -npm run typecheck -npm run build -``` - -If it has Views, create a public Supabase Storage bucket such as `widgets`. -Set its public URL prefix while building so the generated View manifest points -at Storage: - -```bash -PROJECT_REF="YOUR_PROJECT_REF" -ASSETS_URL="https://${PROJECT_REF}.supabase.co/storage/v1/object/public/widgets" -MCP_ASSETS_URL="${ASSETS_URL}" npm run build -``` - -Copy the generated server build into the Edge Function: - -```bash -mkdir -p supabase/functions/mcp-server/.mcp-use -cp -R .mcp-use/build supabase/functions/mcp-server/.mcp-use/ -``` - -The deployed import target is -`supabase/functions/mcp-server/.mcp-use/build/index.js`, not a `dist` -artifact. - -## Map npm imports in Deno - -The built entry keeps its package imports external. Replace -`supabase/functions/mcp-server/deno.json` with: - -```json -{ - "imports": { - "mcp-use": "npm:mcp-use@latest", - "mcp-use/": "npm:mcp-use@latest/", - "zod": "npm:zod@^4.4.3" - } -} -``` - -The import map makes Deno resolve the built server's `mcp-use` imports through -the `npm:mcp-use@latest` package entry point. - -Pin the `npm:mcp-use` version to the same version used by the project when -reproducible builds are required. - -## Forward requests to `server.fetch` - -Replace `supabase/functions/mcp-server/index.ts`: - -```typescript -import server from "./.mcp-use/build/index.js"; - -Deno.serve((request) => server.fetch(request)); -``` - -`server.fetch` returns a Web `Response`, so no Node listener, adapter, or port -is involved. - -## Upload View and public assets - -With the default MCP path above, Storage must preserve the URL hierarchy -embedded by `mcp-use build`: - -```text -widgets/ -└── functions/v1/mcp-server/mcp/ - └── _mcp-use/ - ├── views//... - └── public/... -``` - -For a View named `animal-card`, upload its built files and the public assets: - -```bash -supabase storage cp -r \ - .mcp-use/build/views/animal-card/ \ - "ss:///widgets/functions/v1/mcp-server/mcp/_mcp-use/views/animal-card/" \ - --experimental - -supabase storage cp -r \ - .mcp-use/build/views/public/ \ - "ss:///widgets/functions/v1/mcp-server/mcp/_mcp-use/public/" \ - --experimental -``` - -Repeat the first command for each View directory. You can use the Supabase -Dashboard or another supported Storage client instead; the required part is -the object layout: - -- View bundles load from `/_mcp-use/views//...`. -- Files from the project's `public/` directory load from - `/_mcp-use/public/...`. - -Keep these generated paths intact rather than flattening View and public -assets into generic bucket directories. - -## Build-time, runtime, and CSP values - -The three concerns are distinct: - -| Value | When | Responsibility | -| ------------------------------- | ----------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | -| `MCP_ASSETS_URL` | Build and runtime | CDN/Storage prefix. At build time it rewrites View manifest URLs; at runtime it supplies the public asset base and its origin is added to `resourceDomains`. Use the same value in both places. | -| `MCP_URL` | Runtime | Public server origin only, such as `https://PROJECT.supabase.co`. It is used for server-origin resolution and added to View `connectDomains`. The endpoint path comes from `basePath`. | -| View `csp` or `CSP_*` variables | Authoring/runtime | Allow additional APIs, images, frames, or base URIs used by the View. The server and asset origins do not authorize unrelated external domains. | - -Set the runtime values: - -```bash -supabase secrets set \ - MCP_URL="https://YOUR_PROJECT_REF.supabase.co" \ - MCP_ASSETS_URL="https://YOUR_PROJECT_REF.supabase.co/storage/v1/object/public/widgets" \ - --project-ref YOUR_PROJECT_REF -``` - -Use `CSP_URLS` only when intentionally granting the same extra origins to all -four CSP categories. Prefer the tool's `view.csp` or a category-specific -variable such as `CSP_CONNECT_DOMAINS` for narrower access. - -## Choose gateway authentication - -Supabase gateway authentication and MCP authentication are separate layers. -For a public demo, disable Supabase's gateway JWT check explicitly: - -```toml -[functions.mcp-server] -verify_jwt = false -``` - -For a protected function, keep the gateway check enabled and configure the -MCP client to send the required Supabase authorization headers. Do not put a -service-role key in a browser or public MCP client. - -## Test and deploy - -Check the Deno entry before deployment: - -```bash -deno check supabase/functions/mcp-server/index.ts -``` - -Serve locally when Docker is available: - -```bash -supabase functions serve mcp-server -``` - -The local MCP endpoint is: - -```text -http://127.0.0.1:54321/functions/v1/mcp-server/mcp -``` - -Deploy with the Supabase CLI: - -```bash -supabase functions deploy mcp-server -``` - -Use `--use-docker` to force local bundling, or `--use-api` to force -server-side bundling. Docker is not unconditionally required for deployment. - -The hosted endpoint is: - -```text -https://YOUR_PROJECT_REF.supabase.co/functions/v1/mcp-server/mcp -``` - -Connect the included MCP client to the same path: - -```bash -MCP_ENDPOINT="https://YOUR_PROJECT_REF.supabase.co/functions/v1/mcp-server/mcp" -npx mcp-use client connect supabase-edge "${MCP_ENDPOINT}" --no-oauth -npx mcp-use client supabase-edge tools list -``` - -When gateway JWT verification is enabled, pass its authorization header to -`client connect` with `-H "Authorization: Bearer TOKEN"`. - -## Troubleshooting - -- **Function 404:** verify the project reference, function name, and that - `basePath` matches the full request pathname received by the Edge Function. -- **MCP route 404:** make sure the client includes the final `/mcp`. -- **View asset 404:** compare the Storage object hierarchy with - `/_mcp-use/views/` and `/_mcp-use/public/`. -- **View CSP violation:** add only the missing external origin to `view.csp` - or the corresponding `CSP_*` runtime variable, then redeploy. -- **Bundle too large:** inspect it with `deno info` and try local bundling with - `supabase functions deploy mcp-server --use-docker`. - -## Platform references - -- [Supabase Edge Functions quickstart](https://supabase.com/docs/guides/functions/quickstart) -- [Supabase function configuration](https://supabase.com/docs/guides/local-development/cli/config) -- [Supabase Storage public URLs](https://supabase.com/docs/guides/storage/serving/downloads) -- [MCP Apps Content Security Policy](/v2/typescript/mcp-apps/content-security-policy)