Back to skill

Security audit

会议纪要助手

Security checks for vulnerabilities and agentic risk

Overview

The skill matches its meeting-notes purpose, but it can modify the local environment, send sensitive meeting content to cloud speech services by default, and generate unsafe HTML output.

Review before installing. Use it only if you are comfortable with local package installation, persistent meeting files, and cloud speech providers receiving meeting text or recordings. For confidential meetings, require an explicit local-only mode, pinned dependencies, no runtime installs, safer HTML escaping, and clear retention controls before use.

Vulnerability Patterns
  • 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
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
Findings (3)

T09 · Insecure Skill Coding Practices

Error
Location
scripts/vendor/generate_mindmap_clawhub.py:2382
Finding

Stored Script Injection in Generated Mind-Map HTML

Content
View full analysis
` element. In particular, a string containing `` can terminate the surrounding script element because HTML parsing recognizes that sequence before JavaScript or JSON parsing occurs. The meeting wrapper derives the title and node labels from user-provided meeting topics and minutes. Consequently, malicious content can reach the vulnerable renderer and be persisted in the generated HTML file. ### Attack Path 1. An attacker supplies a crafted meeting topic or transcript containing a payload such as: ```html ``` 2. `scripts/generate_meeting_mindmap.py` extracts ...[truncated 1237 chars]
Remediation
View remediation
... ``` Parse it using: ```javascript const raw = JSON.parse(document.getElementById("mindmap-data").textContent); ``` 3. Before embedding JSON in HTML, neutralize characters significant to the HTML parser: ```python def safe_json_for_html(value): return ( json.dumps(value, ensure_ascii=False) .replace("&", "\\u0026") .replace("<", "\\u003c") .replace(">", "\\u003e") .replace("\u2028", "\\u2028") .replace("\u2029", "\\u2029") ) ``` 4. Avoid generic placeholder replacement for mixed HTML and JavaScript contexts. Use a template engine with automatic HTML escaping and an explicit safe-JSON helper. 5. Add a restrictive Content Security Policy to generated HTML, avoiding `unsafe-inline` where practical. 6. Add regression tests using titles and node labels containing: - `` - `` - Quotes and backslashes - Ampersands and angle brackets - U+2028 and U+2029 ]]>

other

Warning
Location
scripts/audio_bridge.py:758
Finding

Automatic Cloud Disclosure of Sensitive Meeting Content

