Back to skill

Security audit

Cook Like Hoc

Security checks for vulnerabilities and agentic risk

Overview

This recipe skill mostly does what it says, but it can silently send an existing GitHub token from the user's environment while fetching public recipe data.

Review before installing. This skill is not proven malicious, but users with a GITHUB_TOKEN in their environment should know it may be sent to GitHub automatically during recipe lookup. Prefer a version that removes ambient token use, narrows triggers to CookLikeHOC-specific requests, restricts indexed paths to recipe directories, and clearly treats remote Markdown as untrusted content.

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 (2)

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/search_recipe.py:29
Finding

Automatic Transmission of an Ambient GitHub Credential

Content
View full analysis

Vulnerability Details

File Location: scripts/search_recipe.py, lines 29-31
Vulnerability Type: Unnecessary credential exposure and violation of least privilege
Risk Level: Medium

Vulnerable Code

python
# Add optional Github token if available in env to increase limits
if os.environ.get('GITHUB_TOKEN'):
    req.add_header('Authorization', f"token {os.environ.get('GITHUB_TOKEN')}")

Technical Analysis

The script automatically reads the ambient GITHUB_TOKEN environment variable and attaches it to a request sent to https://api.github.com. The declared recipe-search functionality only accesses a public repository and does not require authentication.

Automatically consuming a general-purpose credential solely to increase rate limits exceeds the minimum privileges required by the Skill. The user is not asked to authorize use of the token, and the code does not verify that it is a dedicated, minimally scoped credential.

The request is sent over HTTPS to GitHub's official API, and no malicious exfiltration endpoint was identified. Nevertheless, the credential may become visible to trusted network intermediaries, debugging infrastructure, HTTP instrumentation, or a compromised certificate/proxy environment. Its effective exposure depends on the runtime's network configuration and the token's permissions.

Attack Path

  1. A user or hosting environment places a GitHub token in GITHUB_TOKEN for an unrelated workflow.
  2. The user invokes the recipe-search Skill.
  3. If the local cache is absent or older than 24 hours, fetch_file_list() creates a GitHub API request.
  4. The script silently reads the ambient token and inserts it into the Authorization header.
  5. The credential is transmitted even though the requested repository data is public.
  6. A compromised proxy, TLS trust configuration, diagnostic system, or request logger capable of observing headers could capture the credential.

...[truncated 676 chars]

Remediation
View remediation

Remediation Suggestions

  1. Remove automatic use of GITHUB_TOKEN; public repository metadata should be retrieved anonymously by default.
  2. If authenticated access is necessary, require an explicit command-line option or a Skill-specific variable such as COOKLIKEHOC_GITHUB_TOKEN.
  3. Inform the user before transmitting a credential and document the exact destination and purpose.
  4. Require a fine-grained, read-only token restricted to the single public repository and metadata access.
  5. Read the environment variable once and avoid exposing it through exceptions or diagnostic output.
  6. Prefer relying on the bundled cache or a pinned local index to avoid unnecessary authenticated API requests.
  7. Ensure network proxies and request logging systems redact Authorization headers.

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/search_recipe.py:38
Finding

Overbroad Retrieval and Emission of Mutable Remote Markdown

Content
View full analysis

Vulnerability Details

File Location: scripts/search_recipe.py, lines 38-43; related retrieval and output at lines 56-63 and 99-101
Vulnerability Type: Insufficient validation of remotely sourced content
Risk Level: Medium

Vulnerable Code

python
recipes = {}
for item in data.get('tree', []):
    path = item.get('path', '')
    if path.endswith('.md') and '/' in path and 'README.md' not in path:
        filename = path.split('/')[-1]
        recipe_name = filename.replace('.md', '')
        recipes[recipe_name] = path

The indexed path is later downloaded and emitted without category or content validation:

python
def fetch_recipe_content(path):
    url = RAW_BASE_URL + urllib.parse.quote(path)
    try:
        req = urllib.request.Request(url)
        req.add_header('User-Agent', 'Mozilla/5.0')
        with urllib.request.urlopen(req) as response:
            return response.read().decode('utf-8')
    except Exception as e:
        return f"Error fetching recipe content: {e}"
python
path = recipes[best_match]
print(f"=== {best_match} ===")
content = fetch_recipe_content(path)
print(content)

Technical Analysis

The repository tree filter accepts every nested Markdown file except files whose path contains README.md. It does not restrict matches to the recipe directories declared in SKILL.md.

