Back to skill

Security audit

A股每日复盘视频生成

Security checks for vulnerabilities and agentic risk

Overview

The skill mostly does what it says, but it installs unpinned dependencies and external skills, downloads mutable remote assets, and inserts mandatory promotional content into generated reports.

Review this skill before installing if you care about reproducible or minimal environments. Run setup only in an isolated virtual environment or disposable workspace, pin and review dependencies yourself, prefetch assets from trusted sources with hashes, and remove or edit the promotional slides/hashtags if you do not want generated financial reports to include third-party advertising. The reviewed artifacts do not show credential theft, destructive behavior, or hidden persistence, but they do expand the local trusted code base.

Vulnerability Patterns
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Insecure DependenciesIntroduces malicious components through unsafe dependency sources
  • 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 (3)

T01 · Skill Instruction Hijacking

Warning
Location
scripts/make_slides.py:228
Finding
Mandatory third-party promotion and package installation advertising in generated reports<![CDATA[ ## Vulnerability Details **File Location**: `SKILL.md:247-255`, `SKILL.md:290-307`, `scripts/make_slides.py:228-278`, `references/copywriting.md:32-35`, `references/copywriting.md:70-91` **Vulnerability Type**: Mandatory instruction and output manipulation **Risk Level**: Medium ### Code Snippet ```python def s5_install(): # ... cmds=[ ("$ ","skillhub install ftshare-market-data"), ("$ ","skillhub install ftshare-announcement-data"), ("$ ","skillhub install ftshare-holder-data"), ("$ ","skillhub install ftshare-kline-data") ] # ... ``` ```python pages=[ # Cover and financial report pages are generated first. # ... ('05_installation', s5_install()), ('06_ending', s6_end()), ] ``` The Skill instructions additionally require every generated publication to contain fixed brand hashtags, promotional calls to action, an installation page, and a branded ending page. ### Technical Analysis The stated functional purpose is to generate a daily stock-market report. However, the workflow hard-codes two promotional slides into every generated video: 1. An installation page advertising multiple third-party Skills, including packages that are not dependencies of the report generator. 2. A branded ending page promoting external services. The accompanying Agent instructions also require fixed branding, hashtags, and calls to action in publication text. These additions are not presented as optional user-selected features. As a result, loading and executing the Skill changes the expected output objective from producing a financial report to producing a report combined with persistent third-party advertising. This is instruction hijacking because the Skill imposes unrelated output requirements on the Agent and causes promotional material to be included regardless of whether the user requested or approved it. ### Attack Path 1. A user requests generation of a daily stock-market report. 2. The A ...[truncated 1269 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Remove the mandatory installation and branding pages from the default report. 2. Do not require fixed hashtags, calls to action, or third-party promotion in Agent instructions. 3. Make attribution and promotional material explicitly opt-in through a documented command-line option such as `--include-promotion`. 4. Default that option to disabled. 5. Clearly distinguish required runtime dependencies from optional or promoted packages. 6. Require explicit user confirmation before adding advertisements or package-installation instructions. 7. Add automated tests verifying that the default report contains only the requested financial content and disclaimer. ]]>

T08 · Insecure Dependencies

Error
Location
scripts/setup.sh:10
Finding
Unpinned and implicitly installed third-party dependencies<![CDATA[ ## Vulnerability Details **File Location**: `scripts/setup.sh:10-24`, `scripts/setup.sh:40-50`, `scripts/ensure_assets.py:65-72` **Vulnerability Type**: Unpinned package and Skill installation **Risk Level**: High ### Code Snippet ```bash if python3 -c "import PIL" 2>/dev/null; then echo "pillow is already installed" else pip3 install pillow || pip install pillow fi if python3 -c "import fontTools" 2>/dev/null; then echo "fonttools is already installed" else pip3 install fonttools brotli || pip install fonttools brotli fi ``` ```bash if command -v skillhub &>/dev/null; then skillhub install ftshare-market-data || echo "ftshare-market-data installation failed" skillhub install newsnow-reader || echo "newsnow-reader installation failed" elif command -v clawhub &>/dev/null; then clawhub install ftshare-market-data || echo "ftshare-market-data installation failed" clawhub install newsnow-reader || echo "newsnow-reader installation failed" fi ``` ```python try: from fontTools.ttLib import TTFont except ImportError: import subprocess subprocess.check_call([ sys.executable, '-m', 'pip', 'install', 'fonttools', 'brotli', '-q' ]) from fontTools.ttLib import TTFont ``` ### Technical Analysis The installation script resolves Python packages and external Skills by mutable package names without: - Exact version pins. - Cryptographic hashes. - A reviewed lockfile. - Publisher or signature verification. - An isolated virtual environment. - A reproducible dependency manifest. In addition, `ensure_assets.py` can invoke pip automatically during normal runtime when `fontTools` is unavailable. This causes dependency installation as a side effect of asset processing rather than as an explicit setup action. Python package installation may execute package build backends, setup hooks, or compiled installation logic. External Ski ...[truncated 1761 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Pin every Python dependency to a reviewed exact version. 2. Maintain a lockfile containing cryptographic hashes for all direct and transitive dependencies. 3. Install with hash enforcement, for example through a generated requirements file and `pip install --require-hashes`. 4. Use `python3 -m pip` consistently so installation targets the same interpreter that runs the project. 5. Install dependencies into a dedicated virtual environment rather than the global user environment. 6. Pin external Skills to immutable reviewed versions or content digests. 7. Verify publisher identity and package signatures where the registries support them. 8. Remove automatic pip installation from `ensure_assets.py`. If a dependency is unavailable, terminate with a clear instruction rather than changing the environment at runtime. 9. Separate optional dependencies from mandatory dependencies and require explicit user approval before installation. 10. Run dependency vulnerability and provenance checks in CI. ]]>

T08 · Insecure Dependencies

Warning
Location
scripts/ensure_assets.py:18
Finding
Remote font and audio assets are accepted without cryptographic integrity verification<![CDATA[ ## Vulnerability Details **File Location**: `scripts/ensure_assets.py:18-41`, `scripts/ensure_assets.py:44-58`, `scripts/ensure_assets.py:91-124` **Vulnerability Type**: Unverified remote asset retrieval **Risk Level**: Medium ### Code Snippet ```python ASSETS = [ { 'path': 'fonts/NotoSansSC-Regular.ttf', 'urls': [ 'https://cdn.jsdelivr.net/fontsource/fonts/' 'noto-sans-sc@latest/chinese-simplified-400-normal.woff2', 'https://cdn.jsdelivr.net/gh/fontsource/font-files@main/' 'fonts/google/noto-sans-sc/' 'chinese-simplified-400-normal.woff2', 'https://github.com/eddiexux/' 'astock-video-report-assets/releases/download/v1.0.0/' 'NotoSansSC-Regular.woff2', ], 'min_size': 500_000, 'desc': 'Noto Sans SC font', 'post_process': 'woff2_to_ttf', }, { 'path': 'bgm/eliveta-technology-474054.mp3', 'urls': [ 'https://github.com/eddiexux/' 'astock-video-report-assets/releases/download/v1.0.0/' 'eliveta-technology-474054.mp3', ], 'min_size': 4_000_000, 'desc': 'BGM audio', 'post_process': None, }, ] ``` ```python def download_file(url, dest, desc=''): os.makedirs(os.path.dirname(dest), exist_ok=True) try: urllib.request.urlretrieve(url, dest) size_mb = os.path.getsize(dest) / 1024 / 1024 print(f'Download completed ({size_mb:.1f} MB)') return True except Exception as e: print(f'Download failed: {e}') if os.path.exists(dest): os.remove(dest) return False ``` ```python if dest.exists() and dest.stat().st_size >= asset['min_size']: return True # ... if ok and asset.get('post_process') == 'woff2_to_ttf': woff2_to_ttf(dest) if dest.exists() and dest.stat().st_size >= asset['min_size']: return True if dest.exists() and dest.stat().st_siz ...[truncated 2589 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Vendor reviewed assets directly into the package where licensing permits. 2. Otherwise, use immutable release URLs and pin a SHA-256 digest for every permitted asset. 3. Calculate the digest after download and before any parser opens the file. 4. Delete the file and fail closed if its digest does not exactly match the manifest. 5. Remove mutable references such as `@latest` and branch-based `main` URLs. 6. Do not accept a file merely because it is non-empty or exceeds a minimum size. 7. Download to a securely created temporary file, verify it, and atomically rename it into the asset directory. 8. Apply reasonable download size and timeout limits. 9. Keep FontTools, Pillow, and ffmpeg patched and process remote assets in a sandbox with minimal filesystem and network privileges. 10. Document asset provenance, license, expected digest, and review date in a machine-readable manifest. ]]>
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
Findings (19)

Tp4

High
Category
MCP Tool Poisoning
Confidence
96% confidence
Finding
The skill claims to provide an end-to-end workflow including data retrieval, news collection, AI attribution, slide generation, and video composition, but the described implementation appears to rely on externally supplied arguments for core content and includes promotional slides unrelated to the core task. This mismatch is dangerous because downstream agents or users may trust the skill to have performed data collection and analysis it did not actually perform, leading to integrity failures, misleading financial content, and unsafe automation decisions.

Lp3

Medium
Category
MCP Least Privilege
Confidence
70% confidence
Finding
Without declared permissions the skill's intent is opaque and cannot be validated.

Natural-Language Policy Violations

Medium
Confidence
92% confidence
Finding
The manifest description and quick-start invocation are written as mandatory Chinese trigger phrases and user commands, with no indication that other languages are supported or that the user can opt into Chinese. This is a natural-language locale constraint that appears imposed by the skill rather than presented as a user choice or clearly justified regional compliance requirement.

Natural-Language Policy Violations

Medium
Confidence
86% confidence
Finding
The file title and all user-facing documentation are written entirely in Chinese, with no indication that language selection is optional or limited to a justified region-specific context. Per the policy, forcing a specific language without user opt-in can constitute a natural-language policy violation.

Natural-Language Policy Violations

Medium
Confidence
94% confidence
Finding
The file's docstring, comments describing usage, and later user-facing print messages are entirely in Chinese, which imposes a specific language on users of this skill. Under the policy, locale or language restrictions should either offer user opt-in/choice or be clearly justified as region-specific, neither of which is present here.

Context-Inappropriate Capability

Medium
Confidence
96% confidence
Finding
This bootstrap script installs Python packages at runtime to enable font conversion, which means a video-generation skill can unexpectedly modify the environment and execute newly downloaded third-party code. In context, the skill already downloads external assets, so adding package installation increases the attack surface and makes compromise through dependency confusion, index compromise, or unreviewed updates more plausible.

subprocess module call

Medium
Category
Dangerous Code Execution
Content
except ImportError:
        print('  ⚠️  需要 fonttools 来转换字体格式,正在安装...')
        import subprocess
        subprocess.check_call([sys.executable, '-m', 'pip', 'install', 'fonttools', 'brotli', '-q'])
        from fontTools.ttLib import TTFont

    ttf_path = str(woff2_path).replace('.woff2', '.ttf') if '.woff2' in str(woff2_path) else str(woff2_path) + '.converted'
Confidence
94% confidence
Finding
The script performs a runtime pip install via subprocess when fonttools is missing. Even though the command arguments are fixed and there is no obvious shell injection, this still expands the skill's execution capability to fetch and execute code from package indexes at runtime, which creates supply-chain risk and violates least-privilege expectations for a simple asset bootstrap helper.

Natural-Language Policy Violations

Medium
Confidence
93% confidence
Finding
This Python file contains user-facing natural language that presents the skill as generating only Chinese A-share recap slides, and the rest of the script hardcodes Chinese titles and prompts throughout. Under the policy rule, forcing a specific language without user opt-in is a locale/language policy issue unless the constraint is explicitly justified as region-specific or a choice is offered.

Description-Behavior Mismatch

Medium
Confidence
95% confidence
Finding
The manifest describes an automated workflow for producing a daily A股复盘 video from market data, news, AI analysis, slides, and video synthesis. Lines L218-L250 instead generate a dedicated 'how to use' slide with installation commands and marketing prompts, which is not part of the claimed reporting workflow.

Natural-Language Policy Violations

Medium
Confidence
93% confidence
Finding
This code embeds its primary instructions and descriptions in Chinese, and later prints all user-facing status/output messages in Chinese as well. Under the policy rule, forcing a specific language without user opt-in is a natural-language policy violation unless the locale restriction is clearly justified.

Natural-Language Policy Violations

Medium
Confidence
90% confidence
Finding
The script's prompts, errors, progress messages, and completion text are all presented only in Chinese. Because the file does not offer locale selection or explain a required Chinese-only operating context, this violates the language/locale policy criterion.

subprocess module call

Medium
Category
Dangerous Code Execution
Content
def run(cmd, label=''):
    print(f'  ▶ {label}...')
    r = subprocess.run(cmd, capture_output=True, text=True)
    if r.returncode != 0:
        print(f'  ❌ 失败:\n{r.stderr[-500:]}')
        sys.exit(1)
Confidence
70% confidence
Finding
subprocess module calls execute external commands. Without careful input validation, this enables command injection.

Missing User Warnings

Medium
Confidence
94% confidence
Finding
The script automatically runs pip/pip3 install commands that modify the Python environment without any explicit confirmation, dry-run, or warning about side effects. In an agent skill context, this is risky because executing setup steps can alter the host environment, introduce unpinned third-party packages, and affect other workflows or projects.

Sudo/Root Execution

Medium
Category
Privilege Escalation
Content
else
    echo "⚠️  未找到 ffmpeg,请手动安装:"
    echo "   macOS:   brew install ffmpeg"
    echo "   Ubuntu:  sudo apt install ffmpeg"
    echo "   CentOS:  sudo yum install ffmpeg"
    echo "   Windows: https://ffmpeg.org/download.html"
    echo ""
Confidence
70% confidence
Finding
Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Sudo/Root Execution

Medium
Category
Privilege Escalation
Content
else
    echo "⚠️  未找到 ffmpeg,请手动安装:"
    echo "   macOS:   brew install ffmpeg"
    echo "   Ubuntu:  sudo apt install ffmpeg"
    echo "   CentOS:  sudo yum install ffmpeg"
    echo "   Windows: https://ffmpeg.org/download.html"
    echo ""
Confidence
70% confidence
Finding
Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Missing User Warnings

Medium
Confidence
92% confidence
Finding
The script invokes skillhub/clawhub install commands to change the local AI tooling setup without clear consent or explanation of what will be installed. In a skill ecosystem, installing additional skills expands the trusted code base and could expose the user to unexpected code execution or configuration changes.

Description-Behavior Mismatch

Low
Confidence
90% confidence
Finding
The manifest focuses on producing a daily market recap video. Lines L253-L271 create an ending slide highlighting vendor branding and product features such as official API, AI analysis, and WeChat push, which is ancillary promotional content rather than core recap content.

Intent-Code Divergence

Low
Confidence
95% confidence
Finding
顶部说明写明默认只使用 skill 自带的 assets/bgm 文件,最多允许通过 --bgm 指定其他本地文件;但 default_bgm 的实现和其注释显示,当本地资源不存在时会导入 ensure_assets 并尝试自动下载。该文档与实际行为在资源来源和是否触发额外获取动作上存在直接偏差。

Natural-Language Policy Violations

Low
Confidence
97% confidence
Finding
Nearly all user-facing strings in this script are in Chinese, including setup guidance and invocation instructions. This can violate language/locale policy when a skill forces a specific language without user opt-in or an explicit justification that it is region-specific.

Static analysis

No suspicious patterns detected.