Skip to content

fix: fall back to JSON when JSONP callback sanitizes to empty string#7169

Closed
OussemaNehdi wants to merge 1 commit intoexpressjs:masterfrom
OussemaNehdi:fix/jsonp-sanitized-empty-callback-fallback
Closed

fix: fall back to JSON when JSONP callback sanitizes to empty string#7169
OussemaNehdi wants to merge 1 commit intoexpressjs:masterfrom
OussemaNehdi:fix/jsonp-sanitized-empty-callback-fallback

Conversation

@OussemaNehdi
Copy link
Copy Markdown

Summary

When res.jsonp() receives a callback containing only characters that get
stripped by the sanitization regex (e.g. ?callback=!!! or ?callback=<>@#),
the current code sets Content-Type: text/javascript before sanitizing,
then produces invalid JavaScript output:

/**/ typeof  === 'function' &&  ({"count":1});

This happens because the callback.length !== 0 check runs on the
unsanitized value. After callback.replace(/[^\[\]\w$.]/g, '') strips
everything, the empty string gets interpolated into the JSONP wrapper.

Fix

Move the charset sanitization before the JSONP branch conditional,
so the length check applies to the sanitized callback. When the sanitized
result is empty, the response falls back to a normal JSON response  the
same behavior as when no callback parameter is provided at all.

Test plan

- Added test: callback of only invalid chars (!!!)  falls back to application/json
- Added test: URL-encoded special chars (<>!@#) → JSON fallback, no X-Content-Type-Options override
- Added test: mixed valid/invalid chars (foo!bar) → JSONP with sanitized callback foobar
- All 1252 existing tests pass
- ESLint clean

Move callback charset sanitization before the JSONP branch check so
that callbacks containing only invalid characters (e.g. `?callback=!!!`)
fall back to a plain JSON response instead of producing invalid
JavaScript output with `text/javascript` Content-Type.
@krzysdz
Copy link
Copy Markdown
Contributor

krzysdz commented Apr 7, 2026

Duplicate of #7161

@krzysdz krzysdz marked this as a duplicate of #7161 Apr 7, 2026
@krzysdz krzysdz closed this Apr 7, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants