T09 · Insecure Skill Coding Practices
- Location
scripts/ddg_fetch.py:78- Finding
Unrestricted URL Fetching Enables Server-Side Request Forgery
- Content
View full analysis
- Remediation
View remediation
Security audit
Security checks for vulnerabilities and agentic risk
This skill does what it claims, but its arbitrary URL fetching is under-scoped and could reach internal services from the agent environment.
Install only if you are comfortable with the agent making outbound web requests. Avoid using it for sensitive search terms, private URLs, localhost, intranet hosts, cloud metadata addresses, or URLs containing tokens. Prefer running it in a network-restricted environment and remove or pin the unnecessary dependency instruction before production use.
scripts/ddg_fetch.py:78Unrestricted URL Fetching Enables Server-Side Request Forgery
scripts/ddg_fetch.py:103Unbounded Response Reading and Gzip Decompression Can Exhaust Memory
SKILL.md:10Unpinned and Unnecessary Third-Party Package Installation
The description claims two major functions: web search via DuckDuckGo and URL fetching/content extraction. This code chunk implements only the second function. It accepts a URL argument, issues an HTTP request, parses HTML, extracts readable text, and returns metadata. There is no logic to query DuckDuckGo, construct search requests, parse search result pages, or return a list of search results. Therefore the declared description materially overstates the code’s actual behavior, making it a description-behavior mismatch.
The implemented script matches the search portion of the description: it queries DuckDuckGo without an API key, returns structured search results with title, URL, and snippet, and includes a fallback method using curl. However, the declared purpose also claims support for 'URL fetching' and extracting readable content from web pages, with triggers like 'fetch url' and 'get page content'. No such functionality exists in the supplied code. This is a material description-behavior mismatch because the declared capability includes a second major function that is absent from the implementation.
A search skill reasonably needs outbound HTTP requests, but invoking an external system binary is a materially broader capability than necessary for searching or fetching page content. This introduces command-execution capability unrelated to the manifest's stated purpose of simple web search without API keys.
The README describes web search and page fetching but does not warn that user queries and target URLs are transmitted to external network services. In an agent setting, this omission can mislead operators and users into exposing sensitive prompts, internal hostnames, tokens in URLs, or other confidential data to third parties.
The documented trigger phrases are broad natural-language patterns such as 'search for' and 'look up', which are common in ordinary conversation and can cause unintended invocation of this skill. In an agent environment, that can silently send user queries or referenced URLs to external services, creating privacy and policy-bypass risk through accidental activation rather than explicit consent.
The skill documents executable Python scripts that perform web search/fetch operations and are invoked through shell commands, but the manifest does not declare any tool scope such as permissions or allowed-tools. In an agent ecosystem, undeclared network and shell capability reduces policy enforcement and review visibility, increasing the chance of unintended command execution or outbound requests.
The description includes broad trigger phrases like 'search for', 'look up', and 'get page content', which can cause the skill to activate in many ordinary conversations. In an agent setting, over-broad invocation can lead to unexpected network access, external content retrieval, and shell/script execution without sufficiently specific user intent.
The documentation advertises web search and URL fetching but does not warn that using the skill sends requests to external services and retrieves untrusted remote content. Users and orchestrators may therefore invoke it without understanding privacy, tracking, or hostile-content exposure risks.
The manifest describes a web search and URL-fetching skill, and network access to DuckDuckGo is expected. However, this file's documented behavior is specifically about DuckDuckGo search, while the implementation adds process execution via an external curl command as an additional operational capability not reflected in the skill description.
subprocess module calls execute external commands. Without careful input validation, this enables command injection.
url
]
result = subprocess.run(cmd, capture_output=True, text=True, timeout=25)
html = result.stdout
if result.returncode != 0:
The code hard-codes 'Accept-Language: en-US,en;q=0.9', which imposes a specific language/locale on all requests. This is a natural-language policy concern because the skill does not offer user opt-in or any documented reason for restricting locale behavior.
The primary descriptive text is presented in Chinese with no indication that other languages are available or that the skill is intentionally region-specific. This can violate language or locale policy when a skill imposes a language without user opt-in or justification.
Several headings and instructions switch to Chinese (for example, installation and feature descriptions) even though the rest of the document is in English. This imposes a language choice on users without opt-in and may violate language/locale policy expectations.
The code hard-codes an Accept-Language header of "en-US,en;q=0.9,zh-CN;q=0.8,zh;q=0.7", which imposes a specific locale preference on all requests. This is a natural-language policy concern because users are not given any opt-in or configuration choice for the language/locale the skill presents to external sites.
The script falls back to running curl through subprocess.run, which is a subprocess execution path covered by the warning requirement for code files. Although the module docstring mentions a fallback, there is no visible confirmation, log, or CLI warning that an external command may be executed during operation.
This code sends the user's search query to DuckDuckGo over HTTP(S) via urllib, which is a network operation that transmits user data off-system. While the script's purpose is search, the file provides no explicit user-facing notice in the argument help, output, or runtime messaging that the query will be sent to an external service.
No suspicious patterns detected.