From e4a2bde33b5b840ede777c67722a0170c9a05bc0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Pascal=20Andr=C3=A9?= Date: Tue, 18 Aug 2026 21:12:49 +0200 Subject: [PATCH] fix(server): expose active V2 plugin metadata Allow the read-only OpenCode /api/plugin endpoint through the workspace proxy so the status panel can distinguish active plugins from configured but unloaded packages. Keep the route inside the explicit proxy allowlist and cover it with the instance proxy suite. The focused 25-test proxy suite, server typecheck, and diff check pass. --- .../server/src/server/__tests__/instance-proxy.test.ts | 7 +++++++ packages/server/src/server/http-server.ts | 2 +- 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/packages/server/src/server/__tests__/instance-proxy.test.ts b/packages/server/src/server/__tests__/instance-proxy.test.ts index 53c05b9d..87c9b52f 100644 --- a/packages/server/src/server/__tests__/instance-proxy.test.ts +++ b/packages/server/src/server/__tests__/instance-proxy.test.ts @@ -132,6 +132,13 @@ describe("instance proxy location enforcement", () => { assert.match(JSON.parse(response.body).url, /^\/api\/model\/default\?/) }) + it("allows active plugin metadata", async () => { + const { app } = await harness() + const response = await app.inject({ method: "GET", url: "/workspaces/workspace/instance/api/plugin" }) + assert.equal(response.statusCode, 200) + assert.match(JSON.parse(response.body).url, /^\/api\/plugin\?/) + }) + it("allows ownership-scoped agent fallback lookups", async () => { const { app } = await harness() const response = await app.inject({ method: "GET", url: "/workspaces/workspace/instance/api/agent/build" }) diff --git a/packages/server/src/server/http-server.ts b/packages/server/src/server/http-server.ts index 046981e3..e77294ff 100644 --- a/packages/server/src/server/http-server.ts +++ b/packages/server/src/server/http-server.ts @@ -895,7 +895,7 @@ function hasDotSegment(value: string): boolean { function isAllowedInstanceApiRoute(method: string, pathname: string): boolean { const route = pathname.replace(/\/+$/, "") const allowed: Array<[string, RegExp]> = [ - ["GET", /^\/api\/(?:agent|command|config|integration|mcp|model|provider)$/], + ["GET", /^\/api\/(?:agent|command|config|integration|mcp|model|plugin|provider)$/], ["GET", /^\/api\/agent\/[^/]+$/], ["GET", /^\/api\/model\/default$/], ["GET", /^\/api\/(?:permission|question)\/request$/],