Sanitization Test with DOMPurify
HTML
<!DOCTYPE html>
<html>
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/dompurify/3.0.6/purify.min.js"></script>
</head>
<body>
<h3>Test: XSS between style tags</h3>
<div id="result"></div>
<script>
function sanitizeHtmlWithStylePreservation(html) {
if (!html) return html;
const styleTags = [];
let templateWithoutStyles = html;
const styleRegex = /<style[\s\S]*?<\/style>/gi;
let match;
while ((match = styleRegex.exec(html)) !== null) {
styleTags.push(match[0]);
templateWithoutStyles = templateWithoutStyles.replace(
match[0],
`<div data-style-placeholder="${styleTags.length - 1}"></div>`
);
}
let sanitized = DOMPurify.sanitize(templateWithoutStyles);
let restoredTemplate = sanitized;
styleTags.forEach((styleTag, index) => {
restoredTemplate = restoredTemplate.replace(
`<div data-style-placeholder="${index}"></div>`,
styleTag
);
});
return restoredTemplate;
}
function htmlEncode(str) {
return str.replace(/&/g, '&')
.replace(/</g, '<')
.replace(/>/g, '>')
.replace(/"/g, '"')
.replace(/'/g, ''');
}
// Test
const input = '<stylefoobar>body { color: red; }<img src=x onerror=alert(2)></style>';
const output = sanitizeHtmlWithStylePreservation(input);
document.getElementById('result').innerHTML = `
<p><strong>Encoded Input:</strong><br><code>${htmlEncode(input)}</code></p>
<p><strong>Encoded Output:</strong><br><code>${htmlEncode(output)}</code></p>
...