From 89a684546b0cea8b4539a130cb49f6fb50a8bb76 Mon Sep 17 00:00:00 2001 From: Olivier Chafik Date: Thu, 15 Jan 2026 12:23:13 +0000 Subject: [PATCH] fix(examples): resolve DIST_DIR path for npm package execution (#277) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * fix(examples): resolve DIST_DIR path for npm package execution When servers are compiled to dist/server.js and published to npm, `import.meta.dirname` already points to dist/, so joining with "dist" results in dist/dist/ which doesn't exist. This fix detects whether we're running from TypeScript source or compiled JavaScript and adjusts the path accordingly: - From source (server.ts): use dist/ subdirectory - From compiled (dist/server.js): use current directory Fixes ENOENT errors like: "ENOENT: no such file or directory, open '.../dist/dist/mcp-app.html'" 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 * fix(pdf-server): mark pdfjs-dist as external in bundle The pdf.worker.mjs file wasn't being found when running from npm because bun bundled pdfjs-dist but didn't include the worker file. By marking pdfjs-dist as external, it uses the installed package from node_modules at runtime where the worker is available. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 --------- Co-authored-by: Claude Opus 4.5 --- examples/basic-server-preact/server.ts | 5 ++++- examples/basic-server-react/server.ts | 5 ++++- examples/basic-server-solid/server.ts | 5 ++++- examples/basic-server-svelte/server.ts | 5 ++++- examples/basic-server-vanillajs/server.ts | 5 ++++- examples/basic-server-vue/server.ts | 5 ++++- examples/budget-allocator-server/server.ts | 5 ++++- examples/cohort-heatmap-server/server.ts | 5 ++++- examples/customer-segmentation-server/server.ts | 5 ++++- examples/integration-server/server.ts | 5 ++++- examples/map-server/server.ts | 5 ++++- examples/pdf-server/package.json | 2 +- examples/pdf-server/server.ts | 5 ++++- examples/scenario-modeler-server/server.ts | 5 ++++- examples/shadertoy-server/server.ts | 5 ++++- examples/sheet-music-server/server.ts | 5 ++++- examples/system-monitor-server/server.ts | 5 ++++- examples/threejs-server/server.ts | 5 ++++- examples/transcript-server/server.ts | 5 ++++- examples/video-resource-server/server.ts | 5 ++++- examples/wiki-explorer-server/server.ts | 5 ++++- 21 files changed, 81 insertions(+), 21 deletions(-) diff --git a/examples/basic-server-preact/server.ts b/examples/basic-server-preact/server.ts index 9171159..2d99964 100644 --- a/examples/basic-server-preact/server.ts +++ b/examples/basic-server-preact/server.ts @@ -3,7 +3,10 @@ import type { CallToolResult, ReadResourceResult } from "@modelcontextprotocol/s import fs from "node:fs/promises"; import path from "node:path"; import { registerAppTool, registerAppResource, RESOURCE_MIME_TYPE } from "@modelcontextprotocol/ext-apps/server"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; /** * Creates a new MCP server instance with tools and resources registered. diff --git a/examples/basic-server-react/server.ts b/examples/basic-server-react/server.ts index 45b1dc9..416b217 100644 --- a/examples/basic-server-react/server.ts +++ b/examples/basic-server-react/server.ts @@ -4,7 +4,10 @@ import type { CallToolResult, ReadResourceResult } from "@modelcontextprotocol/s import fs from "node:fs/promises"; import path from "node:path"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; /** * Creates a new MCP server instance with tools and resources registered. diff --git a/examples/basic-server-solid/server.ts b/examples/basic-server-solid/server.ts index 6659ab7..33f76a1 100644 --- a/examples/basic-server-solid/server.ts +++ b/examples/basic-server-solid/server.ts @@ -3,7 +3,10 @@ import type { CallToolResult, ReadResourceResult } from "@modelcontextprotocol/s import fs from "node:fs/promises"; import path from "node:path"; import { registerAppTool, registerAppResource, RESOURCE_MIME_TYPE } from "@modelcontextprotocol/ext-apps/server"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; /** * Creates a new MCP server instance with tools and resources registered. diff --git a/examples/basic-server-svelte/server.ts b/examples/basic-server-svelte/server.ts index b90e70b..dd2dba6 100644 --- a/examples/basic-server-svelte/server.ts +++ b/examples/basic-server-svelte/server.ts @@ -3,7 +3,10 @@ import type { CallToolResult, ReadResourceResult } from "@modelcontextprotocol/s import fs from "node:fs/promises"; import path from "node:path"; import { registerAppTool, registerAppResource, RESOURCE_MIME_TYPE } from "@modelcontextprotocol/ext-apps/server"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; /** * Creates a new MCP server instance with tools and resources registered. diff --git a/examples/basic-server-vanillajs/server.ts b/examples/basic-server-vanillajs/server.ts index 167b056..07e82c2 100644 --- a/examples/basic-server-vanillajs/server.ts +++ b/examples/basic-server-vanillajs/server.ts @@ -4,7 +4,10 @@ import type { CallToolResult, ReadResourceResult } from "@modelcontextprotocol/s import fs from "node:fs/promises"; import path from "node:path"; import { z } from "zod"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; /** * Creates a new MCP server instance with tools and resources registered. diff --git a/examples/basic-server-vue/server.ts b/examples/basic-server-vue/server.ts index 4576263..73cb54d 100644 --- a/examples/basic-server-vue/server.ts +++ b/examples/basic-server-vue/server.ts @@ -3,7 +3,10 @@ import type { CallToolResult, ReadResourceResult } from "@modelcontextprotocol/s import fs from "node:fs/promises"; import path from "node:path"; import { registerAppTool, registerAppResource, RESOURCE_MIME_TYPE } from "@modelcontextprotocol/ext-apps/server"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; /** * Creates a new MCP server instance with tools and resources registered. diff --git a/examples/budget-allocator-server/server.ts b/examples/budget-allocator-server/server.ts index 90fcef9..e522918 100755 --- a/examples/budget-allocator-server/server.ts +++ b/examples/budget-allocator-server/server.ts @@ -17,7 +17,10 @@ import { registerAppResource, registerAppTool, } from "@modelcontextprotocol/ext-apps/server"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; // --------------------------------------------------------------------------- // Schemas - types are derived from these using z.infer diff --git a/examples/cohort-heatmap-server/server.ts b/examples/cohort-heatmap-server/server.ts index 6f0c975..6d07144 100644 --- a/examples/cohort-heatmap-server/server.ts +++ b/examples/cohort-heatmap-server/server.ts @@ -8,7 +8,10 @@ import { registerAppResource, registerAppTool, } from "@modelcontextprotocol/ext-apps/server"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; // Schemas - types are derived from these using z.infer const GetCohortDataInputSchema = z.object({ diff --git a/examples/customer-segmentation-server/server.ts b/examples/customer-segmentation-server/server.ts index 8bfa65c..244415d 100644 --- a/examples/customer-segmentation-server/server.ts +++ b/examples/customer-segmentation-server/server.ts @@ -17,7 +17,10 @@ import { } from "./src/data-generator.js"; import { SEGMENTS, type Customer, type SegmentSummary } from "./src/types.js"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; // Schemas - types are derived from these using z.infer const GetCustomerDataInputSchema = z.object({ diff --git a/examples/integration-server/server.ts b/examples/integration-server/server.ts index d86a9fd..a44c007 100644 --- a/examples/integration-server/server.ts +++ b/examples/integration-server/server.ts @@ -11,7 +11,10 @@ import type { import fs from "node:fs/promises"; import path from "node:path"; import { z } from "zod"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; const RESOURCE_URI = "ui://get-time/mcp-app.html"; /** diff --git a/examples/map-server/server.ts b/examples/map-server/server.ts index f860649..e6ff564 100644 --- a/examples/map-server/server.ts +++ b/examples/map-server/server.ts @@ -21,7 +21,10 @@ import { } from "@modelcontextprotocol/ext-apps/server"; import { randomUUID } from "crypto"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; const RESOURCE_URI = "ui://cesium-map/mcp-app.html"; // Nominatim API response type diff --git a/examples/pdf-server/package.json b/examples/pdf-server/package.json index bead423..cf9f6ee 100644 --- a/examples/pdf-server/package.json +++ b/examples/pdf-server/package.json @@ -14,7 +14,7 @@ "dist" ], "scripts": { - "build": "tsc --noEmit && cross-env INPUT=mcp-app.html vite build && tsc -p tsconfig.server.json && bun build server.ts --outdir dist --target node && bun build main.ts --outfile dist/index.js --target node --external \"./server.js\" --banner \"#!/usr/bin/env node\"", + "build": "tsc --noEmit && cross-env INPUT=mcp-app.html vite build && tsc -p tsconfig.server.json && bun build server.ts --outdir dist --target node --external pdfjs-dist && bun build main.ts --outfile dist/index.js --target node --external \"./server.js\" --external pdfjs-dist --banner \"#!/usr/bin/env node\"", "watch": "cross-env INPUT=mcp-app.html vite build --watch", "serve": "bun --watch main.ts", "start": "cross-env NODE_ENV=development npm run build && npm run serve", diff --git a/examples/pdf-server/server.ts b/examples/pdf-server/server.ts index f07921f..77e6f33 100644 --- a/examples/pdf-server/server.ts +++ b/examples/pdf-server/server.ts @@ -37,7 +37,10 @@ import { type PdfIndex, } from "./src/types.js"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; const RESOURCE_URI = "ui://pdf-viewer/mcp-app.html"; const DEFAULT_PDF = "https://arxiv.org/pdf/1706.03762"; // Attention Is All You Need diff --git a/examples/scenario-modeler-server/server.ts b/examples/scenario-modeler-server/server.ts index d3cbf0d..b59851c 100644 --- a/examples/scenario-modeler-server/server.ts +++ b/examples/scenario-modeler-server/server.ts @@ -11,7 +11,10 @@ import type { import fs from "node:fs/promises"; import path from "node:path"; import { z } from "zod"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; // ============================================================================ // Schemas - types are derived from these using z.infer diff --git a/examples/shadertoy-server/server.ts b/examples/shadertoy-server/server.ts index 0d9ec8b..1c96fea 100644 --- a/examples/shadertoy-server/server.ts +++ b/examples/shadertoy-server/server.ts @@ -11,7 +11,10 @@ import type { import fs from "node:fs/promises"; import path from "node:path"; import { z } from "zod"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; const TOOL_DESCRIPTION = `Renders a ShaderToy-compatible GLSL fragment shader in real-time using WebGL 2.0. diff --git a/examples/sheet-music-server/server.ts b/examples/sheet-music-server/server.ts index 4a1cb8c..cfd319b 100644 --- a/examples/sheet-music-server/server.ts +++ b/examples/sheet-music-server/server.ts @@ -12,7 +12,10 @@ import { registerAppResource, registerAppTool, } from "@modelcontextprotocol/ext-apps/server"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; const DEFAULT_ABC_NOTATION_INPUT = `X:1 T:Twinkle, Twinkle Little Star diff --git a/examples/system-monitor-server/server.ts b/examples/system-monitor-server/server.ts index 1a1b56f..61bfa91 100644 --- a/examples/system-monitor-server/server.ts +++ b/examples/system-monitor-server/server.ts @@ -53,7 +53,10 @@ const SystemStatsSchema = z.object({ type CpuCore = z.infer; type MemoryStats = z.infer; type SystemStats = z.infer; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; // Returns raw CPU timing data per core (client calculates usage from deltas) function getCpuSnapshots(): CpuCore[] { diff --git a/examples/threejs-server/server.ts b/examples/threejs-server/server.ts index eef7997..64063af 100644 --- a/examples/threejs-server/server.ts +++ b/examples/threejs-server/server.ts @@ -14,7 +14,10 @@ import fs from "node:fs/promises"; import path from "node:path"; import { z } from "zod"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; // Default code example for the Three.js widget const DEFAULT_THREEJS_CODE = `const scene = new THREE.Scene(); diff --git a/examples/transcript-server/server.ts b/examples/transcript-server/server.ts index 96afe09..035c8b6 100644 --- a/examples/transcript-server/server.ts +++ b/examples/transcript-server/server.ts @@ -11,7 +11,10 @@ import { RESOURCE_MIME_TYPE, RESOURCE_URI_META_KEY, } from "@modelcontextprotocol/ext-apps/server"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; const RESOURCE_URI = "ui://transcript/mcp-app.html"; /** diff --git a/examples/video-resource-server/server.ts b/examples/video-resource-server/server.ts index 71be1a0..2397665 100644 --- a/examples/video-resource-server/server.ts +++ b/examples/video-resource-server/server.ts @@ -20,7 +20,10 @@ import type { import fs from "node:fs/promises"; import path from "node:path"; import { z } from "zod"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; const RESOURCE_URI = "ui://video-player/mcp-app.html"; /** diff --git a/examples/wiki-explorer-server/server.ts b/examples/wiki-explorer-server/server.ts index faf1d66..fe2e89b 100644 --- a/examples/wiki-explorer-server/server.ts +++ b/examples/wiki-explorer-server/server.ts @@ -12,7 +12,10 @@ import * as cheerio from "cheerio"; import fs from "node:fs/promises"; import path from "node:path"; import { z } from "zod"; -const DIST_DIR = path.join(import.meta.dirname, "dist"); +// Works both from source (server.ts) and compiled (dist/server.js) +const DIST_DIR = import.meta.filename.endsWith(".ts") + ? path.join(import.meta.dirname, "dist") + : import.meta.dirname; type PageInfo = { url: string; title: string };