Back to skill

Security audit

Content Claw

Security checks for vulnerabilities and agentic risk

Overview

This skill mostly matches its content-generation purpose, but it needs Review because it can fetch arbitrary URLs, write generated files from user-controlled names, and includes a Reddit prompt designed to make AI-written content look like organic human testimony.

Install only after reviewing the Reddit agent and disabling or rewriting it for transparent, fact-backed drafts. Run URL extraction in a sandbox with restricted network access, avoid internal or sensitive URLs, use scoped API keys, prefer verified package installation with a lockfile, and validate brand and recipe names before allowing writes.

Vulnerability Patterns
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • Insecure DependenciesIntroduces malicious components through unsafe dependency sources
  • 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
Findings (7)

T03 · Remote Payload Retrieval and Execution

Error
Location
SKILL.md:53
Finding

Remote Installer Is Downloaded and Executed Without Integrity Verification

Content
View full analysis
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Error
Location
scripts/extractors/extract.py:17
Finding

Arbitrary Source URLs Permit Server-Side Request Forgery and Local-Network Access

Content
View full analysis
str: """Fetch a page's HTML using Playwright with stealth settings.""" from playwright.sync_api import sync_playwright with sync_playwright() as p: browser = p.chromium.launch( headless=True, args=[ "--disable-blink-features=AutomationControlled", "--no-sandbox", ], ) context = browser.new_context( user_agent="Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36", viewport={"width": 1280, "height": 800}, locale="en-US", ) page = context.new_page() page.add_init_script("Object.defineProperty(navigator, 'webdriver', {get: () => undefined})") page.goto(url, wait_until="domcontentloaded", timeout=30000) ``` ```python resp = httpx.get( url, follow_redirects=True, timeout=60, headers={ "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/131.0.0.0 Safari/537.36", }, ) ``` ```python url = sys.argv[1] source_type = detect_type(url) extractors = { "web": extract_web, "pdf": extract_pdf, "reddit": extract_reddit, "twitter": extract_twitter, "github": extract_github, } extractor = extractors.get(source_type) ``` ### Technical Analysis The extractor accepts a user-controlled URL and sends it to Playwright or `httpx` without validating the scheme, hostname, resolved IP address, or redirect destination. It does not reject loopback, private, link-local, reserved, multicast, or cloud metadata addresses. The PDF path follows redirects automatically, but each r ...[truncated 1104 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Error
Location
SKILL.md:328
Finding

User-Controlled Recipe and Brand Names Can Escape the Declared Project Directory

Content
View full analysis
.yaml`. Tell the user: "Recipe saved. You can now run it with: `run `" ``` ```markdown Create YAML files in `BASE_DIR/brand-graphs//`: - `identity.yaml`: name, positioning, description, services - `audience.yaml`: who, interests, pain_points, stage - `strategy.yaml`: goals, niche_keywords - `visual.yaml`: primary_color, accent_color (if provided) - `feedback.yaml`: empty file with `insights: []` (populated over time) ``` The affected instructions conflict with the declared boundary: ```markdown This skill only reads and writes files within `BASE_DIR`. Do not read, write, or search files outside of `BASE_DIR`. ``` ### Technical Analysis Recipe slugs and brand names are incorporated into filesystem paths without a documented requirement to reject path separators, absolute paths, `.` components, or `..` traversal components. The host Agent is instructed to perform the writes with its `Write` or shell tools. A crafted value such as `../../target` could normalize outside the intended `recipes` or `brand-graphs` directories. The prose-only `BASE_DIR` restriction does not provide a technical boundary if the resulting path is not canonicalized and checked before use. ### Attack Path 1. A user requests creation of a recipe or brand with a name containing traversal components. 2. The Agent derives or retains an unsafe slug or brand name. 3. The unsafe value is interpolated into the documented output path. 4. The path resolves outside the intended project subdirectory and potentially outside `BASE_DIR`. 5. The Agent creates or overwrites files wherever its host filesystem permissions allow. ### Impact Assessment Successful exploitation may create or overwrite user-accessible files outsi ...[truncated 297 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/extractors/extract.py:20
Finding

Chromium Sandbox Is Disabled While Rendering Untrusted Pages

Content
View full analysis
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Note
Location
scripts/extractors/extract.py:88
Finding

Downloaded PDF Files Are Left Behind in Temporary Storage

Content
View full analysis
Remediation
View remediation

T08 · Insecure Dependencies

Warning
Location
pyproject.toml:6
Finding

Unpinned Dependencies Make Installations Non-Reproducible

Content
View full analysis
=0.27", "pymupdf>=1.24", "readabilipy>=0.2", "playwright>=1.49", "fal-client>=0.5", "exa-py>=1.0", ] [dependency-groups] dev = [ "pytest>=8.0", "pyyaml>=6.0", ] ``` Related installation instructions include: ```markdown - pip/pipx: `pipx install uv` ... After installing uv, run `uv sync` in the skill directory to install all Python dependencies. ``` ### Technical Analysis All dependencies use open-ended lower bounds. No reviewed lockfile was present in the audited directory. As a result, two users installing the same Skill at different times may receive different dependency versions, including future releases that were not part of this audit. The package names appear consistent with the imports, and no dependency-confusion or typosquatting package was confirmed. The issue is the lack of reproducibility and integrity controls, not proof that any listed package is currently malicious. ### Attack Path 1. A future release of a dependency or transitive dependency is compromised or malicious. 2. A user runs `uv sync` without an enforced reviewed lockfile. 3. The resolver selects the new release because it satisfies the open lower bound. 4. Malicious package installation or runtime code executes in the Skill environment. 5. The package receives the same process-level access as the Skill. ### Impact Assessment A compromised dependency could execute arbitrary Python code during installation, import, or runtime. It could access the declared API keys in the environment, source data processed by the Skill, project files, and network resources available to the process. The practical impact depends on the behavior of a compromised upstream package. ]]>
Remediation
View remediation

