Back to skill

Security audit

Daily News Fetcher

Security checks for vulnerabilities and agentic risk

Overview

This skill does what it says by fetching public RSS news, with some quality and integrity risks but no evidence of hidden access, persistence, or malicious behavior.

Install only if you are comfortable with a skill that contacts public RSS feeds when asked for news and returns Chinese-formatted output. Treat headlines and summaries as untrusted news data, especially because one feed uses HTTP and upstream feed content could be altered or misleading.

Vulnerability Patterns
  • Insecure Skill Coding PracticesFinds exploitable flaws such as hardcoded secrets or command injection
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • Embedded Malicious CodeShips malicious scripts inside the skill and executes them locally
Findings (1)

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/fetch_news.py:43
Finding
Untrusted RSS Content Can Manipulate Agent Output## Vulnerability Details **File Location**: `scripts/fetch_news.py`, lines 43-78, 101, and 144-153 **Vulnerability Type**: Untrusted external content handling and plaintext transport **Risk Level**: Medium ### Vulnerable Code ```python with urllib.request.urlopen(req, timeout=10) as response: content = response.read().decode('utf-8', errors='ignore') # Simple RSS parsing items = content.split('<item>') for item in items[1:]: # Skip header title = '' link = '' description = '' # Extract title if '<title>' in item and '</title>' in item: start = item.find('<title>') + 7 end = item.find('</title>') title = item[start:end].strip() # Remove CDATA if present title = title.replace('<![CDATA[', '').replace(']]>', '') # Extract link if '<link>' in item and '</link>' in item: start = item.find('<link>') + 6 end = item.find('</link>') link = item[start:end].strip() # Extract description if '<description>' in item and '</description>' in item: start = item.find('<description>') + 13 end = item.find('</description>') description = item[start:end].strip() # Remove HTML tags and CDATA description = description.replace('<![CDATA[', '').replace(']]>', '') # Simple tag removal import re description = re.sub(r'<[^>]+>', '', description) if len(description) > 150: description = description[:150] + '...' ``` ```python feeds = [ ('https://feeds.bbci.co.uk/news/rss.xml', 'BBC'), ('http://www.xinhuanet.com/english/news_english.xml', '新华网'), ('https://rss.nytimes.com/services/xml/rss/nyt/World.xml', 'NYTimes'), ] ``` ```python for i, item in enumerate(news_items, 1): emoji = ['1️⃣', '2️⃣', '3️⃣', '4️⃣', '5️⃣'][i-1] lines.append(f"{emoji} {item['title']}") lines.append(f" 来源:{item['source']}") if item['description'] and item['description'] != '暂无摘要': lines ...[truncated 2301 chars]
Remediation
## Remediation Suggestions 1. Replace the plaintext RSS URL with a verified HTTPS endpoint. Reject any configured URL that does not use HTTPS. 2. Validate redirects explicitly and reject redirects to plaintext schemes or unexpected hosts. 3. Maintain an allowlist of exact feed hostnames and validate the final response URL after redirects. 4. Parse feeds with a maintained XML or RSS parser rather than delimiter-based string operations. 5. Treat every title, description, and link as untrusted data. Present these values in a clearly delimited or quoted data structure and instruct the consuming Agent never to follow instructions found in feed content. 6. Normalize control characters and apply reasonable field-length limits before output. 7. Validate extracted links and permit only expected `https` URLs if links are later exposed or opened. 8. Consider using source authentication, signed content where available, or a trusted news aggregation API when output integrity is important. 9. Log fetch and validation failures without including unsafe feed content, rather than silently suppressing every exception.
Vulnerability Patterns
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
Findings (6)

Lp3

Medium
Category
MCP Least Privilege
Confidence
96% confidence
Finding
The skill instructs the agent to run a network-capable script, but the manifest declares no explicit tool scope or permissions. This creates an authorization gap: the runtime may permit network access without a clear, reviewable policy boundary, increasing the chance of unintended data egress or misuse of external connectivity.

Vague Triggers

Medium
Confidence
94% confidence
Finding
The activation condition "or any request for current news updates" is open-ended and likely to match a wide range of normal user requests beyond the intended scope. Broad matching increases the chance of unintended execution of a networked script, which can bypass user expectations and expand the skill's operational footprint.

Vague Triggers

Medium
Confidence
97% confidence
Finding
Using the single trigger phrase "news" is overly broad and can cause accidental invocation during ordinary conversation, causing the agent to run the skill when the user did not intend it. Because this skill launches a script with network behavior, over-triggering can lead to unnecessary external requests and reduced user control over agent actions.

Natural-Language Policy Violations

Medium
Confidence
95% confidence
Finding
This code embeds Chinese-only user-facing text such as '暂无摘要', and later formats all status/output strings in Chinese. The policy requires avoiding forced language/locale behavior unless the user is given an opt-in choice or the locale restriction is clearly documented and justified.

Natural-Language Policy Violations

Medium
Confidence
98% confidence
Finding
The function returns and formats all end-user messages in Chinese, including date formatting like '%Y年%m月%d日' and labels such as '今日新闻摘要' and '数据来源'. Because the file provides no option to select another language and no documented justification for a Chinese-only experience, this is a natural-language policy violation.

Natural-Language Policy Violations

Low
Confidence
86% confidence
Finding
The documented output format is written in Chinese (for example, "今日新闻摘要", "来源", and "摘要") while the skill also advertises English trigger phrases like "news". Because no opt-in or language-selection behavior is described, this may violate language/locale policy expectations by imposing a specific locale on users.

Static analysis

No suspicious patterns detected.