Back to skill

Security audit

Trakt.tv Integration

Security checks for vulnerabilities and agentic risk

Overview

This Trakt skill has a coherent purpose, but it needs Review because setup handles sensitive Trakt credentials with weak storage and unsafe shell/install guidance.

Before installing, treat this as a Review item: use a virtual environment, avoid --break-system-packages, do not grant all Trakt permissions, store ~/.openclaw/trakt_config.json with owner-only permissions, and do not let an agent run the INSTALL.md PIN command through a shell with untrusted input.

Vulnerability Patterns
  • Unauthorized Access and Privilege EscalationObtains permissions beyond the task's legitimate needs
  • 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 (5)

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/setup.py:121
Finding

OAuth Credentials and Tokens Stored Without Enforced Access Permissions

Content
View full analysis
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Note
Location
scripts/setup.py:110
Finding

Client Secret Is Collected Through a Terminal-Echoing Prompt

Content
View full analysis
Remediation
View remediation

T05 · Unauthorized Access and Privilege Escalation

Warning
Location
scripts/setup.py:72
Finding

Setup Recommends Granting All Available Trakt Permissions

Content
View full analysis
Remediation
View remediation

T08 · Insecure Dependencies

Warning
Location
scripts/setup.py:47
Finding

Setup Automatically Modifies the System Python Environment Using an Unbounded Dependency