The bundled scripts/recipe_tree_cache.json confirms that non-recipe content is already indexed:

json
"development": "docs/development.md"

Consequently, documentation and any future nested Markdown files can be treated as recipes. Content is then downloaded through jsDelivr from the mutable main branch and printed without path normalization, directory allowlisting, content-type checks, response-size limits, or recipe-format validation.

This is not remote code execution: the downloaded Markdown is printed rather than executed. No actua ...[truncated 1827 chars]

Remediation
View remediation

Remediation Suggestions

  1. Allowlist the documented recipe directories, such as 主食/, 炒菜/, 汤/, 炖菜/, 炸品/, 烤类/, 烫菜/, 煮锅/, 砂锅菜/, 蒸菜/, 配料/, and 饮品/.
  2. Explicitly reject docs/, hidden directories, unexpected nesting, and paths outside the allowlist.
  3. Normalize and validate each repository path before storing or using it.
  4. Pin both the repository-tree request and content download to a reviewed commit hash instead of mutable main.
  5. Verify that fetched content has a reasonable size and expected Markdown or text content type before reading it.
  6. Apply a strict download-size limit to prevent excessive memory consumption.
  7. Validate expected recipe structure, such as recognized ingredient and preparation sections.
  8. Clearly delimit remote content and instruct the integrating agent to treat it only as quoted recipe data, never as operational instructions.
  9. Remove the existing development entry from the bundled cache and regenerate the cache using the restricted directory policy.
  10. Consider bundling reviewed recipes locally when freshness is less important than integrity.
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • 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
Findings (8)

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
89% confidence
Finding

The skill instructs the agent to execute a local Python script that can access environment data, local files, and the network, but it declares no explicit tool restrictions or permission scope. This creates an unnecessary trust gap: if the script is modified, replaced, or behaves unexpectedly, the agent may invoke capabilities broader than the user would reasonably expect from a recipe lookup skill.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The trigger phrases include very broad terms such as '做菜' and general recipe-seeking language, which can cause the skill to activate for many unrelated cooking requests. Unintended invocation increases the chance that the agent runs local code or fetches repository-backed content when the user did not specifically ask for this source, creating unnecessary execution and content-trust risk.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
85% confidence
Finding

The description states the skill contains recipes from the Chinese-language source "老乡鸡菜品溯源报告" and elsewhere centers Chinese recipe names, but it does not explicitly offer a language choice or explain how to handle users who prefer another language. This can create a locale/language policy issue if the skill defaults to a specific language without user opt-in.

Content

No source excerpt is available for this finding.

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · scripts/search_recipe.py (reported line 10)May include surrounding context.

python
import os
import time

TREE_API_URL = "https://api.github.com/repos/Gar-b-age/CookLikeHOC/git/trees/main?recursive=1"
# 使用 jsDelivr 官方 CDN 替换原版 raw.githubusercontent.com 
# 以保障中国大陆等网络较差情况的直连获取速度稳定
RAW_BASE_URL = "https://fastly.jsdelivr.net/gh/Gar-b-age/CookLikeHOC@main/"

Context-Inappropriate Capability

Medium
Category
Not specified by scanner
Confidence
91% confidence
Finding

The script reads a GitHub token from the environment and uses it for a recipe lookup feature, which is a broader credential-handling capability than the skill appears to require. Even though the destination is GitHub’s API, automatically consuming ambient credentials increases the risk of unintended token disclosure or misuse in a low-trust, networked skill context.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The code transmits an environment-derived GitHub token in an Authorization header to an external service without any disclosure or consent mechanism. In an agent skill, this is dangerous because users or operators may not expect a simple recipe search tool to exfiltrate locally available credentials, and any compromise, logging, or redirection in that path could expose the token.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
82% confidence
Finding

This manifest-style JSON is largely composed of Chinese dish names and paths, but also includes the English key/value pair "development": "docs/development.md". Because SQP-3 applies to all file types and covers language/locale policy, this file appears to assume mixed locale behavior without any accompanying natural-language indication that users can choose language or that the locale constraint is intentional.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
76% confidence
Finding

The natural-language comments justify a network endpoint selection based on a specific region rather than presenting it as a user-selectable option. This can be interpreted as a locale-oriented policy choice embedded in the skill without explicit opt-in or documented regional scope.

Content

No source excerpt is available for this finding.

Static analysis

No suspicious patterns detected.