← CodeClarityLab Home
Browse by Category
+ added · updated 7d
← Back to glossary

Server-Side Request Forgery (SSRF)

security CWE-918 OWASP A10:2021 CVSS 8.6 PHP 5.0+ Advanced

Also Known As

Server-Side Request Forgery SSRF attack internal request forgery

TL;DR

The server is tricked into making HTTP requests to internal or unintended destinations on behalf of the attacker.

Explanation

SSRF allows attackers to make the server issue requests to arbitrary URLs — including internal services (cloud metadata endpoints, databases, admin interfaces) not exposed to the public internet. In cloud environments, SSRF against 169.254.169.254 can expose IAM credentials. Mitigation: validate and allowlist target URLs, block private IP ranges, reject non-http(s) schemes, and prefer dedicated HTTP client libraries with configurable restrictions.

How It's Exploited

POST webhook_url=http://169.254.169.254/latest/meta-data/
# AWS metadata endpoint — returns instance credentials
POST webhook_url=http://internal-admin.corp/secret

Diagram

flowchart TD
    ATK[Attacker] -->|fetch http://internal-api/secret| APP[Vulnerable App<br/>fetch URL param]
    APP -->|request from server| INT[Internal API<br/>192.168.1.100]
    APP -->|request from server| META[AWS Metadata<br/>169.254.169.254]
    INT & META -->|sensitive data| APP --> ATK
    subgraph Fix
        ALLOW[Allowlist external URLs<br/>Block internal IP ranges<br/>169.254/10.x/172.16/192.168]
    end
style FIX fill:#238636,color:#fff
style INT fill:#f85149,color:#fff
style META fill:#f85149,color:#fff

Common Misconception

SSRF is only dangerous if the server can reach the internet. SSRF is most dangerous for reaching internal services — cloud metadata endpoints (169.254.169.254), internal admin panels, and databases that are unreachable from the outside.

Why It Matters

SSRF turns your server into a proxy to attack internal services — cloud metadata endpoints, internal databases, and services on 127.0.0.1 that are unreachable from the internet.

Common Mistakes

  • Fetching user-supplied URLs with curl_exec() or file_get_contents() without validating the resolved IP.
  • DNS rebinding bypass: validating the hostname but not re-checking the IP at connection time.
  • Not blocking private IP ranges (10.x, 172.16.x, 192.168.x, 127.x, 169.254.x) after DNS resolution.
  • Allowing file://, gopher://, or dict:// URL schemes alongside http://

Code Examples

✗ Vulnerable
\$url  = \$_POST['webhook_url'];
\$resp = file_get_contents(\$url); // SSRF — attacker controls the URL
✓ Fixed
function safeRequest(string \$url): string {
    \$parsed = parse_url(\$url);

    // Only allow HTTPS to public internet
    if (\$parsed['scheme'] !== 'https') throw new \InvalidArgumentException('HTTPS required');

    // Block private/internal IP ranges
    \$ip = gethostbyname(\$parsed['host']);
    if (filter_var(\$ip, FILTER_VALIDATE_IP, FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE) === false) {
        throw new \InvalidArgumentException('Private/reserved IP not allowed');
    }

    return (new GuzzleHttp\Client())->get(\$url)->getBody()->getContents();
}

Added 15 Mar 2026
Edited 22 Mar 2026
Views 29
Rate this term
No ratings yet
🤖 AI Guestbook educational data only
| |
Last 30 days
0 pings F 0 pings S 0 pings S 0 pings M 0 pings T 0 pings W 0 pings T 0 pings F 0 pings S 0 pings S 1 ping M 0 pings T 0 pings W 1 ping T 0 pings F 0 pings S 1 ping S 1 ping M 0 pings T 0 pings W 1 ping T 1 ping F 0 pings S 1 ping S 0 pings M 0 pings T 0 pings W 0 pings T 1 ping F 0 pings S
No pings yet today
Amazonbot 9 Perplexity 7 SEMrush 3 Google 2 Ahrefs 2 ChatGPT 1 Unknown AI 1
crawler 22 crawler_json 1 pre-tracking 2
DEV INTEL Tools & Severity
🔴 Critical ⚙ Fix effort: Medium
⚡ Quick Fix
Validate and allowlist target URLs server-side; never forward raw user-supplied URLs to curl/file_get_contents
📦 Applies To
PHP 5.0+ web cli
🔗 Prerequisites
🔍 Detection Hints
curl_exec or file_get_contents or fopen with $_GET/$_POST URL parameter
Auto-detectable: ✓ Yes semgrep psalm
⚠ Related Problems
🤖 AI Agent
Confidence: High False Positives: Medium ✗ Manual fix Fix: High Context: Function Tests: Update
CWE-918

✓ schema.org compliant