other

Warning
Location
agents/reddit-human.md:3
Finding

Reddit Agent Encourages Fabricated Human-Like Personal Testimony

Content
View full analysis
Remediation
View remediation
Vulnerability Patterns
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • System Prompt LeakageDirect Leakage, Indirect Extraction, Tool-Based Exfiltration
  • Rogue AgentSelf-Modification, Session Persistence
Findings (55)

Tp4

High
Category
MCP Tool Poisoning
Confidence
99% confidence
Finding

The declared description focuses on transforming content into publish-ready marketing assets and discovering/generating topics and images. This code does not perform content generation at all; its primary purpose is ingestion/extraction of source text from various online resources. While extraction could be a supporting step in a larger content pipeline, the supplied chunk itself implements undeclared scraping/extraction capabilities, including browser-based retrieval with bot-evasion measures, PDF downloading, and API-based GitHub retrieval. It also lacks the core declared behaviors: no Exa integration, no fal.ai calls, no social-post generation, no infographic/diagram creation, and no content recipe logic. Therefore the code chunk is materially mismatched with the declared purpose.

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding

The declared description focuses on generating publish-ready marketing/social content, trend discovery, and image creation. The actual code does none of that. Instead, it tests a content/source extraction pipeline that fetches and classifies URLs and validates returned JSON. This is a materially different primary purpose from the declared skill behavior. While extraction could hypothetically support a larger content workflow, this specific code chunk is centered on extractor testing and source parsing, which is not accurately represented by the declared description.

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding

The declared description focuses on runtime content creation and topic discovery capabilities, but the provided code chunk does not implement any of those behaviors. Instead, it performs offline validation/testing of recipe configuration files and agent file references. While recipe validation could be a supporting development detail in a larger content-generation system, this chunk’s actual primary purpose is test/schema enforcement rather than generating content, discovering topics, or creating images. Therefore, the supplied code does not accurately represent the declared end-user functionality.

Content

