IP Allowlist Bypass Exposes Internal Metrics
The Risk
Anyone on the internet could read an internal status page that was supposed to be private and locked to a short list of trusted addresses. By adding a tiny, harmless-looking change to the web address, a stranger walked straight past that lock with no password, no login, and no special access. The page handed back the work email addresses of thousands of employees along with the complete list of the company's business customers and exactly which product each one used. That is enough information to run convincing, targeted scam emails against every customer and staff member at once.
The Vulnerability
The target ran an internal monitoring and metrics endpoint that was meant to be reachable only from a small set of trusted source addresses. An address-based allowlist at the edge gateway returned 403 Forbidden to anyone else requesting the endpoint directly.
The flaw was in the order of operations at the gateway. The allowlist check ran against the raw request path, but the path was normalized (cleaned up) only afterward, once the request had already passed the check. That gap meant a request that did not look like the protected path during the check could still resolve to it after the check.
Two different gateway fleets fronted the affected hosts, each with its own normalization quirk:
- One fleet stripped a leading dot-segment after the allowlist match, so
/./metricsslipped through while a bare/metricswas blocked. - The other fleet collapsed a trailing slash after the match, so
/metrics/slipped through while/metricsand/./metricswere blocked.
A single combined variant, /./metrics/ sent with the raw path preserved, defeated both fleets at once. A separate set of hosts exposed the metrics endpoint with no allowlist at all and answered 200 OK directly.
The Attack
No account, token, or credential was required. The entire attack was a single unauthenticated GET request.
Confirming the Control, Then Defeating It
A direct request to the protected endpoint returned 403 Forbidden, confirming the allowlist was active:
curl -sI "https://internal-dashboard.example/metrics"
# HTTP/1.1 403 Forbidden Adding a leading dot-segment and preserving the raw path returned 200 OK with the full metrics payload, over 600 KB of data:
curl -s --path-as-is "https://internal-dashboard.example/./metrics" The same trick worked across the company's internal dashboard host and 7 related servers spanning production and staging. On the second gateway fleet, where the dot-segment alone was blocked, a trailing slash (/metrics/) achieved the same bypass.
Harvesting the Full Roster Across Replicas
Each line in the metrics payload that tracked login counts carried labels for a real person: their employer organization, the specific product they used, and their work email address in clear text. A single request returned hundreds of unique employee emails across dozens of customer organizations.
The counters were held in memory per backend replica, and each request was load-balanced to a different replica, so every response returned a different subset. No single response held the complete set. By polling the endpoint repeatedly and taking the union across replicas, an attacker accumulated the entire roster. The union across several consecutive requests reached several thousand distinct employee emails across more than a hundred organizations, larger than any single response.
The Bypass Was Not Limited to One Path
The same normalization flaw defeated the allowlist on every path, not just the metrics endpoint. An address-restricted admin route returned 403 directly but reached the application behind it (returning 401) through the dot-segment variant:
curl -s -o /dev/null -w "direct=%{http_code}\n" \
"https://internal-dashboard.example/api/admin"
# direct=403 (blocked by the allowlist)
curl -s -o /dev/null -w "bypass=%{http_code}\n" --path-as-is \
"https://internal-dashboard.example/./api/admin"
# bypass=401 (reached the app, which enforces its own auth) This proved the network-level allowlist was fully circumventable on every path. The metrics endpoint was simply the path that had no additional application authentication behind it, so the bypass there produced a complete data dump.
The Impact
An unauthenticated attacker on the public internet could retrieve the personal work email addresses of thousands of employees, together with the complete list of the provider's B2B customers and exactly which product each customer used.
The customer base spanned regulated-industry operators. Each login record mapped one real person to their employer, the product they used, and their login count, all in clear text. Counts observed during testing cycled through discrete tiers depending on which replica answered, with the polled union reaching several thousand distinct emails across more than a hundred organizations.
This exposure enabled:
- Targeted spear-phishing against the entire customer base and internal staff, using real names, real employers, and the exact product each person used as pretext.
- Competitive and regulatory intelligence: a map of which operator ran which product, plus per-organization activation status.
- Reconnaissance for further attacks: the same payload leaked the server-side language version and a full inventory of internal administrative route names (user impersonation, password reset, mass user assignment, identity sync, and sensitive-data decryption).
The route names leaked through the metric labels, but the routes themselves remained gated by application authentication and were not reachable through the bypass.
Remediation
- Normalize the request path before evaluating the allowlist, so the check runs against the same resolved path the backend will serve. Reject or collapse dot-segments and trailing slashes prior to the access decision.
- Do not rely on a network address allowlist as the only control on sensitive endpoints. Add real authentication in front of the metrics endpoint and any administrative route.
- Strip personally identifiable labels (email addresses, names, employer organizations) out of metric series. Counters should aggregate, not enumerate individuals.
- Remove the metrics endpoint from public-facing hosts entirely, or move it onto a separate internal-only network path that the public edge cannot route to.
- Audit all hosts in the fleet for the same exposure, including staging environments, and confirm consistent normalization behavior across every gateway type in use.