diff --git a/CHANGELOG.md b/CHANGELOG.md index 051addbb2..d1dc4c74c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,12 @@ All notable changes to this project will be documented in this file. The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/), and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). +## Unreleased + +### Added + +- Added support for routing outgoing requests through a proxy per domain via the `PROXY_ROUTES` setting in the `FetchService` + ## 3.17.0 - 2026-06-26 ### Added diff --git a/apps/api/src/services/fetch/fetch.service.ts b/apps/api/src/services/fetch/fetch.service.ts index 9dc464d39..6006db04a 100644 --- a/apps/api/src/services/fetch/fetch.service.ts +++ b/apps/api/src/services/fetch/fetch.service.ts @@ -190,25 +190,29 @@ export class FetchService implements OnModuleInit { */ private applyProxyRoute(input: RequestInfo | URL): RequestInfo | URL { try { - const url = new URL( + const requestUrl = new URL( input instanceof Request ? input.url : input.toString() ); const route = this.proxyRoutes.find(({ domain }) => { - return this.matchesDomain(url.hostname, domain); + return this.hostnameMatchesDomain({ + domain, + hostname: requestUrl.hostname + }); }); if (!route) { return input; } - const target = new URL(route.url); - url.protocol = target.protocol; - url.host = target.host; + const proxyUrl = new URL(route.url); + requestUrl.protocol = proxyUrl.protocol; + requestUrl.hostname = proxyUrl.hostname; + requestUrl.port = proxyUrl.port; return input instanceof Request - ? new Request(url.toString(), input) - : url.toString(); + ? new Request(requestUrl.toString(), input) + : requestUrl.toString(); } catch { return input; } @@ -219,14 +223,20 @@ export class FetchService implements OnModuleInit { const { hostname } = new URL(url); return this.webFetchRoutes.find(({ domain }) => { - return this.matchesDomain(hostname, domain); + return this.hostnameMatchesDomain({ domain, hostname }); }); } catch { return undefined; } } - private matchesDomain(hostname: string, domain: string): boolean { + private hostnameMatchesDomain({ + domain, + hostname + }: { + domain: string; + hostname: string; + }): boolean { return hostname === domain || hostname.endsWith(`.${domain}`); } diff --git a/apps/api/src/services/fetch/interfaces/proxy-route.interface.ts b/apps/api/src/services/fetch/interfaces/proxy-route.interface.ts index 49c374916..7236ac8ee 100644 --- a/apps/api/src/services/fetch/interfaces/proxy-route.interface.ts +++ b/apps/api/src/services/fetch/interfaces/proxy-route.interface.ts @@ -9,8 +9,8 @@ * * [ * { - * "domain": "www.trackinsight.com", - * "url": "http://trackinsight-proxy:8191" + * "domain": "example.com", + * "url": "http://example-proxy:8191" * } * ] *