diff --git a/lib/__tests__/email-sanitization.test.ts b/lib/__tests__/email-sanitization.test.ts index d09e462..dba46de 100644 --- a/lib/__tests__/email-sanitization.test.ts +++ b/lib/__tests__/email-sanitization.test.ts @@ -287,6 +287,15 @@ describe('email-sanitization', () => { expect(html).toContain('class="text-primary hover:underline"'); }); + it('escapes linkClassName to defend against a caller-supplied injection', () => { + const malicious = 'x" onfocus="alert(1)" x="'; + const html = plainTextToSafeHtml('https://x.test', { linkClassName: malicious }); + const a = parseAnchor(html); + expect(a).not.toBeNull(); + expect(a!.getAttribute('onfocus')).toBeNull(); + expect(a!.className).toContain('onfocus='); + }); + it('preserves line breaks and tabs', () => { const html = plainTextToSafeHtml('a\nb\tc\r\nd'); expect(html).toContain('a
b    c
d'); diff --git a/lib/email-sanitization.ts b/lib/email-sanitization.ts index 53125e8..00b50aa 100644 --- a/lib/email-sanitization.ts +++ b/lib/email-sanitization.ts @@ -123,7 +123,7 @@ export function plainTextToSafeHtml( options?: { linkClassName?: string } ): string { const linkClass = options?.linkClassName - ? ` class="${options.linkClassName}"` + ? ` class="${escapeHtml(options.linkClassName)}"` : ''; return escapeHtml(text) .replace(/\r\n/g, '
')