Content
View full analysis
=2.31.0 ``` ### Technical Analysis The setup wizard invokes pip automatically and passes `--break-system-packages`, bypassing protections intended to prevent modification of an externally managed Python environment. This can overwrite or conflict with operating-system-managed packages and destabilize other Python applications. The installation command does not pin a reviewed version or verify package hashes. The requirement `requests>=2.31.0` permits any future release satisfying that lower bound. Therefore, the effective dependency code can change after the Skill itself has been reviewed. The package name is legitimate and no malicious dependency is embedded in the project. The risk arises from automatic mutable resolution and modifi ...[truncated 1231 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Error
Location
INSTALL.md:103
Finding

Unquoted PIN Interpolation Enables Shell Command Injection in the Documented Agent Flow

Content
View full analysis
Remediation
View remediation
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Tool MisuseTool Parameter Abuse, Chaining Abuse, Unsafe Defaults
  • Rogue AgentSelf-Modification, Session Persistence
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
Findings (32)

Tainted flow: 'pin' from input (line 187, user input) → subprocess.run (code execution)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

External input (network, user) flows to a code execution sink. This enables remote code execution or command injection.

Content

Scanner excerpt · scripts/setup.py (reported line 195)May include surrounding context.

python
# Run auth with PIN
        print("\nAuthenticating...")
        result = subprocess.run(
            [sys.executable, str(CLIENT_SCRIPT), "auth", pin],
            capture_output=True,
            text=True

Tool Parameter Abuse

High
Category
Tool Misuse
Confidence
98% confidence
Finding

Using shell=True for opening URLs on Windows is an unsafe tool invocation pattern because it delegates parsing to the shell. Even with a constant URL today, this is a fragile construct that can become exploitable if any future refactor or environment influence makes the target value attacker-controlled.

Content

Scanner excerpt · scripts/setup.py (reported line 94)May include surrounding context.

python
elif sys.platform == 'linux':
            subprocess.run(['xdg-open', url], check=False)
        elif sys.platform == 'win32':
            subprocess.run(['start', url], shell=True, check=False)
        print_success(f"Opened {url}")
    except Exception as e:
        print_info(f"Please visit: {url}")

Tool Parameter Abuse

High
Category
Tool Misuse
Confidence
99% confidence
Finding

This is a stronger case of tool parameter abuse because shell=True is used with pin_url, which is derived from another process's output and is not validated. If an attacker can influence that output, they may be able to trigger arbitrary shell command execution on Windows during setup.

Content

Scanner excerpt · scripts/setup.py (reported line 177)May include surrounding context.

python
elif sys.platform == 'linux':
                subprocess.run(['xdg-open', pin_url], check=False)
            elif sys.platform == 'win32':
                subprocess.run(['start', pin_url], shell=True, check=False)
            print_success(f"Opened {pin_url}")
        except:
            print_info(f"Please visit: {pin_url}")

Context-Inappropriate Capability

Medium
Category
Not specified by scanner
Confidence
85% confidence
Finding

The installation guide directs the agent to execute local shell commands such as dependency checks and package installation, which goes beyond the skill's user-facing purpose of recommendations and watch tracking. Even though the commands shown are specific, permitting an agent to run local commands and launch browser actions from documentation increases attack surface and can normalize unsafe execution behavior.

Content

No source excerpt is available for this finding.

Session Persistence

Medium
Category
Rogue Agent
Confidence
60% confidence
Finding

Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Content

Scanner excerpt · INSTALL.md (reported line 21)May include surrounding context.

pip3 install requests --break-system-packages

text

## Step 2: Create Trakt Application

**Action:** Open browser to Trakt application creation page

Context-Inappropriate Capability

Medium
Category
Not specified by scanner
Confidence
90% confidence
Finding

The guide instructs the agent to solicit a Trakt Client ID and Client Secret from the user and then write them into a local configuration file. While this is part of OAuth-style setup, it expands the agent's authority into credential handling and local persistence, creating unnecessary exposure if the file is readable by other processes or if the agent logs or mishandles the values.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

The guide tells the agent to collect a sensitive Client Secret and save it in plaintext under ~/.openclaw/trakt_config.json without discussing sensitivity, permissions, or secure storage. This can lead to credential disclosure through permissive filesystem access, backups, logs, or other local processes, enabling unauthorized use of the Trakt application identity.

Content

No source excerpt is available for this finding.

Session Persistence

Medium
Category
Rogue Agent
Confidence
60% confidence
Finding

Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Content

Scanner excerpt · README.md (reported line 37)May include surrounding context.

md
This will guide you through the entire setup process automatically:
- Install dependencies
- Help you create a Trakt application
- Configure credentials
- Authenticate with PIN
- Test the integration

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The README instructs users to store a client secret, access token, and refresh token in a local JSON file but does not warn about the sensitivity of these credentials or recommend secure file permissions. If the local environment is shared, backed up insecurely, or accidentally exposed, these secrets could be used to access the user's Trakt account.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The README says the skill 'automatically triggers when Trakt-related queries are detected' without clearly defining scope or guardrails. In an agent system, ambiguous auto-triggering can cause unintended activation on loosely related prompts, which may expose personal viewing history or invoke authenticated actions unexpectedly.

Content

No source excerpt is available for this finding.

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
97% confidence
Finding

The skill instructs the agent to read local files, write credential-bearing configuration, access the network, and execute shell commands, but it declares no explicit tool scope or permissions boundary. In an agent environment, this increases the chance of over-privileged execution and makes it harder to constrain or audit what the skill is allowed to do.

Content

No source excerpt is available for this finding.

Session Persistence

Medium
Category
Rogue Agent
Confidence
71% confidence
Finding

The skill establishes persistent local storage for authentication material in ~/.openclaw/trakt_config.json, which creates a session that survives beyond a single interaction. Persistence itself is expected for OAuth integrations, but it becomes a security concern here because long-lived tokens are retained locally without discussion of lifecycle controls, revocation, or storage hardening.

Content

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

md
2. **Trakt.tv account** with Pro subscription (required for automatic watch tracking)

3. **Trakt API application** - Create at <https://trakt.tv/oauth/applications>

4. **Configuration file:** `~/.openclaw/trakt_config.json` (see setup below)

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The skill directs users to store a Trakt client secret, access token, and refresh token in a plaintext local JSON file without any warning about their sensitivity or guidance on file permissions. If that file is exposed through local compromise, backups, logs, or overly broad agent/file access, an attacker could reuse the credentials to access or manipulate the user's Trakt account.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
91% confidence
Finding

The authentication section shows client_secret, access_token, and refresh_token values in request and response examples, but provides no caution about secure storage, redaction, or avoiding exposure in logs. For markdown guidance that may be used to implement the skill, omission of any credential-handling warning is a meaningful safety gap.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
88% confidence
Finding

This markdown file describes calls to /sync/history/{type}/{id} and /recommendations/{type} using Authorization: Bearer <access_token>, which involve sensitive user behavioral data and personalized account information. The documentation does not include any warning that these requests access or transmit private user data to a third-party service.

Content

No source excerpt is available for this finding.

subprocess module call

Medium
Category
Dangerous Code Execution
Confidence
82% confidence
Finding

The setup script automatically installs a package into the user's Python environment using pip and the --break-system-packages flag, which weakens environment isolation and may alter system-managed packages. In an agent skill context, auto-modifying the host environment increases supply-chain and integrity risk, especially if users do not expect setup scripts to perform package installation.

Content

Scanner excerpt · scripts/setup.py (reported line 60)May include surrounding context.

python
print_info("Installing requests...")
        
        try:
            subprocess.run([
                sys.executable, "-m", "pip", "install", 
                "requests", "--break-system-packages"
            ], check=True, capture_output=True)

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

python
url = "https://trakt.tv/oauth/applications"
    try:
        if sys.platform == 'darwin':
            subprocess.run(['open', url], check=False)
        elif sys.platform == 'linux':
            subprocess.run(['xdg-open', url], check=False)
        elif sys.platform == 'win32':

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

python
if sys.platform == 'darwin':
            subprocess.run(['open', url], check=False)
        elif sys.platform == 'linux':
            subprocess.run(['xdg-open', url], check=False)
        elif sys.platform == 'win32':
            subprocess.run(['start', url], shell=True, check=False)
        print_success(f"Opened {url}")

subprocess module call

Medium
Category
Dangerous Code Execution
Confidence
97% confidence
Finding

This uses shell=True on Windows to invoke start, which causes shell parsing and creates command-injection risk if the opened target ever becomes attacker-controlled. Even though url is hardcoded here, using this pattern in a setup script normalizes an unsafe execution primitive and increases the blast radius if the value later becomes variable.

Content

Scanner excerpt · scripts/setup.py (reported line 94)May include surrounding context.

python
elif sys.platform == 'linux':
            subprocess.run(['xdg-open', url], check=False)
        elif sys.platform == 'win32':
            subprocess.run(['start', url], shell=True, check=False)
        print_success(f"Opened {url}")
    except Exception as e:
        print_info(f"Please visit: {url}")

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
93% confidence
Finding

The script writes the Trakt client ID and client secret to a predictable file in the user's home directory without setting restrictive permissions or clearly warning the user about local secret storage. In an agent skill, storing API secrets unencrypted and implicitly can expose credentials to other local users, backup systems, or unrelated processes.

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

python
# Run auth command to get PIN URL
    try:
        result = subprocess.run(
            [sys.executable, str(CLIENT_SCRIPT), "auth"],
            capture_output=True,
            text=True

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

python
# Open browser to PIN URL
        try:
            if sys.platform == 'darwin':
                subprocess.run(['open', pin_url], check=False)
            elif sys.platform == 'linux':
                subprocess.run(['xdg-open', pin_url], check=False)
            elif sys.platform == 'win32':

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

python
if sys.platform == 'darwin':
                subprocess.run(['open', pin_url], check=False)
            elif sys.platform == 'linux':
                subprocess.run(['xdg-open', pin_url], check=False)
            elif sys.platform == 'win32':
                subprocess.run(['start', pin_url], shell=True, check=False)
            print_success(f"Opened {pin_url}")

subprocess module call

Medium
Category
Dangerous Code Execution
Confidence
99% confidence
Finding

This combines shell=True with pin_url derived from another program's stdout, creating a credible command-injection path on Windows if the helper script or upstream data can influence that URL. In a skill setup flow, opening attacker-influenced content through a shell is especially dangerous because it can lead to arbitrary command execution on the host.

Content

Scanner excerpt · scripts/setup.py (reported line 177)May include surrounding context.

python
elif sys.platform == 'linux':
                subprocess.run(['xdg-open', pin_url], check=False)
            elif sys.platform == 'win32':
                subprocess.run(['start', pin_url], shell=True, check=False)
            print_success(f"Opened {pin_url}")
        except:
            print_info(f"Please visit: {pin_url}")

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

python
# Run auth with PIN
        print("\nAuthenticating...")
        result = subprocess.run(
            [sys.executable, str(CLIENT_SCRIPT), "auth", pin],
            capture_output=True,
            text=True

Static analysis

No suspicious patterns detected.