Back to skill

Security audit

sjht doubao text to image

Security checks for vulnerabilities and agentic risk

Overview

This skill appears to be a real Doubao image generator, but it needs review because it handles an API key, sends prompts to an external service, and writes a preview page with a real HTML-injection flaw.

Install only if you are comfortable sending image prompts to Volcengine/Doubao and using an ARK API key. Prefer ARK_API_KEY from a protected environment over --api-key, avoid secrets or personal data in prompts, be cautious opening the generated index.html for prompts you did not fully control, and consider pinning dependencies before routine 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

Warning
Location
scripts/gen.py:61
Finding

Stored HTML Injection in the Generated Gallery

Content
View full analysis
Path: """生成图库预览 HTML""" html_items = "" for it in items: fname = it["file"] prompt_escaped = it["prompt"].replace("<", "<").replace(">", ">") html_items += f"""
{prompt_escaped}
{prompt_escaped}
{it.get('model','')} · {it.get('size','')} · {it.get('index','')}
""" ``` The accumulated markup is subsequently written directly to the gallery: ```python index_path = out_dir / "index.html" index_path.write_text(html, encoding="utf-8") ``` ### Technical Analysis The application attempts to sanitize the prompt by replacing only `<` and `>`. This is insufficient for an HTML attribute context because quotation marks and ampersands are not escaped. The prompt is placed inside the double-quoted `alt` attribute of an `` element, so an attacker-controlled quotation mark can terminate the attribute and introduce new attributes such as `onload`. The user-controlled `--model` value is also inserted directly into an HTML element without any escaping. If a supplied model string is accepted through the generation workflow, it can introduce arbitrary HTML elements or event handlers. This is a stored injection issue: the malicious input is persisted in `index.html` and becomes active when the generated gallery is opened in a browser. ### Attack Path 1. An attacker supplies or influences the image prompt passed to the Skill. 2. The prompt contains an attribute-break ...[truncated 1612 chars]
Remediation
View remediation
`, and event-handler payloads. 6. Consider adding a restrictive Content Security Policy to the generated page, such as one that disallows inline scripts and external network connections. ]]>

T09 · Insecure Skill Coding Practices

Note
Location
scripts/gen.py:213
Finding

API Key Exposure Through Command-Line Arguments

