From f70a65ea02a0aa2ac0b51fb496f7f863bd82e065 Mon Sep 17 00:00:00 2001 From: David Taylor Date: Fri, 2 Aug 2024 16:23:54 +0100 Subject: [PATCH] FIX: Do not strip `//` from the middle of URLs in discourse-url (#28210) Protocol/domain should only be stripped when they occur at the beginning of a URL --- .../javascripts/discourse/app/lib/url.js | 2 +- .../discourse/tests/unit/lib/url-test.js | 34 +++++++++++++++++++ 2 files changed, 35 insertions(+), 1 deletion(-) diff --git a/app/assets/javascripts/discourse/app/lib/url.js b/app/assets/javascripts/discourse/app/lib/url.js index e9e63596ebd..7a942426c0c 100644 --- a/app/assets/javascripts/discourse/app/lib/url.js +++ b/app/assets/javascripts/discourse/app/lib/url.js @@ -214,7 +214,7 @@ class DiscourseURL extends EmberObject { return this.redirectTo(path); } - const pathname = path.replace(/(https?\:)?\/\/[^\/]+/, ""); + const pathname = path.replace(/^(https?\:)?\/\/[^\/]+/, ""); if (!this.isInternal(path)) { return this.redirectTo(path); diff --git a/app/assets/javascripts/discourse/tests/unit/lib/url-test.js b/app/assets/javascripts/discourse/tests/unit/lib/url-test.js index f47c6de8712..8efc03846bf 100644 --- a/app/assets/javascripts/discourse/tests/unit/lib/url-test.js +++ b/app/assets/javascripts/discourse/tests/unit/lib/url-test.js @@ -114,6 +114,40 @@ module("Unit | Utility | url", function (hooks) { ); }); + test("routeTo protocol/domain stripping", async function (assert) { + sinon.stub(DiscourseURL, "origin").get(() => "http://example.com"); + sinon.stub(DiscourseURL, "handleURL"); + sinon.stub(DiscourseURL, "router").get(() => { + return { + currentURL: "/bar", + }; + }); + + DiscourseURL.routeTo("http://example.com/foo1"); + assert.ok( + DiscourseURL.handleURL.calledWith(`/foo1`), + "it strips the protocol and domain when http" + ); + + DiscourseURL.routeTo("https://example.com/foo2"); + assert.ok( + DiscourseURL.handleURL.calledWith(`/foo2`), + "it strips the protocol and domain when https" + ); + + DiscourseURL.routeTo("//example.com/foo3"); + assert.ok( + DiscourseURL.handleURL.calledWith(`/foo3`), + "it strips the protocol and domain when protocol-less" + ); + + DiscourseURL.routeTo("https://example.com//foo4"); + assert.ok( + DiscourseURL.handleURL.calledWith(`//foo4`), + "it does not strip double-slash in the middle of urls" + ); + }); + test("routeTo does not rewrite routes started with /my", async function (assert) { logIn(); sinon.stub(DiscourseURL, "router").get(() => {