From f5e997ba9214c8a4a50803f0cad7ceee01cef876 Mon Sep 17 00:00:00 2001 From: Linus Rath <139418639+rathlinus@users.noreply.github.com> Date: Thu, 29 Oct 2026 02:54:23 +0100 Subject: [PATCH 01/12] fix: drop event handlers that follow a slash and run no inline handlers in the reader and composer --- src/components/EmailBodyView.tsx | 7 +- src/lib/__tests__/editor-html.test.ts | 19 +- src/lib/__tests__/email-html.test.ts | 80 ++++++ src/lib/editor-html.ts | 15 +- src/lib/email-html.ts | 334 +++++++++++++++++++++----- 5 files changed, 383 insertions(+), 72 deletions(-) diff --git a/src/components/EmailBodyView.tsx b/src/components/EmailBodyView.tsx index bc2068f9..86c47d6d 100644 --- a/src/components/EmailBodyView.tsx +++ b/src/components/EmailBodyView.tsx @@ -5,7 +5,7 @@ import { useNavigation } from '@react-navigation/native'; import type { NativeStackNavigationProp } from '@react-navigation/native-stack'; import { Image as ImageIcon, ShieldCheck } from './icons'; import type { Email } from '../api/types'; -import { extractCidRefs } from '../lib/email-html'; +import { extractCidRefs, isUserLinkNavigation } from '../lib/email-html'; import { hasTruncatedDisplayedBody, pickEmailBody, selectRenderableHtml } from '../lib/email-body'; import { buildQuoteCollapseScript } from '../lib/quote-collapse'; import { bodyDocument } from '../lib/email-body-document'; @@ -834,6 +834,11 @@ export default function EmailBodyView({ // any other) navigation would replace the email body with no way // back, so it is refused; images are reachable via the chips. if (!url || url === 'about:blank') return true; + // A message opens links only when the user taps one. The page + // runs no script of its own, so nothing else should navigate; + // iOS says how a navigation started, so anything but a tap is + // refused there as well. Android always reports 'other'. + if (!isUserLinkNavigation(request, Platform.OS)) return false; if (/^mailto:/i.test(url)) { openMailto(url); return false; diff --git a/src/lib/__tests__/editor-html.test.ts b/src/lib/__tests__/editor-html.test.ts index 9e4a3265..a5f192b6 100644 --- a/src/lib/__tests__/editor-html.test.ts +++ b/src/lib/__tests__/editor-html.test.ts @@ -5,7 +5,7 @@ import { import { LIGHT_COLORS, DARK_COLORS } from '../../theme/tokens'; function extractScript(html: string): string { - const m = html.match(/