T09 · Insecure Skill Coding Practices
- Location
scripts/iresearch_report_search.py:425- Finding
Unrestricted Upstream-Controlled Report URL Fetch Enables SSRF
- Content
View full analysis
Vulnerability Details
File Location:
scripts/iresearch_report_search.py, lines 425–428, 471–478, 697, and 1079–1080
Vulnerability Type: Server-Side Request Forgery (SSRF) through insufficient URL validation
Risk Level: MediumVulnerable Code
python def fetch_bytes(url: str, headers: dict[str, str]) -> bytes: """Fetch a URL and return raw bytes.""" request = Request(url, headers=headers) with urlopen(request, timeout=20) as response: return response.read()python def normalize_report_link(url: str | None) -> str: """Normalize and validate a public report link.""" value = clean_text(url or "") if not value: return "" if value.startswith("//"): return f"https:{value}" if value.startswith("http://") or value.startswith("https://"): return value return ""python detail_url=normalize_report_link(item.get("VisitUrl")),python detail_url = require_report_link(summary.detail_url) html = fetch_html(detail_url)Technical Analysis
The iResearch list API supplies the
VisitUrlfield. The script treats that field as a valid report URL whenever it starts withhttp://,https://, or a protocol-relative prefix. It does not enforce an allowlist of expected report hosts, require HTTPS, restrict destination ports, validate resolved IP addresses, or validate redirect destinations.The accepted URL is later passed to
urlopen(), which performs the request and follows HTTP redirects by default. Consequently, a compromised or malicious upstream API response could direct the script toward:- Loopback services such as
127.0.0.1 - Private network services
- Link-local destinations
- Cloud instance metadata endpoints
- Unexpected external hosts
- An apparently legitimate host that redirects to one of these destinations
The user-supplied search query is ranked locally and is not sent to these report endpoints. The configured browser-like headers contain ...[truncated 1778 chars]
- Loopback services such as
- Remediation
View remediation
Remediation Suggestions
-
Allowlist exact destination hosts
- Permit only the report hosts required by the Skill, such as
report.iresearch.cn. - Reject userinfo components, ambiguous hostnames, unexpected subdomains, and nonstandard ports.
- Do not rely on substring or suffix checks that can be bypassed by domains such as
report.iresearch.cn.attacker.example.
- Permit only the report hosts required by the Skill, such as
-
Require HTTPS
- Reject plaintext
http://URLs. - Preserve TLS certificate and hostname verification.
- Reject plaintext
-
Construct URLs from trusted identifiers
- Prefer generating report detail URLs from validated numeric report IDs or known path formats.
- Avoid fetching arbitrary
VisitUrlvalues supplied by the remote API.
-
Validate resolved addresses
- Resolve the hostname before connecting.
- Reject loopback, private, link-local, multicast, reserved, unspecified, and other non-public address ranges for both IPv4 and IPv6.
- Account for DNS rebinding by ensuring the validated address is the address used for the connection.
-
Control redirects
- Disable automatic redirects or validate every redirect target using the same scheme, hostname, port, and resolved-address policy.
- Set a small redirect limit.
-
Apply response limits
- Enforce a maximum response size and verify expected content types to reduce denial-of-service and unexpected-content risks.
- Retain strict connection and read timeouts.
-
Add security tests
- Test rejection of localhost, RFC1918 ranges, IPv6 loopback, link-local addresses, cloud metadata addresses, encoded IP representations, protocol-relative URLs, credentials in URLs, nonstandard ports, and redirects to prohibited destinations.
-