No source excerpt is available for this finding.

Self-Modification

High
Category
Rogue Agent
Confidence
93% confidence
Finding

This task explicitly plans for the agent/skill to author or rewrite its own SKILL.md, which is the instruction set governing future behavior. Self-modification of the skill definition is dangerous because it can let untrusted content, prompt injection from sources, or erroneous generations persistently alter agent behavior, expand capabilities, or weaken safety constraints. In a content-generation skill that ingests external web/PDF/social sources, this context makes the issue more dangerous because adversarial source material could influence durable instruction changes.

Content

Scanner excerpt · TODOS.md (reported line 17)May include surrounding context.

md
- **Effort:** S
- **Blocked by:** Recipe YAML schema.

### Write SKILL.md (core skill definition)
- **What:** Write the OpenClaw SKILL.md that teaches the agent the full Content Claw pipeline: recipe execution, brand graph wizard, recipe listing, error handling, all user commands.
- **Why:** This IS the product. The SKILL.md is the instruction set that makes the OpenClaw agent a content engine.
- **Effort:** M

Description-Behavior Mismatch

High
Category
Not specified by scanner
Confidence
98% confidence
Finding

This agent is materially out of scope for the declared skill purpose of creating publish-ready branded assets: it is optimized for covert Reddit participation disguised as an ordinary user. That mismatch increases risk because it suggests the capability is meant to bypass governance and use a benign manifest as cover for undisclosed social manipulation.

Content

No source excerpt is available for this finding.

Context-Inappropriate Capability

High
Category
Not specified by scanner
Confidence
99% confidence
Finding

The skill explicitly instructs the model to generate Reddit content that appears to have been written by a real person, which is deceptive impersonation rather than transparent assistance. In the context of a content-generation skill, this enables covert influence, astroturfing, and evasion of platform or user disclosure expectations.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

High
Category
Not specified by scanner
Confidence
99% confidence
Finding

The line 'reads like it was typed by a real person' is a direct instruction to impersonate a human author and conceal AI involvement. This is dangerous because it facilitates deceptive communication at scale, undermines trust, and can be used for undisclosed marketing, persuasion, or manipulation in public forums.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

High
Category
Not specified by scanner
Confidence
99% confidence
Finding

The repeated stylistic directives—intentional typos, meandering details, inconsistent capitalization, and other 'humanizing' artifacts—are deliberate deception techniques designed to evade detection as AI-generated or coordinated content. In a Reddit-focused agent, this materially increases the likelihood of covert influence operations and policy evasion.

Content

No source excerpt is available for this finding.

Lp1

High
Category
MCP Least Privilege
Confidence
75% confidence
Finding

The skill uses 'env' capability that is not listed in its permissions. This may indicate deceptive intent or missing permission declarations.

Content

No source excerpt is available for this finding.

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/discover_topics.py (reported line 12)May include surrounding context.

python
"""Scoped .env loader for Content Claw. Only loads declared keys."""

import os
from pathlib import Path

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/discover_topics.py (reported line 23)May include surrounding context.

python
"""Scoped .env loader for Content Claw. Only loads declared keys."""

import os
from pathlib import Path

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/env.py (reported line 1)May include surrounding context.

python
"""Scoped .env loader for Content Claw. Only loads declared keys."""

import os
from pathlib import Path

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

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

python
"""Scoped .env loader for Content Claw. Only loads declared keys."""

import os
from pathlib import Path

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/generate_image.py (reported line 12)May include surrounding context.

python
"""Scoped .env loader for Content Claw. Only loads declared keys."""

import os
from pathlib import Path

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/generate_image.py (reported line 209)May include surrounding context.

python
"""Scoped .env loader for Content Claw. Only loads declared keys."""

import os
from pathlib import Path

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/generate_image.py (reported line 249)May include surrounding context.

python
"""Scoped .env loader for Content Claw. Only loads declared keys."""

import os
from pathlib import Path

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/discover_topics.py (reported line 25)May include surrounding context.

