From 06f559e5623597949e41087c5811f5bfca45e891 Mon Sep 17 00:00:00 2001 From: Jonathan Addington Date: Mon, 31 Mar 2025 14:18:34 -0400 Subject: [PATCH 1/2] Fix: Prevent XSS vulnerability in error message display MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Added escapeHtml function to properly sanitize error messages - Updated failSvg function to escape error messages before rendering in SVG - Prevents cross-site scripting attacks via error message manipulation 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude --- index.js | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) diff --git a/index.js b/index.js index cf6f695..364631e 100644 --- a/index.js +++ b/index.js @@ -88,6 +88,18 @@ function utf8ToAscii(str) { .join(''); } +function escapeHtml(str) { + if (typeof str !== 'string') { + return ''; + } + return str + .replace(/&/g, '&') + .replace(//g, '>') + .replace(/"/g, '"') + .replace(/'/g, '''); +} + function sanitizeErrorHeader(msg) { if (typeof msg === 'string') { return utf8ToAscii(msg).replace(/\r?\n|\r/g, ''); @@ -122,7 +134,7 @@ function failSvg(res, msg, statusCode = 500) { -

${msg}

+

${escapeHtml(msg)}

`); } From f655b5e2f28dcaeca78cf23486b1f5f23639497d Mon Sep 17 00:00:00 2001 From: Jonathan Addington Date: Mon, 31 Mar 2025 14:19:35 -0400 Subject: [PATCH 2/2] Fix: Prevent reflected XSS vulnerability in format error message MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Added HTML escaping to format error message to prevent reflected XSS attacks - Uses the escapeHtml function to sanitize user-provided format parameter - Ensures unrecognized file format values cannot be used for XSS attacks 🤖 Generated with [Claude Code](https://claude.ai/code) Co-Authored-By: Claude --- index.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/index.js b/index.js index 364631e..647ec91 100644 --- a/index.js +++ b/index.js @@ -365,7 +365,7 @@ app.get('/chart', (req, res) => { renderChartToPng(req, res, opts); } else { logger.error(`Request for unsupported format ${outputFormat}`); - res.status(500).end(`Unsupported format ${outputFormat}`); + res.status(500).end(`Unsupported format ${escapeHtml(outputFormat)}`); } telemetry.count('chartCount');