From e12129f21a2cc62e6386918dd20cc2c98632c45c Mon Sep 17 00:00:00 2001 From: Iams4kura <126048986+Iams4kura@users.noreply.github.com> Date: Sat, 8 Aug 2026 00:29:46 +0800 Subject: [PATCH 1/2] fix(mcp): report the bound HTTP port --- .changeset/report-bound-http-port.md | 5 +++++ packages/mcp/src/index.ts | 4 +++- packages/mcp/test/integration.test.ts | 24 ++++++++++++++++++------ 3 files changed, 26 insertions(+), 7 deletions(-) create mode 100644 .changeset/report-bound-http-port.md diff --git a/.changeset/report-bound-http-port.md b/.changeset/report-bound-http-port.md new file mode 100644 index 000000000..75b45f8a5 --- /dev/null +++ b/.changeset/report-bound-http-port.md @@ -0,0 +1,5 @@ +--- +"@upstash/context7-mcp": patch +--- + +Report the actual assigned HTTP port when `--port 0` requests an ephemeral port. diff --git a/packages/mcp/src/index.ts b/packages/mcp/src/index.ts index b63ff3657..eca1fb6cc 100644 --- a/packages/mcp/src/index.ts +++ b/packages/mcp/src/index.ts @@ -539,8 +539,10 @@ async function main() { }); httpServer.once("listening", () => { + const address = httpServer.address(); + const boundPort = typeof address === "object" && address ? address.port : port; console.error( - `Context7 Documentation MCP Server v${SERVER_VERSION} running on HTTP at http://localhost:${port}/mcp` + `Context7 Documentation MCP Server v${SERVER_VERSION} running on HTTP at http://localhost:${boundPort}/mcp` ); }); }; diff --git a/packages/mcp/test/integration.test.ts b/packages/mcp/test/integration.test.ts index 0c9d68401..9550cd0ca 100644 --- a/packages/mcp/test/integration.test.ts +++ b/packages/mcp/test/integration.test.ts @@ -71,13 +71,12 @@ function startStubApi(): Promise { }); } -function startHttpChild(): Promise<{ child: ChildProcess; url: string }> { +function startHttpChild(port = BASE_PORT): Promise<{ child: ChildProcess; url: string }> { return new Promise((resolve, reject) => { - const child = spawn( - process.execPath, - [DIST, "--transport", "http", "--port", String(BASE_PORT)], - { env: childEnv, stdio: ["ignore", "ignore", "pipe"] } - ); + const child = spawn(process.execPath, [DIST, "--transport", "http", "--port", String(port)], { + env: childEnv, + stdio: ["ignore", "ignore", "pipe"], + }); let stderr = ""; child.stderr!.on("data", (chunk: Buffer) => { stderr += chunk.toString(); @@ -105,6 +104,19 @@ afterAll(() => { stubServer?.close(); }); +test("reports the bound port when port zero requests an ephemeral port", async () => { + const { child, url } = await startHttpChild(0); + try { + expect(new URL(url).port).not.toBe("0"); + + const response = await fetch(new URL("/ping", url)); + expect(response.ok).toBe(true); + await expect(response.json()).resolves.toMatchObject({ status: "ok" }); + } finally { + child.kill(); + } +}); + async function connect(transportKind: "http" | "stdio", era: "modern" | "legacy") { const client = new Client( { name: "test-harness", version: "1.0.0" }, From 93f71abbf03350dde41b9d0459429ca3873a39fa Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fahreddin=20=C3=96zcan?= Date: Tue, 18 Aug 2026 11:49:53 +0300 Subject: [PATCH 2/2] fix(mcp): enforce bound HTTP address --- packages/mcp/src/index.ts | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/packages/mcp/src/index.ts b/packages/mcp/src/index.ts index eca1fb6cc..08bbefc1f 100644 --- a/packages/mcp/src/index.ts +++ b/packages/mcp/src/index.ts @@ -540,9 +540,12 @@ async function main() { httpServer.once("listening", () => { const address = httpServer.address(); - const boundPort = typeof address === "object" && address ? address.port : port; + if (!address || typeof address === "string") { + console.error("Failed to determine the bound HTTP port"); + process.exit(1); + } console.error( - `Context7 Documentation MCP Server v${SERVER_VERSION} running on HTTP at http://localhost:${boundPort}/mcp` + `Context7 Documentation MCP Server v${SERVER_VERSION} running on HTTP at http://localhost:${address.port}/mcp` ); }); };