python
def load_env(extra_keys: set[str] | None = None):
    """Load only allowed keys from .env into process environment."""
    allowed = ALLOWED_KEYS | (extra_keys or set())
    env_path = Path(__file__).parent.parent / ".env"
    if not env_path.exists():
        return
    for line in env_path.read_text().splitlines():

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/env.py (reported line 12)May include surrounding context.

python
def load_env(extra_keys: set[str] | None = None):
    """Load only allowed keys from .env into process environment."""
    allowed = ALLOWED_KEYS | (extra_keys or set())
    env_path = Path(__file__).parent.parent / ".env"
    if not env_path.exists():
        return
    for line in env_path.read_text().splitlines():

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/generate_image.py (reported line 251)May include surrounding context.

python
def load_env(extra_keys: set[str] | None = None):
    """Load only allowed keys from .env into process environment."""
    allowed = ALLOWED_KEYS | (extra_keys or set())
    env_path = Path(__file__).parent.parent / ".env"
    if not env_path.exists():
        return
    for line in env_path.read_text().splitlines():

Lp1

High
Category
MCP Least Privilege
Confidence
92% confidence
Finding

This extractor performs broad outbound network access to arbitrary user-supplied URLs via Playwright and httpx, but the capability is not declared or constrained. In an agent skill context, undeclared network access is risky because it can be used for SSRF-style access to internal resources, metadata endpoints, or unintended third-party transmission without clear user awareness.

Content

No source excerpt is available for this finding.

Direct Prompt Extraction

High
Category
System Prompt Leakage
Confidence
85% confidence
Finding

Skill contains instructions that could directly expose system prompts, internal rules, or hidden instructions to users or external parties.

Content

Scanner excerpt · scripts/generate_image.py (reported line 113)May include surrounding context.

python
f"\n\n{content_description}"
        )

    return prompt


FAL_MODELS = {

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
97% confidence
Finding

The trigger phrases are broad and overlap with ordinary user requests like 'generate content' or 'make a post from this.' In agent ecosystems with automatic skill routing, that can cause unintended invocation of a skill that performs external fetches, browser automation, file writes, and API-backed actions, expanding the attack surface without deliberate user intent.

Content

No source excerpt is available for this finding.

Session Persistence

Medium
Category
Rogue Agent
Confidence
76% confidence
Finding

The skill is explicitly designed to persist specs, generated content, metadata, topics, and brand graphs across runs using Write/Edit permissions. Persistent storage is not inherently malicious, but it does create privacy and integrity risks if sensitive source material, URLs, or derived metadata are retained longer than the user expects.

Content

Scanner excerpt · SKILL.md (reported line 31)May include surrounding context.

md
allowed-tools:
  - Bash
  - Read
  - Write
  - Edit
  - Glob
  - Grep

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

The skill claims it only accesses files within BASE_DIR, but instructs resolution of BASE_DIR by reading symlink targets under the user's home directory. Even limited metadata access outside the declared boundary weakens the trust model and can expose filesystem layout or resolve to an unexpected target if the symlink is tampered with. In a security-sensitive agent environment, boundary contradictions are dangerous because users may rely on the narrower scope guarantee.

Content

No source excerpt is available for this finding.

Autonomous Decision Making

Medium
Category
Excessive Agency
Confidence
88% confidence
Finding

Automatically running topic discovery after brand creation initiates external-network activity and data processing without a separate confirmation step. Because this uses Exa and brand-derived inputs, it can transmit user-provided business context externally and create unexpected side effects, especially if the user only intended to save configuration.

Content

Scanner excerpt · SKILL.md (reported line 424)May include surrounding context.

md
### Auto-discovery during brand creation

After completing the brand graph wizard (all 6 questions answered and files saved), automatically run topic discovery:

1. Tell the user: "Brand graph saved. Now discovering trending topics for <brand-name>..."
2. Run the topic discovery script with the new brand directory

Static analysis

No suspicious patterns detected.