Attack ChainAIDerived
Hypothetical attack flow derived from CVE metadata – not a confirmed exploit chain
-
AccessIdentify 9Router login reachable without custom-server.js wrapper
-
DeliverySend POST /api/auth/login with rotating X-9r-Real-Ip header
-
ExploitEach guess keyed to fresh bucket, no 429 lockout
-
ExecutionBrute-force admin password unthrottled
-
ImpactRecover credentials, obtain administrative session
Vulnerability Assessment
| Weakness |
CWE
OWASP Top 10:2025
A07:2025 - Authentication Failures
ASVS 5.0
V6 - Authentication Brute-force prevention, rate limiting
|
| Exploitation Conditions | Exploitable only when 9Router is deployed so that HTTP requests reach Next.js directly WITHOUT the bundled custom-server.js wrapper that normally overwrites X-9r-Real-Ip from the unspoofable TCP socket address; in that mode the login endpoint (POST /api/auth/login, default bind 0.0.0.0) trusts the attacker-supplied X-9r-Real-Ip header as the loginLimiter bucket key. The attacker needs no authentication or user interaction and simply rotates the header per request to defeat the five-attempt progressive lockout. Realistic impact is LIMITED by: (1) the non-default deployment requirement (missing/bypassed custom-server.js sanitizer), and (2) the fact that administrative takeover still requires the dashboard password to be weak or guessable - the flaw only removes the throttle, it does not itself yield credentials. |
| Impact | The CVSS 3.1 vector (AV:N/AC:L/PR:N/UI:N/S:U/C:L/I:N/A:N, 5.3 Medium) reflects a network-reachable, unauthenticated, low-complexity flaw whose direct technical impact is limited to confidentiality (C:L) - it removes brute-force throttling rather than directly disclosing data or granting code execution. Crucially, the vulnerability is gated on a non-default deployment mode: requests must reach Next.js WITHOUT the bundled custom-server.js wrapper, so the header is attacker-controlled. That deployment precondition is not captured in the vendor's AC:L and realistically raises attack complexity (I lean AC:H). There is no EPSS score, no CISA KEV listing, and no distinct public exploit artifact provided, so this is no public exploit identified at time of analysis - though the GHSA advisory states the bypass was reproduced against a live instance (header rotation yielding unlimited 401s vs. 429 lockout on a fixed header), which raises confidence the weakness is real and trivially triggerable. Real-world priority is LOW-to-MEDIUM: even successful exploitation only enables unthrottled guessing, and administrative takeover still depends on a weak/guessable dashboard password. Combined with the product's tiny deployment footprint, this is a genuine-but-narrow issue rather than a widespread emergency. Note a data conflict: the description and release tag say fixed in 0.5.6 while the package intelligence lists vulnerable <=0.5.4 and fixed in 0.5.8 - verify the exact fixed version with the vendor. |
| Exploit ScenarioDerived | An operator deploys 9Router in a mode that bypasses the custom-server.js sanitizer (e.g., serving Next.js directly, default bind 0.0.0.0), so the client-supplied X-9r-Real-Ip header reaches getClientIp unmodified. A remote unauthenticated attacker scripts password guesses against POST /api/auth/login, assigning a fresh X-9r-Real-Ip value (10.0.0.1, 10.0.0.2, ...) on each request so every guess lands in a new lockout bucket and the five-attempt 429 progressive lock never fires, permitting unlimited guessing until the admin password is recovered. No standalone public exploit code is published, but the advisory documents a working reproduction against a live instance. |
Get an e-mail when this CVE is exploited, patched or re-scored. Free account.
Alert meAnalysisAIv1 – Sep 22, 2026
Improper restriction of excessive authentication attempts (CWE-307) in the 9Router AI router package (decolua/9router) before version 0.5.6 allows remote unauthenticated attackers to defeat the dashboard login lockout by rotating the client-controlled X-9r-Real-Ip header on every password guess, so each request lands in a fresh failed-attempt bucket and the five-attempt progressive 429 lockout never fires. The flaw is exploitable only in deployments where HTTP requests reach Next.js directly without the bundled custom-server.js wrapper that normally overwrites X-9r-Real-Ip from the unspoofable TCP socket address; the login endpoint binds to 0.0.0.0 by default, so exposure is network-reachable. Impact is limited to confidentiality (unauthorized administrative session only if the dashboard password is separately weak or guessable) and the throttle removal itself does not yield credentials; no public exploit identified at time of analysis, and the weakness is not listed in CISA KEV.
RemediationAI
Apply the vendor fix by upgrading 9Router to version 0.5.6 or later; the advisory GHSA-32gc-64m7-hj7v and release tag v0.5.6 designate the patched release, while the package metadata in the same advisory lists 0.5.8 as the fixed version, so upgrading to 0.5.8 or newer is the safest choice. The upstream patch is commit efd20be8d81ef2e256a7037f3aa78e6b567b5fd3, which makes custom-server.js trust X-Real-Ip/X-Forwarded-For only when the TCP peer is a loopback reverse proxy. If immediate upgrade is not possible, ensure the deployment actually runs through the bundled custom-server.js wrapper and that nothing in front of it strips or bypasses that sanitizer; never expose the Next.js listener directly. Where a reverse proxy is used, configure it to strip any inbound X-9r-Real-Ip (and normalize X-Forwarded-For/X-Real-IP) before forwarding, so attacker-chosen values cannot reach the app - the trade-off is that misconfigured proxy-header handling can itself break rate-limiting keys, so validate the resulting client-IP determination. Bind the dashboard to loopback or a restricted management network and firewall off public access to POST /api/auth/login (side effect: legitimate remote dashboard users lose direct access and must use a VPN or jump host). Enforce a long, unique administrative password and enable MFA/SSO if the deployment supports it, and apply edge/WAF rate limiting keyed on the unspoofable TCP source address rather than any header (trade-off: shared NAT or proxy egress addresses may be throttled collectively). Monitor authentication logs for sustained 401 bursts from a single source address that never trigger 429 responses, which is the signature of this bypass.
Affected VersionsENISA
Affected Packages
Source: OSV (Open Source Vulnerabilities)
Affects your stack
Affects 1 package in npm
Checking this CVE against your own stacks and servers is part of the Basic plan and up.
Technical ContextAI · show details
9Router is a Node.js/Next.js application that proxies AI provider requests and includes an administrative dashboard. Authentication for that dashboard is handled by POST /api/auth/login, protected by a per-IP progressive lockout implemented in src/lib/auth/loginLimiter.js: getClientIp() derives the rate-limit bucket key, and checkLock()/recordFail() maintain a per-bucket counter with MAX_FAILS_BEFORE_LOCK = 5 before returning HTTP 429. The root cause is CWE-307 (Improper Restriction of Excessive Authentication Attempts): the bucket key is read from the client-supplied X-9r-Real-Ip header rather than from the transport layer, under the assumption that the bundled custom-server.js wrapper always overwrites that header with the TCP socket peer address. In direct-to-Next.js deployments that assumption fails and the attacker chooses the bucket key, so counters never accumulate. The upstream fix in commit efd20be8d81ef2e256a7037f3aa78e6b567b5fd3 changes custom-server.js to trust X-Real-Ip/X-Forwarded-For only when the TCP peer is a loopback reverse proxy (127.0.0.1, ::1, ::ffff:127.0.0.1), otherwise keying on the unspoofable socket address; the same commit incidentally adds unrelated CodeBuddy CN executor/provider registry code. CPE cpe:2.3:a:decolua:9router:*:*:*:*:*:*:*:* covers all affected releases. The published CVSS 3.1 vector is AV:N/AC:L/PR:N/UI:N/S:U/C:L/I:N/A:N (5.3 Medium); the independent assessment adjusts attack complexity to High (AV:N/AC:H/PR:N/UI:N/S:U/C:L/I:N/A:N) to reflect the non-default deployment prerequisite, while agreeing that the direct technical impact is confidentiality-only and that no authentication or user interaction is required on the vulnerable endpoint.
Know when 9Router gets its next vulnerability
- Watch products and get an email when something new is published
- Check this CVE against your own stack and servers
- Exploit and PoC references, threat intelligence from 22 sources
No credit card · 7-day full trial
Severity by source
AV:N/AC:L/PR:N/UI:N/S:U/C:L/I:N/A:N
Unauthenticated network reach with a trivial header trick, but gated on a non-default deployment lacking the custom-server.js sanitizer (AC:H); impact limited to enabling brute-force so C:L, I:N, A:N.
Primary rating from Vendor (GitHub_M).
CVSS VectorVendor: GitHub_M
Lifecycle Timeline
1DescriptionCVE.org
9Router is an AI router & token saver. Prior to 0.5.6, 9Router deployments that allow requests to reach Next.js without the sanitizing custom-server.js wrapper use the client-supplied X-9r-Real-Ip value as the bucket key in getClientIp, checkLock, and recordFail in src/lib/auth/loginLimiter.js for POST /api/auth/login. A remote unauthenticated attacker can rotate the header on every password guess so each request uses a new failed-attempt bucket and the five-attempt progressive lockout never returns HTTP 429. This permits unthrottled password guessing against the dashboard login and can lead to an administrative session if the password is recovered. This issue is fixed in version 0.5.6.
Threat Intelligence Overview
How this decision was reached
The engine reads each signal below and applies a fixed list of rules from top to bottom. The first rule that matches sets the recommended action – like a statement, every line is shown.
What every action level means
SSVC AssessmentENISA
Priority Score
Unauthenticated CRUD on the provider-management API in 9Router (through 0.4.41) lets remote attackers with no credential
Server-Side Request Forgery (SSRF) in 9Router 0.5.4 and earlier allows unauthenticated remote attackers to probe interna
Authentication bypass in 9Router (npm package '9router') before 0.5.6 lets a remote, unauthenticated attacker reach the
Remote unauthenticated code execution in 9router 0.4.59 (by decolua) lets an attacker chain three flaws - a hardcoded de
Remote authorization bypass in decolua 9router up to version 0.3.47 allows unauthenticated network attackers to access t
Unauthenticated API key disclosure in 9Router (npm package '9router' by decolua) through version 0.4.41 lets any remote
Authenticated remote code execution in 9Router before 0.5.2 lets a logged-in attacker run arbitrary OS commands on the h
Unauthenticated information disclosure in 9Router (decolua/9router) through version 0.4.41 lets remote attackers read ev
Authentication bypass in 9Router (AI router & token saver) prior to 0.5.4 lets any authenticated user disable applicatio
Authorization-gate bypass in 9Router (decolua/9router) before 0.5.2 lets a remote unauthenticated attacker reach protect
Server-side request forgery in 9Router before 0.4.72 lets an authenticated (PR:L) or locally-connected user abuse the /v
Authentication bypass in 9Router (decolua/9router) versions prior to 0.5.2 lets remote unauthenticated attackers reach p
EUVD-2026-84542
GHSA-32gc-64m7-hj7v
NVD
CVE.org
EPSS
Vulnrichment
Exploit-DB