From b4370c09c6b270459dbd25e98fc9f78b13777860 Mon Sep 17 00:00:00 2001 From: Nikolai Emil Damm Date: Thu, 18 Dec 2025 15:55:39 +0100 Subject: [PATCH] feat: add normalizeConfluenceWebUIPath function and tests for URL rewriting Signed-off-by: Nikolai Emil Damm --- page/link.go | 26 +++++++++++++++++++++++++- page/link_test.go | 18 ++++++++++++++++++ 2 files changed, 43 insertions(+), 1 deletion(-) diff --git a/page/link.go b/page/link.go index 4167faf..347b4a2 100644 --- a/page/link.go +++ b/page/link.go @@ -221,6 +221,30 @@ func getConfluenceLink( } // Confluence supports relative links to reference other pages: // https://confluence.atlassian.com/doc/links-776656293.html - linkPath := linkUrl.Path + linkPath := normalizeConfluenceWebUIPath(linkUrl.Path) return linkPath, nil } + +// normalizeConfluenceWebUIPath rewrites Confluence Cloud "experience" URLs +// ("/ex/confluence//wiki/..."), to canonical wiki paths ("/wiki/..."). +// +// This function is intentionally conservative and only touches the exact +// experience prefix, so that local relative paths like "./img/foo.png" are not +// impacted. +func normalizeConfluenceWebUIPath(path string) string { + if path == "" { + return path + } + + // Example: + // /ex/confluence/05594958-6d5d-4e00-9017-90926d8b82d5/wiki/spaces/DVT/pages/5645697027/DX + // -> + // /wiki/spaces/DVT/pages/5645697027/DX + re := regexp.MustCompile(`^/ex/confluence/[^/]+(/wiki/.*)$`) + match := re.FindStringSubmatch(path) + if len(match) == 2 { + return match[1] + } + + return path +} diff --git a/page/link_test.go b/page/link_test.go index 3f94ddf..3196718 100644 --- a/page/link_test.go +++ b/page/link_test.go @@ -51,3 +51,21 @@ func TestParseLinks(t *testing.T) { assert.Equal(t, "example.md", links[7].full) assert.Equal(t, len(links), 8) } + +func TestNormalizeConfluenceWebUIPath(t *testing.T) { + t.Run("confluence-cloud-experience-prefix", func(t *testing.T) { + input := "/ex/confluence/05594958-6d5d-4e00-9017-90926d8b82d5/wiki/spaces/DVT/pages/5645697027/DX" + expected := "/wiki/spaces/DVT/pages/5645697027/DX" + assert.Equal(t, expected, normalizeConfluenceWebUIPath(input)) + }) + + t.Run("already-canonical-wiki", func(t *testing.T) { + input := "/wiki/spaces/DVT/pages/5645697027/DX" + assert.Equal(t, input, normalizeConfluenceWebUIPath(input)) + }) + + t.Run("local-relative-path-unchanged", func(t *testing.T) { + input := "./img/some-nice-image.png" + assert.Equal(t, input, normalizeConfluenceWebUIPath(input)) + }) +}