Content
View full analysis
tuple[str, Path]: api_key = os.getenv("OPENAI_API_KEY") if not api_key: raise RuntimeError("OPENAI_API_KEY is not set") model = os.getenv("OPENAI_TTS_MODEL", "gpt-4o-mini-tts") chosen_voice = voice or os.getenv("OPENAI_TTS_VOICE", "alloy") out_mp3 = out_prefix.with_suffix(".mp3") payload = { "model": model, "voice": chosen_voice, "input": text_file.read_text(encoding="utf-8"), "format": "mp3", } data = post_json( "https://api.openai.com/v1/audio/speech", openai_headers(api_key, "application/json"), payload, ) out_mp3.write_bytes(data) return chosen_voice, out_mp3 ``` Edge TTS transmits the text through the `edge_tts` service: ```python async def _run(voice_name: str) -> None: import edge_tts # type: ignore text = text_file.read_text(encoding="utf-8") communicate = edge_tts.Communicate(text=text, voice=voice_name) await communicate.save(str(out_mp3)) ``` OpenAI ASR uploads the complete audio file: ```python def openai_asr(audio_file: Path, language: str | None) -> dict: api_key = os.getenv("OPENAI_API_KEY") if not api_key: raise RuntimeError("OPENAI_API_KEY is not set") model = os.getenv("OPENAI_ASR_MODEL", "gpt-4o-mini-transcribe") fields = {"model": model} if language: fields["language"] = language data = post_multipart( "https://api.openai.com/v1/audio/transcriptions", {"Authorization": f"Bearer {api_key}"}, ...[truncated 2685 chars]
Remediation
View remediation
edge -> openai` - ASR: `local -> builtin`, with no cloud fallback unless explicitly authorized. 2. Add a strict local-only option: ```text --local-only ``` When enabled, the program must fail closed rather than silently switching to Edge or OpenAI. 3. Require explicit cloud consent before transmission. The prompt should identify: - Provider name. - Destination. - Whether text or audio will be transmitted. - Whether the complete file or only a reduced excerpt will be sent. 4. Separate provider selection from fallback. For example, require `--allow-cloud-fallback` before an automatic route may use any network-backed service. 5. Display the selected provider before uploading data rather than only reporting it after success. 6. Minimize transmitted content: - Send only the briefing text for TTS. - Do not generate or upload full-text audio unless expressly requested. - Where supported, split or redact recordings before cloud transcription. 7. Document applicable retention, privacy, and data-processing considerations for each provider. 8. Add tests verifying that `--local-only` produces no outbound connections even when local providers fail. ]]>

T08 · Insecure Dependencies

Warning
Location
scripts/vendor/generate_mindmap_clawhub.py:25
Finding

Automatic Installation of Unpinned Third-Party Dependencies

Content
View full analysis
/dev/null 2>&1; then echo "[ACTION] Installing ffmpeg (required for m4a/mp3/aac/mp4 ASR)..." if ! brew install ffmpeg; then ``` ```bash if [[ "$MODE" == "all" || "$MODE" == "tts" || "$MODE" == "asr" ]]; t ...[truncated 2952 chars]
Remediation
View remediation
Vulnerability Patterns
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • 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
  • Behavioral ASTexec() Call, eval() Call, Dynamic Import
Findings (55)

Tp4

High
Category
MCP Tool Poisoning
Confidence
97% confidence
Finding

This mismatch is more security-relevant because it includes undeclared package installation via pip and interactive tooling outside the described meeting-processing scope. Hidden installation behavior can pull remote code or alter the local environment without clear user consent, which is risky in a skill expected to summarize meetings.

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
90% confidence
Finding

This mismatch is more security-relevant because it includes undeclared package installation via pip and interactive tooling outside the described meeting-processing scope. Hidden installation behavior can pull remote code or alter the local environment without clear user consent, which is risky in a skill expected to summarize meetings.

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
97% confidence
Finding

This mismatch is more security-relevant because it includes undeclared package installation via pip and interactive tooling outside the described meeting-processing scope. Hidden installation behavior can pull remote code or alter the local environment without clear user consent, which is risky in a skill expected to summarize meetings.

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding

This mismatch is more security-relevant because it includes undeclared package installation via pip and interactive tooling outside the described meeting-processing scope. Hidden installation behavior can pull remote code or alter the local environment without clear user consent, which is risky in a skill expected to summarize meetings.

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding

This mismatch is more security-relevant because it includes undeclared package installation via pip and interactive tooling outside the described meeting-processing scope. Hidden installation behavior can pull remote code or alter the local environment without clear user consent, which is risky in a skill expected to summarize meetings.

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
99% confidence
Finding

This mismatch is more security-relevant because it includes undeclared package installation via pip and interactive tooling outside the described meeting-processing scope. Hidden installation behavior can pull remote code or alter the local environment without clear user consent, which is risky in a skill expected to summarize meetings.

Content

No source excerpt is available for this finding.

Env Variable Harvesting

High
Category
Data Exfiltration
Confidence
60% confidence
Finding

Code enumerates, copies, or searches environment variables for secrets. Bulk environment access can collect credentials unrelated to the skill's stated purpose.

Content

Scanner excerpt · scripts/audio_bridge.py (reported line 237)May include surrounding context.

python
def run(cmd: list[str], env: dict[str, str] | None = None) -> subprocess.CompletedProcess:
    merged_env = os.environ.copy()
    if env:
        merged_env.update(env)
    return subprocess.run(cmd, check=False, text=True, capture_output=True, env=merged_env)

Context-Inappropriate Capability

High
Category
Not specified by scanner
Confidence
99% confidence
Finding

A meeting-notes/mind-map generator should not self-install Python packages during execution. This behavior is risky in agent environments because it creates an undeclared supply-chain and system-modification capability, enabling remote package retrieval and arbitrary code introduced through dependency installation hooks.

Content

No source excerpt is available for this finding.

YARA rule 'agent_skill_mcp_tool_poisoning_metadata': MCP/tool metadata poisoning indicators in tool schemas or skill manifests [agent_skills]

High
Category
YARA Match
Confidence
80% confidence
Finding

YARA rule matched a hack tool or exploit indicator (offensive tools, reconnaissance, privilege escalation, or exploit frameworks).

Content

Scanner excerpt · scripts/vendor/generate_mindmap_clawhub.py (reported line 134)May include surrounding context.

python
�─────────────────────────────────
# CLI
# ─────────────────────────────────────────────────────────────────────────────
def parse_args():
    p = argparse.ArgumentParser(
        description="OpenClaw Mind Map Generator — cross-platform (macOS / Linux / Windows)"
    )
    p.add_argument("--title",   required=True,  help="Mind map title")
    p.add_argument("--output",  default=None,   help="Output file path (default: ~/.openclaw/workspace/mindmap_<ts>.<ext>)")
    p.add_argument("--data",    required=True,  help="JSON string describing the mind map structure")
    p.add_argument("--format",  default="html",
                   choices=["html","svg","png","jpg","pdf","xmind"],
                   help="Output format (default: html)")
    p.add_argument("--scale",   typ

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
97% confidence
Finding

The skill instructs the agent to use shell, file writes, environment variables, and potentially networked package installation, but the manifest declares no explicit tool scope or permission boundaries. In a skill that handles sensitive meeting data and can auto-run diagnostic/install scripts, this creates excessive implicit authority and weakens reviewability, making unintended command execution, data persistence, or dependency fetching more dangerous.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The trigger phrases are broad enough to match ordinary conversation about meetings, audio, summaries, or brainstorming, which raises the chance of unintended activation. Because the skill can write files, run shell commands, and initiate ASR/TTS workflows, accidental invocation may expose or persist sensitive meeting content without a clear user request.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
97% confidence
Finding

The skill mandates writing outputs to a persistent private directory for meeting notes, audio, and mind maps without a clear user-facing warning or consent flow. Meeting data is often confidential, so automatic persistence materially increases the risk of unauthorized later access, retention beyond necessity, and mismatch with user expectations about ephemeral processing.

Content

No source excerpt is available for this finding.

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
92% confidence
Finding

The skill simultaneously limits final deliverables to three files while requiring ASR transcript artifacts to be retained, creating ambiguity around data retention. In the context of sensitive meeting recordings and transcripts, unclear retention rules can cause unintended storage of confidential content beyond what users expect.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The skill defaults to converting meeting text into audio even when the user did not explicitly request speech output, without a privacy warning. This increases the risk of sensitive meeting content being transformed into additional persistent artifacts and potentially routed through external TTS providers, expanding exposure beyond the original user intent.

Content

No source excerpt is available for this finding.

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
98% confidence
Finding

Lines L107-L110 state that Action Items with missing owner or deadline must block a completed output and force a DRAFT_PENDING state. But lines L214-L215 later instruct filling missing owners/dates with placeholders like 待指定 and 待确认, which directly contradicts the earlier prohibition on those values.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

Natural-language policy review applies to all file types. These lines set the default voice to zh-CN-XiaoxiaoNeural, which imposes a specific language/locale choice for generated speech without stating that the user can choose or consent to another locale first.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

These lines require a fixed provider and zh-CN-XiaoxiaoNeural voice across models, reinforcing a locale-specific output policy. The instructions do not present this as an optional default or solicit the user's preferred language/locale, so it constitutes a natural-language locale policy violation.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
98% confidence
Finding

The default prompt forces the first interaction to be in Chinese regardless of the user's language preference. While this is not a classic code-execution issue, it can mislead users, impair informed consent, and increase the chance that they approve installation or processing steps they do not fully understand, especially since the prompt also instructs the agent to present environment status and install commands up front.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The skill enables allow_implicit_invocation without any visible trigger constraints, so the platform may invoke it based on loosely matched user intent rather than an explicit user request. Because this skill can drive ASR/TTS workflows, installation guidance, and script execution, unintended invocation increases the chance of surprising actions, privacy issues around meeting content, and unnecessary exposure to local tooling or external services.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The template is written entirely in Chinese and prescribes section headings and output structure in Chinese, which implies a fixed language requirement for generated content. The file does not provide user opt-in, multilingual alternatives, or justification that this is a region-specific template, creating a natural-language locale policy concern.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The checklist hard-codes Chinese-centric output conventions and terminology without indicating that output language should follow explicit user preference. In a meeting-notes skill, this can override user intent, cause unwanted disclosure through translation or reformulation, and degrade usability or compliance in multilingual or regulated contexts.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

The smoke test hard-codes --language zh, which imposes a specific language/locale behavior on users regardless of their audio content or preferences. The file does not offer an opt-in, configurable default, or a documented region-specific justification for this constraint.

Content

No source excerpt is available for this finding.

subprocess module call

Medium
Category
Dangerous Code Execution
Confidence
70% confidence
Finding

subprocess module calls execute external commands. Without careful input validation, this enables command injection.

Content

Scanner excerpt · scripts/audio_bridge.py (reported line 240)May include surrounding context.

python
merged_env = os.environ.copy()
    if env:
        merged_env.update(env)
    return subprocess.run(cmd, check=False, text=True, capture_output=True, env=merged_env)


def print_install_steps(mode: str) -> None:

Context-Inappropriate Capability

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The skill can automatically invoke a bootstrap shell script to install system and Python dependencies when --auto-install is enabled. For a meeting-notes/audio-processing skill, executing installation scripts and modifying the host environment exceeds core functionality and creates a significant supply-chain and host-integrity risk, especially because it runs a local shell script with inherited environment and potentially broad user privileges.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
93% confidence
Finding

The built-in ASR locale candidates default to "zh-CN", and elsewhere the TTS voice selection is hard-coded to Chinese voices by default. This imposes a specific language/locale behavior on users unless they explicitly override it, which matches the policy-violation category for forced language/locale selection.

Content

No source excerpt is available for this finding.

Static analysis

No suspicious patterns detected.