Skip to content

Commit

Permalink
feat(interceptor): add applyForwardedHeaders request interceptor
Browse files Browse the repository at this point in the history
  • Loading branch information
jollytoad committed Oct 8, 2024
1 parent da195df commit 51793b1
Show file tree
Hide file tree
Showing 4 changed files with 63 additions and 0 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,11 @@ and this project adheres to

This changelog will need to be split between individual packages

### Added

- [@http/interceptor] new RequestInterceptor `applyForwardedHeaders` to apply
`x-forwarded-*` to the Request URL

## [0.23.1]

### Fixed
Expand Down
22 changes: 22 additions & 0 deletions packages/interceptor/apply_forwarded_headers.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
import { assertEquals } from "@std/assert/equals";
import { applyForwardedHeaders } from "./apply_forwarded_headers.ts";

Deno.test("x-forwarded", () => {
const incomingBody = new ReadableStream();

const incomingReq = new Request("http://localhost:8000/yeah?this=that", {
method: "PUT",
headers: {
"X-Forwarded-Proto": "https",
"X-Forwarded-Host": "something.cool",
"X-Forwarded-Port": "443",
},
body: incomingBody,
});

const adjustedReq = applyForwardedHeaders(incomingReq);

assertEquals(adjustedReq.url, "https://something.cool/yeah?this=that");
assertEquals(adjustedReq.method, "PUT");
assertEquals(adjustedReq.body, incomingBody);
});
35 changes: 35 additions & 0 deletions packages/interceptor/apply_forwarded_headers.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
/**
* A RequestInterceptor that applies any `X-Forwarded-*` headers
* to the URL of the Request object.
*
* Useful where your server may be behind a proxy that forwards the
* request and set these headers.
*
* Deno Deploy conveniently supplies you with a Request object with
* the original URL, so this interceptor isn't required in Deploy.
*
* @example
* ```ts
* Deno.serve(intercept(handler, { request: applyForwardedHeaders }));
* ```
*
* TODO: check and parse the `Forwarded` header too.
*
* @param req The request
* @returns either the original Request or a new Request with the adjusted URL
*/
export function applyForwardedHeaders(req: Request): Request {
const proto = req.headers.get("x-forwarded-proto");
const host = req.headers.get("x-forwarded-host");
const port = req.headers.get("x-forwarded-port");

if (proto || host || port) {
const url = new URL(req.url);
url.protocol = proto ?? url.protocol;
url.host = host ?? url.host;
url.port = port ?? url.port;
return new Request(url, req);
}

return req;
}
1 change: 1 addition & 0 deletions packages/interceptor/deno.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
"name": "@http/interceptor",
"version": "0.23.0",
"exports": {
"./apply-forwarded-headers": "./apply_forwarded_headers.ts",
"./catch-response": "./catch_response.ts",
"./cors": "./cors.ts",
"./intercept": "./intercept.ts",
Expand Down

0 comments on commit 51793b1

Please sign in to comment.