Content
View full analysis
str: """按优先级读取 API Key:CLI 参数 > 环境变量 > ~/.doubao-image-gen/.env""" if cli_key: return cli_key if key := os.environ.get("ARK_API_KEY"): return key env_file = Path.home() / ".doubao-image-gen" / ".env" if env_file.exists(): for line in env_file.read_text(encoding="utf-8").splitlines(): line = line.strip() if line.startswith("ARK_API_KEY="): return line.split("=", 1)[1].strip().strip('"').strip("'") return "" ``` The documentation repeatedly encourages passing the key on the command line: ```bash python {baseDir}/scripts/gen.py --prompt "赛博朋克风格的上海夜景" --api-key YOUR_KEY python {baseDir}/scripts/gen.py --prompt "水墨风格的山水画" --count 4 --api-key YOUR_KEY python {baseDir}/scripts/gen.py --prompt "星空下的草原" --size 2K --api-key YOUR_KEY python {baseDir}/scripts/gen.py --prompt "古风仙侠" --out-dir ./output --api-key YOUR_KEY ``` ### Technical Analysis Secrets supplied as command-line arguments can be exposed outside the Python process. Depending on the operating environment, complete command lines may be visible through: - Shell history files. - Process inspection tools and operating-system process metadata. - Agent or automation execution logs. - Terminal session recording. - Monitoring and diagnostic systems. The implementation does not print the key itself, but that does not protect the secret from command-line-level exposure. The ...[truncated 1420 chars]
Remediation
View remediation

T08 · Insecure Dependencies

Note
Location
SKILL.md:15
Finding

Unbounded and Incompletely Declared Third-Party Dependencies

Content
View full analysis
=1.0"` ``` The implementation imports that package at runtime and recommends the same unbounded installation command: ```python try: from openai import OpenAI except ImportError: print("请先安装 openai 库:pip install 'openai>=1.0'", file=sys.stderr) sys.exit(1) ``` A second runtime dependency is imported without being included in the setup command: ```python import requests as req_lib r = req_lib.get(url, timeout=60) ``` ### Technical Analysis The constraint `openai>=1.0` permits any future release satisfying the lower bound. There is no upper bound, lockfile, hash verification, or reviewed dependency snapshot. Installation may therefore select code that did not exist when the Skill was audited. The script also depends directly on `requests`, but the primary setup instructions do not install or pin it. It may currently be present transitively or already installed in a user's environment, but relying on that behavior produces non-reproducible deployments. Python packages and their transitive dependencies execute code in the local environment during installation and runtime. Open-ended resolution increases exposure to compromised future releases, malicious transitive dependency changes, and incompatible updates. No evidence indicates that the currently named packages are malicious; the issue is the unsafe dependency-management practice. ### Attack Path 1. A user follows the setup instruction and runs: ```bash pip install "openai>=1.0" ``` 2. The package resolver selects the latest matching release and its current transitive dependencies. ...[truncated 932 chars]
Remediation
View remediation
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • 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 (9)

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.

Lp1

High
Category
MCP Least Privilege
Confidence
75% confidence
Finding

The skill uses 'network' 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/gen.py (reported line 47)May include surrounding context.

python
def _load_api_key(cli_key: str | None) -> str:
    """按优先级读取 API Key:CLI 参数 > 环境变量 > ~/.doubao-image-gen/.env"""
    if cli_key:
        return cli_key

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/gen.py (reported line 54)May include surrounding context.

python
def _load_api_key(cli_key: str | None) -> str:
    """按优先级读取 API Key:CLI 参数 > 环境变量 > ~/.doubao-image-gen/.env"""
    if cli_key:
        return cli_key

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/gen.py (reported line 238)May include surrounding context.

python
print("❌ 未找到 API Key,请通过以下方式之一提供:", file=sys.stderr)
        print("   1. --api-key YOUR_KEY", file=sys.stderr)
        print("   2. 环境变量 ARK_API_KEY=YOUR_KEY", file=sys.stderr)
        print("   3. ~/.doubao-image-gen/.env 文件写入 ARK_API_KEY=YOUR_KEY", file=sys.stderr)
        return 2

    # 输出目录

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The skill documentation explains how to configure and use an API key, but it does not warn users that their prompts and related generation parameters are transmitted to the external Volcengine/Doubao image-generation service. In this context, users may include confidential business information, personal data, or proprietary creative material in prompts, so the lack of disclosure creates a meaningful privacy and consent risk.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
92% confidence
Finding

The activation examples include broad, everyday phrases like '帮我画一张' and '生成一张', which can cause the skill to trigger in contexts where the user did not explicitly intend to invoke this external image-generation workflow. Because the skill can call a script that sends prompts to a third-party API and writes output files, accidental activation increases the risk of unintended data disclosure, unexpected external API usage, and surprise costs.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The file's user-facing description, CLI help text, status messages, and generated HTML explicitly use Chinese, including <html lang="zh">, without offering a language selection or documenting that the skill is intended only for a Chinese-speaking or region-specific audience. This is a natural-language policy issue because it imposes a specific language/locale on all users without opt-in.

Content

No source excerpt is available for this finding.

Missing User Warnings

Low
Category
Not specified by scanner
Confidence
87% confidence
Finding

This markdown file states that the skill automatically downloads generated images, writes a prompts.json mapping file, and generates an index.html preview page. For markdown files, SQP-2 applies when the description omits warnings about behaviors that may affect user data or system integrity; here the changelog notes the writes but gives no caution that running the skill will create multiple files in the working/output location.

Content

No source excerpt is available for this finding.