GHSA-jfgx-762w-99vr: CSRF

Published Oct 20, 2026
·
Updated

An incomplete fix for GHSA-58c5-g7wp-6w37 (CVE-2025-66035) in @angular/common's HTTP Client (HttpClient) allows Cross-Site Request Forgery (XSRF) tokens to be leaked to attacker-controlled cross-origin domains when requests use URLs that exploit parsing discrepancies between regular expressions and the browser's WHATWG URL parser.

Technical Description

To address CVE-2025-66035, xsrfInterceptorFn introduced a regular expression (const ABSOLUTEURLREGEX = /^(?:https?:)?\/\//i) to detect and skip absolute and protocol-relative URLs before attaching the X-XSRF-TOKEN header.

However, browsers resolve request URLs passed to fetch() and XMLHttpRequest.open() using the WHATWG URL parser. For http: and https: schemes, the WHATWG URL standard performs several normalizations prior to resolving the authority/origin: Backslashes (\) are treated as forward slashes (/) — e.g., /\evil.example/x, \\evil.example/x, \/evil.example/x, https:\\evil.example/x, https:/\evil.example/x. Leading and trailing C0 control characters and spaces (<= 0x20) are stripped — e.g., ' //evil.example/x', '\0//evil.example/x', '\x1f//evil.example/x'. ASCII tab (\t), newline (\n), and carriage return (\r) characters are removed anywhere in the input — e.g., '/\t/evil.example/x', '/\n/evil.example/x', 'htt\tps://evil.example/x'.

Because these URLs do not match /^(?:https?:)?\/\//i, xsrfInterceptorFn treats them as relative same-origin URLs and attaches the X-XSRF-TOKEN header, while the browser resolves and dispatches the request to the cross-origin host (evil.example).

Note: Angular 21.0.3+ and 22.x replaced the regular expression with a WHATWG new URL(req.url, locationOrigin) origin comparison in #65683 and were already unaffected. However, the 20.3.x LTS branch retained the regular expression until 20.3.34.

Impact

The token leakage bypasses Angular's built-in XSRF protection on affected versions, allowing an attacker to capture the user's valid X-XSRF-TOKEN header if their server permits the request and custom header via CORS. Once obtained, the attacker can perform Cross-Site Request Forgery (CSRF) attacks against the victim user's session.

Attack Preconditions

1. The victim's Angular application must have XSRF protection enabled (enabled by default in HttpClient). 2. The attacker must be able to make the application send a state-changing HTTP request (e.g., POST, PUT, DELETE, PATCH) to a URL they control (such as /\attacker.example/api or //attacker.example/api).

Patches

The issue is resolved by parsing and comparing the request URL's origin against the application's current origin using the standard URL constructor (new URL(req.url, locationOrigin)).

21.0.3 (and all 22.x releases) 20.3.34

Workarounds

If you cannot immediately upgrade to a patched version: Validate and normalize outgoing request URLs using new URL(url, window.location.origin) and verify that parsedUrl.origin === window.location.origin before passing dynamic URLs to mutating HttpClient requests. Avoid passing untrusted or user-controlled URLs to HttpClient mutating methods.

Affected Software

3 affected componentsFixes available
npm/@angular/common<=19.2.25
npm/@angular/common>=20.0.0<20.3.34
20.3.34
npm/@angular/common>=21.0.0<21.0.3
21.0.3

Remediation

Recommended actions to resolve this vulnerability, in priority order.

  1. Upgrade

    Upgrade npm/@angular/common to a version that resolves this vulnerability.

    Fixed in 20.3.34
  2. Upgrade

    Upgrade npm/@angular/common to a version that resolves this vulnerability.

    Fixed in 21.0.3
  3. Upgrade

    Upgrade @angular/common to a version that resolves this vulnerability.

    Fixed in 20.3.34
  4. Upgrade

    Upgrade @angular/common to a version that resolves this vulnerability.

    Fixed in 21.0.3
  5. Upgrade

    Upgrade @angular/common to a version that resolves this vulnerability.

    Fixed in 22.x
  6. Compensating control

    Validate and normalize outgoing request URLs with new URL(url, window.location.origin), and verify that parsedUrl.origin === window.location.origin before passing dynamic URLs to mutating HttpClient requests.

Event History

Oct 20, 2026
Advisory Published
via GitHub·08:37 PM
Data Sourced
via GitHub·08:37 PM
DescriptionWeaknessAffected Software

Frequently Asked Questions

1

What conditions are needed for an attacker to receive an XSRF token?

The application must make an HttpClient request using an attacker-controlled cross-origin URL that bypasses the interceptor's regular-expression check but is resolved by the browser's WHATWG URL parser as cross-origin. Such URLs can use backslashes or leading/trailing C0 control characters or spaces to create the parsing discrepancy.

2

Which request URL forms are relevant when assessing exposure?

Review requests whose URLs may be influenced by untrusted input, especially forms such as /\evil.example/x, \\evil.example/x, \/evil.example/x, https:\\evil.example/x, and https:/\evil.example/x. Also consider URLs with leading or trailing spaces or C0 control characters, because browsers strip these before resolving the destination origin.

Contact

SecAlerts Pty Ltd.
132 Wickham Terrace
Fortitude Valley,
QLD 4006, Australia
info@secalerts.co
By using SecAlerts services, you agree to our services end-user license agreement. This website is safeguarded by reCAPTCHA and governed by the Google Privacy Policy and Terms of Service. All names, logos, and brands of products are owned by their respective owners, and any usage of these names, logos, and brands for identification purposes only does not imply endorsement. If you possess any content that requires removal, please get in touch with us.
© 2026 SecAlerts Pty Ltd.
ABN: 70 645 966 203, ACN: 645 966 203