From 13cc62567c0463d16d7dec17a5c269f0da2371f8 Mon Sep 17 00:00:00 2001 From: Leonid Zaliubovskyi Date: Sun, 13 Sep 2026 13:37:55 +0200 Subject: [PATCH] Fix 12844 notification external link (#12845) * Fix external notification links * Add notification link regression test * Preserve fallback for empty notification links * Satisfy Biome optional-chain check * Apply Biome formatting * Retrigger CI --------- Co-authored-by: Oliver --- .../src/components/nav/NotificationDrawer.tsx | 8 +- src/frontend/tests/pui_notifications.spec.ts | 92 +++++++++++++++++++ 2 files changed, 98 insertions(+), 2 deletions(-) create mode 100644 src/frontend/tests/pui_notifications.spec.ts diff --git a/src/frontend/src/components/nav/NotificationDrawer.tsx b/src/frontend/src/components/nav/NotificationDrawer.tsx index 907023aa97..f220d99e7a 100644 --- a/src/frontend/src/components/nav/NotificationDrawer.tsx +++ b/src/frontend/src/components/nav/NotificationDrawer.tsx @@ -62,6 +62,10 @@ function NotificationEntry({ } } + const base = `/${getBaseUrl()}`; + const href = + link?.startsWith('/') && !link.startsWith(base) ? `${base}${link}` : link; + return ( @@ -72,7 +76,7 @@ function NotificationEntry({ > { @@ -81,7 +85,7 @@ function NotificationEntry({ onRead(); } - if (link.startsWith('/')) { + if (link?.startsWith('/')) { navigateToLink(link, navigate, event); } }} diff --git a/src/frontend/tests/pui_notifications.spec.ts b/src/frontend/tests/pui_notifications.spec.ts new file mode 100644 index 0000000000..add5675db5 --- /dev/null +++ b/src/frontend/tests/pui_notifications.spec.ts @@ -0,0 +1,92 @@ +import { expect, test } from './baseFixtures.js'; +import { doLogin } from './login.js'; + +const notifications = [ + { + pk: 1, + target: { + model_type: 'pluginconfig', + model_id: 1, + link: 'https://example.com/path' + }, + source: null, + user: 1, + category: 'test_external', + name: 'External Notification', + message: 'External notification link', + creation: '2026-09-12 12:00', + age: 1, + age_human: 'a moment ago', + read: false + }, + { + pk: 2, + target: { + model_type: 'pluginconfig', + model_id: 1, + link: '/settings/admin/' + }, + source: null, + user: 1, + category: 'test_internal', + name: 'Internal Notification', + message: 'Internal notification link', + creation: '2026-09-12 12:00', + age: 1, + age_human: 'a moment ago', + read: false + }, + { + pk: 3, + target: { + model_type: 'pluginconfig', + model_id: 1, + link: '/web/settings/admin/' + }, + source: null, + user: 1, + category: 'test_base', + name: 'Base Notification', + message: 'Notification link with base path', + creation: '2026-09-12 12:00', + age: 1, + age_human: 'a moment ago', + read: false + } +]; + +test('Notifications - link targets', async ({ page }) => { + await page.route('**/api/notifications/**', async (route) => { + if (route.request().method() !== 'GET') { + await route.continue(); + return; + } + + await route.fulfill({ + status: 200, + contentType: 'application/json', + body: JSON.stringify({ + count: notifications.length, + next: null, + previous: null, + results: notifications + }) + }); + }); + + await doLogin(page); + + await page.getByRole('button', { name: 'open-notifications' }).click(); + + await expect( + page.getByRole('link', { name: 'External Notification' }) + ).toHaveAttribute('href', 'https://example.com/path'); + + await expect( + page.getByRole('link', { name: 'Internal Notification' }) + ).toHaveAttribute('href', '/web/settings/admin/'); + + await expect( + page.getByRole('link', { name: 'Base Notification' }) + ).toHaveAttribute('href', '/web/settings/admin/'); +});