Skip to content
CommonLayer
Documentation menu
On this page

ADR-0025: One SSRF-safe client for user-influenced outbound HTTP

Status: Accepted (WP-01). Implemented in crates/commonlayer-net/src/lib.rs and ranges.rs.

Context

The platform fetches URLs that users influence: outbound webhook endpoints, manifest files from registered repositories, OAuth/OIDC providers. A naive client can be pointed at internal services, cloud metadata endpoints or loopback addresses, directly or via DNS rebinding and redirects.

Decision

commonlayer_net::SafeClient:

  • resolves DNS itself and refuses the answer if any address is in a blocked range (loopback, private, link-local, CGNAT, multicast, metadata, IPv6 equivalents and mapped addresses), then pins the connection to the vetted address;
  • never follows redirects, rejects credentials in URLs, enforces HTTPS in production, and caps time and response size;
  • ignores environment proxy settings, because a proxy would bypass the address checks. Explicit allowed_networks can exempt ranges (tests, private OIDC providers).

Consequences

  • Feeds whose canonical URL redirects cannot be fetched; the EPSS default was changed to the FIRST API for this reason (WP-12).
  • In environments that only allow egress through a proxy, feed and webhook calls fail by design. In the build sandbox the feed adapters were therefore tested against recorded responses only.
  • Payment-provider calls (Stripe) use a regular client because their URL is operator configuration, not user input.