Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions .jules/sentinel.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
## 2025-01-30 - Prevent XSS in Email Previews with Sandboxed Iframes
**Vulnerability:** Use of `dangerouslySetInnerHTML` for rendering email HTML, even when sanitized by `DOMPurify`, can present residual XSS risks.
**Learning:** Using a sandboxed `iframe` with `srcDoc` and `sandbox="allow-popups allow-popups-to-escape-sandbox"` eliminates script execution and same-origin access risks, providing defense in depth. However, styles must be manually injected via `<style>` tag within the `srcDoc` to preserve visual formatting because Tailwind classes on the `iframe` do not affect inner elements.
**Prevention:** Default to using sandboxed `iframes` for displaying any complex, untrusted, or dynamic HTML rather than relying solely on sanitization libraries.
18 changes: 16 additions & 2 deletions components/accounts/ppp-savings-panel.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -232,8 +232,22 @@ export function PppSavingsPanel({ orgSlug, accountId }: PppSavingsPanelProps) {
)}
</div>
</div>
<div className="min-h-[24rem] w-full overflow-auto bg-white p-6 text-sm text-black">
<div dangerouslySetInnerHTML={{ __html: sanitizedEmailHtml }} />
<div className="min-h-[24rem] w-full overflow-hidden bg-white text-sm text-black">
<iframe

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Add the required implementation run report

This changes browser-rendering and security behavior in the PPP email preview, making it a meaningful implementation slice, but the diff contains no docs/runs/ report recording the validation performed and remaining risk; .jules/sentinel.md does not follow the run-report template. Add the required report so the claimed Playwright and project-check results are auditable.

AGENTS.md reference: AGENTS.md:L39-L39

Useful? React with πŸ‘Β / πŸ‘Ž.

title="Email Preview"
srcDoc={`<style>
body {
margin: 0;
padding: 1.5rem;
font-family: ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji";
font-size: 0.875rem;
line-height: 1.25rem;
color: black;
}
</style>${sanitizedEmailHtml}`}
sandbox="allow-popups allow-popups-to-escape-sandbox"
className="h-full min-h-[24rem] w-full border-0"
/>
</div>
</div>
</div>
Expand Down
Loading