| 81 | /** Upstream on 127.0.0.1 that authenticates for real: `GET /issues` is 200 for |
| 82 | * any bearer it has not been told to reject, and 401 for one it has. */ |
| 83 | const serveUpstream = () => |
| 84 | Effect.acquireRelease( |
| 85 | Effect.callback<UpstreamHandle>((resume) => { |
| 86 | const seen: string[] = []; |
| 87 | const revoked = new Set<string>(); |
| 88 | const server = createServer((request, response) => { |
| 89 | const bearer = (request.headers.authorization ?? "").replace(/^Bearer\s+/i, ""); |
| 90 | if (request.method === "GET" && (request.url ?? "").startsWith("/issues")) { |
| 91 | seen.push(bearer); |
| 92 | if (revoked.has(bearer)) { |
| 93 | response.writeHead(401, { "content-type": "application/json" }); |
| 94 | response.end(JSON.stringify({ error: "invalid_token" })); |
| 95 | return; |
| 96 | } |
| 97 | response.writeHead(200, { "content-type": "application/json" }); |
| 98 | response.end(JSON.stringify({ issues: [{ id: 1, title: "first" }] })); |
| 99 | return; |
| 100 | } |
| 101 | response.writeHead(404, { "content-type": "application/json" }); |
| 102 | response.end(JSON.stringify({ error: "not_found" })); |
| 103 | }); |
| 104 | server.listen(0, "127.0.0.1", () => { |
| 105 | const address = server.address(); |
| 106 | const port = typeof address === "object" && address ? address.port : 0; |
| 107 | resume( |
| 108 | Effect.succeed({ |
| 109 | url: `http://127.0.0.1:${port}`, |
| 110 | revokeSeenBearers: () => { |
| 111 | for (const bearer of seen) revoked.add(bearer); |
| 112 | }, |
| 113 | close: () => { |
| 114 | server.close(); |
| 115 | server.closeAllConnections(); |
| 116 | }, |
| 117 | }), |
| 118 | ); |
| 119 | }); |
| 120 | }), |
| 121 | (server) => Effect.sync(server.close), |
| 122 | ); |
| 123 | |
| 124 | const spec = ( |
| 125 | baseUrl: string, |