From 70701f53901ad70edffd7d43c165e25016105470 Mon Sep 17 00:00:00 2001 From: Andrew <112019350+andrewkernel@users.noreply.github.com> Date: Tue, 30 Jun 2026 02:14:53 -0500 Subject: [PATCH] fix(req): ignore trailing dot in subdomains --- History.md | 3 ++- lib/request.js | 2 ++ test/req.subdomains.js | 13 +++++++++++++ 3 files changed, 17 insertions(+), 1 deletion(-) diff --git a/History.md b/History.md index 9e6ee903f40..88897f2afdd 100644 --- a/History.md +++ b/History.md @@ -4,9 +4,10 @@ - Fixed HTTP header conflict between Content-Length and Transfer-Encoding in res.send - by [@YuryShkoda](https://github.com/YuryShkoda) in [#4893](https://github.com/expressjs/express/pull/4893) - Fixed the behavior of `res.send()` to prevent conflicts between `Content-Length` and `Transfer-Encoding` HTTP headers in responses. The `Content-Length` header in `res.send()` is now only added when a `Transfer-Encoding` header is not present, complying with the HTTP specification that states both headers should not coexist in the same response +- Fixed `req.subdomains` handling for fully qualified domain names with a trailing dot, so the root label is ignored when applying the subdomain offset. + ## 🚀 Improvements * Improve HTML structure in `res.redirect()` responses when HTML format is accepted by adding ``, ``, and `<body>` tags for better browser compatibility - by [@Bernice55231](https://github.com/Bernice55231) in [#5167](https://github.com/expressjs/express/pull/5167) diff --git a/lib/request.js b/lib/request.js index 68243f52b6d..cb79fb8b31a 100644 --- a/lib/request.js +++ b/lib/request.js @@ -385,6 +385,8 @@ defineGetter(req, 'subdomains', function subdomains() { if (!hostname) return []; + hostname = hostname.replace(/\.$/, ''); + var offset = this.app.get('subdomain offset'); var subdomains = !isIP(hostname) ? hostname.split('.').reverse() diff --git a/test/req.subdomains.js b/test/req.subdomains.js index e5600f2eb56..b41cbbc256f 100644 --- a/test/req.subdomains.js +++ b/test/req.subdomains.js @@ -19,6 +19,19 @@ describe('req', function(){ .expect(200, ['ferrets', 'tobi'], done); }) + it('should ignore trailing dot on fully qualified domain names', function(done){ + var app = express(); + + app.use(function(req, res){ + res.send(req.subdomains); + }); + + request(app) + .get('/') + .set('Host', 'tobi.ferrets.example.com.') + .expect(200, ['ferrets', 'tobi'], done); + }) + it('should work with IPv4 address', function(done){ var app = express();