|
|
@@ -1972,6 +1972,83 @@ test("wellknown URL with trailing slash is normalized", async () => {
|
|
|
}
|
|
|
})
|
|
|
|
|
|
+test("wellknown remote_config supports templated env vars in headers", async () => {
|
|
|
+ const originalFetch = globalThis.fetch
|
|
|
+ const originalToken = process.env.TEST_TOKEN
|
|
|
+ let wellknownFetchedUrl: string | undefined
|
|
|
+ let remoteFetchedUrl: string | undefined
|
|
|
+ let remoteHeaders: HeadersInit | undefined
|
|
|
+ globalThis.fetch = mock((url: string | URL | Request, init?: RequestInit) => {
|
|
|
+ const urlStr = url instanceof Request ? url.url : url instanceof URL ? url.href : url
|
|
|
+ if (urlStr.includes(".well-known/opencode")) {
|
|
|
+ wellknownFetchedUrl = urlStr
|
|
|
+ return Promise.resolve(
|
|
|
+ new Response(
|
|
|
+ JSON.stringify({
|
|
|
+ remote_config: {
|
|
|
+ url: "https://config.example.com/opencode.json",
|
|
|
+ headers: {
|
|
|
+ Authorization: "Bearer {env:TEST_TOKEN}",
|
|
|
+ },
|
|
|
+ },
|
|
|
+ }),
|
|
|
+ { status: 200 },
|
|
|
+ ),
|
|
|
+ )
|
|
|
+ }
|
|
|
+ if (urlStr.includes("config.example.com")) {
|
|
|
+ remoteFetchedUrl = urlStr
|
|
|
+ remoteHeaders = init?.headers
|
|
|
+ return Promise.resolve(
|
|
|
+ new Response(
|
|
|
+ JSON.stringify({
|
|
|
+ mcp: { confluence: { type: "remote", url: "https://confluence.example.com/mcp", enabled: true } },
|
|
|
+ }),
|
|
|
+ { status: 200 },
|
|
|
+ ),
|
|
|
+ )
|
|
|
+ }
|
|
|
+ return originalFetch(url, init)
|
|
|
+ }) as unknown as typeof fetch
|
|
|
+
|
|
|
+ const fakeAuth = Layer.mock(Auth.Service)({
|
|
|
+ all: () =>
|
|
|
+ Effect.succeed({
|
|
|
+ "https://example.com": new Auth.WellKnown({ type: "wellknown", key: "TEST_TOKEN", token: "test-token" }),
|
|
|
+ }),
|
|
|
+ })
|
|
|
+
|
|
|
+ const layer = Config.layer.pipe(
|
|
|
+ Layer.provide(testFlock),
|
|
|
+ Layer.provide(AppFileSystem.defaultLayer),
|
|
|
+ Layer.provide(Env.defaultLayer),
|
|
|
+ Layer.provide(fakeAuth),
|
|
|
+ Layer.provide(emptyAccount),
|
|
|
+ Layer.provideMerge(infra),
|
|
|
+ Layer.provide(noopNpm),
|
|
|
+ )
|
|
|
+
|
|
|
+ try {
|
|
|
+ await provideTmpdirInstance(
|
|
|
+ () =>
|
|
|
+ Config.Service.use((svc) =>
|
|
|
+ Effect.gen(function* () {
|
|
|
+ const config = yield* svc.get()
|
|
|
+ expect(wellknownFetchedUrl).toBe("https://example.com/.well-known/opencode")
|
|
|
+ expect(remoteFetchedUrl).toBe("https://config.example.com/opencode.json")
|
|
|
+ expect(remoteHeaders).toEqual({ Authorization: "Bearer test-token" })
|
|
|
+ expect(config.mcp?.confluence?.enabled).toBe(true)
|
|
|
+ }),
|
|
|
+ ),
|
|
|
+ { git: true },
|
|
|
+ ).pipe(Effect.scoped, Effect.provide(layer), Effect.runPromise)
|
|
|
+ } finally {
|
|
|
+ globalThis.fetch = originalFetch
|
|
|
+ if (originalToken === undefined) delete process.env.TEST_TOKEN
|
|
|
+ else process.env.TEST_TOKEN = originalToken
|
|
|
+ }
|
|
|
+})
|
|
|
+
|
|
|
describe("resolvePluginSpec", () => {
|
|
|
test("keeps package specs unchanged", async () => {
|
|
|
await using tmp = await tmpdir()
|