Skip to content

fix(utils/redirect): escape HTML special characters in body#1317

Merged
pi0 merged 9 commits into
mainfrom
fix/redirect-html-escape
Mar 16, 2026
Merged

fix(utils/redirect): escape HTML special characters in body#1317
pi0 merged 9 commits into
mainfrom
fix/redirect-html-escape

Conversation

@productdevbook

@productdevbook productdevbook commented Mar 14, 2026

Copy link
Copy Markdown
Member

Summary

  • The `redirect()` function's meta refresh HTML body only escaped `"` as `%22`, but `<`, `>`, `&`, and `'` were left unescaped
  • A redirect URL containing HTML tags (e.g. `"><script>alert(1)</script>`) could inject markup into the redirect page body
  • Now escapes `&` as `&`, `<` as `%3C`, `>` as `%3E`, `'` as `%27` — all valid in URL context and safe in HTML attribute context
  • The raw `location` header remains unmodified (correct per RFC 3986)

Test plan

  • Existing redirect test passes
  • New test verifies `<script>` tags are escaped in the HTML body
  • All utils tests pass (73/73)

🤖 Generated with Claude Code

Summary by CodeRabbit

  • Bug Fixes

    • Improved redirect response encoding so HTML-special characters (&, ", <, >) are escaped in the returned page, preventing raw HTML/JS injection and reducing XSS risk.
    • Redirect HTML bodies now consistently present percent-encoded representations of unsafe characters while preserving the original Location header.
  • Tests

    • Added test coverage to verify special characters are escaped in redirect HTML bodies and Location headers remain correct.

@productdevbook productdevbook requested a review from pi0 as a code owner March 14, 2026 15:53
@coderabbitai

coderabbitai Bot commented Mar 14, 2026

Copy link
Copy Markdown

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Redirect embedding now HTML-escapes special characters (&, ", <, >) when inserting the Location into the meta-refresh HTML; a new test verifies the Location header remains unchanged while the HTML body contains escaped/percent-encoded representations.

Changes

Cohort / File(s) Summary
Redirect implementation
src/utils/response.ts
Changed how the redirect URL is embedded in the HTML response: HTML-escape &, ", <, > for the meta-refresh/body instead of only quoting; response headers and control flow unchanged.
Redirect tests
test/utils.test.ts
Added test "escapes special characters in HTML body" that sends a malicious URL, asserts the Location header equals the input, and verifies the HTML body does not contain raw <script> but contains its percent-encoded form (%3Cscript%3E) and the HTML entity &quot;.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~10 minutes

Poem

🐇 I hop through code with careful paws,
swapping raw signs for safer laws.
%3Cscript%3E tucked from sight,
&quot; shines gentle, soft and light. 🥕

🚥 Pre-merge checks | ✅ 3
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 'fix(utils/redirect): escape HTML special characters in body' directly and clearly summarizes the main change: adding HTML escaping for special characters in the redirect response body to prevent injection attacks.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch fix/redirect-html-escape
📝 Coding Plan
  • Generate coding plan for human review comments

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Tip

You can enable review details to help with troubleshooting, context usage and more.

Enable the reviews.review_details setting to include review details such as the model used, the time taken for each step and more in the review comments.

@pkg-pr-new

pkg-pr-new Bot commented Mar 14, 2026

Copy link
Copy Markdown

Open in StackBlitz

npm i https://pkg.pr.new/h3@1317

commit: 3c8f614

Comment thread src/utils/response.ts Outdated
productdevbook and others added 2 commits March 14, 2026 23:23
The `redirect()` function only escaped double quotes in the meta refresh
HTML body, leaving `<`, `>`, `&`, and `'` unescaped. A malicious redirect
URL containing HTML tags (e.g. `<script>`) could inject markup into the
redirect page body.

Now properly escapes all HTML-significant characters using percent-encoding
for URL characters (`<`, `>`, `'`, `"`) and HTML entities for `&`.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Replace manual regex chain with standard URL/encodeURI escaping:
- Absolute URLs: URL constructor properly percent-encodes unsafe chars
- Relative URLs: encodeURI handles the escaping

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@productdevbook productdevbook force-pushed the fix/redirect-html-escape branch from bd6e58f to c69de1f Compare March 14, 2026 20:24
Comment thread src/utils/response.ts Outdated

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@src/utils/response.ts`:
- Line 47: The encodedLoc assignment must ensure ampersands are HTML-escaped for
use inside the meta-refresh body: after computing encodedLoc (via
URL.canParse(...) ? new URL(location).href : encodeURI(location)), replace all
'&' with '&amp;'; additionally, for the encodeURI(...) branch ensure single
quotes are percent-encoded (replace "'" with "%27") as a safety net, while
avoiding redundant "'->%27" on the URL.href branch. Update the logic around
encodedLoc (the URL.canParse / new URL(location).href / encodeURI(path)) to
perform these replacements before using encodedLoc in the HTML meta-refresh.

In `@test/utils.test.ts`:
- Around line 45-53: Update the "escapes special characters in HTML body" test
to assert that ampersand and single-quote are escaped by adding checks after
fetching the body: reuse the existing malicious variable and result/body
variables and assert body does not contain literal "&" or "'" unescaped where
they would appear, and assert it contains their percent-encoded/escaped
equivalents (e.g., "%26" and "%27" or the expected HTML-escaped sequences) so
that redirect(malicious), t.fetch("/"), result.headers.get("location"), and body
assertions cover &, ' in addition to <script>.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: a8bf44aa-0055-4361-89a5-e97f4ce54122

📥 Commits

Reviewing files that changed from the base of the PR and between bd6e58f and 21366c1.

📒 Files selected for processing (2)
  • src/utils/response.ts
  • test/utils.test.ts

Comment thread src/utils/response.ts Outdated
Comment thread test/utils.test.ts
productdevbook and others added 2 commits March 15, 2026 07:44
Per maintainer review:
- URL.canParse may not be available in all runtimes
- encodeURI handles both absolute and relative URLs correctly
- No need for conditional logic — encodeURI is sufficient

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
`encodeURI` does not escape HTML metacharacters (`"`, `<`, `>`), allowing
potential XSS via attribute breakout in the `<meta>` refresh tag.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@codecov

codecov Bot commented Mar 16, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.

📢 Thoughts on this report? Let us know!

pi0 and others added 2 commits March 16, 2026 10:52
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@pi0 pi0 changed the title fix(response): escape HTML special characters in redirect body fix(utils/redirect): escape HTML special characters in body Mar 16, 2026
@pi0 pi0 merged commit 60a2e91 into main Mar 16, 2026
7 of 8 checks passed
@pi0 pi0 deleted the fix/redirect-html-escape branch March 16, 2026 09:59
@coderabbitai coderabbitai Bot mentioned this pull request Mar 19, 2026
6 tasks
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants