Back to skill

Security audit

Veo 3 Video Gen (Gemini API)

Security checks for vulnerabilities and agentic risk

Overview

This skill does what it claims: it generates videos through Google's Gemini/Veo API, with some expected privacy and dependency cautions.

Install only if you are comfortable sending prompts and any provided reference or last-frame images to Google's Gemini API. Use GEMINI_API_KEY instead of --api-key, restrict the key's quota and permissions where possible, and consider pinning dependencies before running in a sensitive environment.

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

T08 · Insecure Dependencies

Warning
Location
scripts/generate_video.py:2
Finding

Unbounded Dependency Versions Allow Unreviewed Supply-Chain Code

Content
View full analysis

Vulnerability Details

File Location: scripts/generate_video.py:2-7
Vulnerability Type: Unpinned runtime dependencies
Risk Level: Medium

Vulnerable Code:

python
# /// script
# requires-python = ">=3.10"
# dependencies = [
#     "google-genai>=1.0.0",
#     "pillow>=10.0.0",
# ]
# ///

Technical Analysis

The documented execution method uses uv run, while the inline dependency metadata permits any future version of google-genai and pillow that satisfies the specified minimum version. Consequently, the dependency code resolved and installed at execution time can differ from the code reviewed during this audit.

The script imports google.genai and gives the resulting package access to the process environment, Gemini API credentials, prompts, local images, generated media, and the invoking user's filesystem permissions. A compromised or malicious future package release could therefore execute with the same privileges as the user running the Skill.

pillow is declared but is not imported or otherwise used by the audited script. Including this unnecessary package expands the dependency and supply-chain attack surface beyond what is required for the declared functionality.

Attack Path

  1. An attacker compromises a permitted dependency release or its package-publishing account.
  2. The attacker publishes a version satisfying google-genai>=1.0.0 or pillow>=10.0.0.
  3. A user invokes the documented uv run scripts/generate_video.py workflow without a reviewed lockfile.
  4. The dependency resolver selects and installs the compromised release.
  5. Malicious dependency code executes during import or runtime with the invoking user's privileges.
  6. The dependency can read accessible process data, including GEMINI_API_KEY, prompts, supplied media, and local files, or perform unauthorized network and filesystem operations.

Impact Assessment

Exploitation could provide code ...[truncated 468 chars]

Remediation
View remediation

Remediation Suggestions

  1. Pin every direct dependency to an exact, reviewed version rather than using open-ended minimum versions.
  2. Generate and commit a lockfile, or use the equivalent locked-script workflow supported by uv, and enforce locked resolution during execution.
  3. Where supported, verify downloaded distributions using cryptographic hashes.
  4. Remove pillow because the audited script does not use it.
  5. Review transitive dependencies and update them only through a controlled dependency-review process.
  6. Run the Skill with restricted filesystem and network access where practical, exposing only the output directory, required input files, and the Google API endpoint.

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/generate_video.py:241
Finding

Gemini API Key Can Be Exposed Through Command-Line Arguments

Content
View full analysis

Vulnerability Details

File Location: scripts/generate_video.py:241-245
Vulnerability Type: Sensitive credential accepted as a process argument
Risk Level: Medium

Vulnerable Code:

python
parser.add_argument(
    "--api-key",
    "-k",
    help="API key (overrides GEMINI_API_KEY)",
)

The command-line credential is subsequently selected by the following function:

python
def get_api_key(provided_key: str | None) -> str | None:
    if provided_key:
        return provided_key
    return os.environ.get("GEMINI_API_KEY")

Technical Analysis

Accepting an API key through --api-key places the secret in the process argument vector. Depending on the operating system and host configuration, command-line arguments may be exposed through shell history, process-listing utilities, /proc process metadata, monitoring agents, crash diagnostics, audit logs, terminal transcripts, or automation logs.

The API key is legitimately required for the declared cloud video-generation behavior and is passed to Google's GenAI client. The vulnerability is not the authenticated network request itself, but the avoidable command-line transport of the credential. The script already supports GEMINI_API_KEY, so accepting the same secret through a visible command-line argument is not necessary for its core functionality.

Attack Path

  1. A user runs the Skill with --api-key SECRET.
  2. The command is retained in shell history, captured by an execution log, or exposed in process metadata while the command is running.
  3. A local user, monitoring component, log reader, or other principal with access to that data retrieves the key.
  4. The exposed key is reused to authenticate to Gemini API services.
  5. The attacker consumes available quota or performs any other operation authorized by that key.

This path requires access to process metadata, command history, or collected logs; the script does not ...[truncated 544 chars]

Remediation
View remediation

Remediation Suggestions

  1. Remove the --api-key and -k command-line options.
  2. Require GEMINI_API_KEY or retrieve the credential from an operating-system credential store or managed secret provider.
  3. Update the usage text and SKILL.md requirements so they no longer recommend or advertise command-line secret submission.
  4. If interactive entry is needed, use a non-echoing prompt such as getpass.getpass() rather than a command-line argument.
  5. Advise users who previously supplied keys through the command line to remove affected shell-history entries and rotate keys if logs or process metadata may have been accessible.
  6. Apply API restrictions, project-level quotas, billing alerts, and least-privilege controls to limit the impact of any exposed key.
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Behavioral ASTexec() Call, eval() Call, Dynamic Import
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
Findings (6)

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
89% confidence
Finding

The skill invokes a Python script with network access, file reads/writes, environment variable usage, and optional shell-dependent tooling like ffmpeg, yet the manifest declares no explicit tool scope or allowed permissions. This creates an avoidable trust gap: an agent or reviewer cannot easily tell that executing the skill may access secrets, contact external APIs, and write output files.

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

python
def require_bin(name: str) -> None:
    if subprocess.run(["bash", "-lc", f"command -v {shlex.quote(name)}"], capture_output=True).returncode != 0:
        raise RuntimeError(f"Required binary not found on PATH: {name}")

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

python
"2",
        str(out_png),
    ]
    p = subprocess.run(cmd, capture_output=True, text=True)
    if p.returncode != 0:
        raise RuntimeError(f"ffmpeg last-frame extract failed: {p.stderr[-2000:]}")
    return out_png

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

python
"2",
        str(out_png),
    ]
    p = subprocess.run(cmd, capture_output=True, text=True)
    if p.returncode != 0:
        raise RuntimeError(f"ffmpeg last-frame extract failed: {p.stderr[-2000:]}")
    return out_png

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

python
"192k",
            str(out_path),
        ]
        p2 = subprocess.run(cmd2, capture_output=True, text=True)
        if p2.returncode != 0:
            raise RuntimeError(
                "ffmpeg concat failed.\n"

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
91% confidence
Finding

The script reads local reference and last-frame images and sends them to a third-party API without an explicit, prominent disclosure at the point of use. In an agent skill context, this increases the risk of unintended exfiltration of sensitive local images or screenshots because users may not realize these files leave the local environment.

Content

No source excerpt is available for this finding.

Static analysis

No suspicious patterns detected.