Back to skill

Security audit

Polymarket Volume Tracker

Security checks for vulnerabilities and agentic risk

Overview

The skill is not overtly malicious, but it should be reviewed because it charges users and can present lifetime Polymarket volume as recent activity while handling a billing API key on the command line.

Review before installing. Treat the reported volumes as lifetime aggregate and approximate Yes/No splits, not verified recent trading momentum. Be aware that normal use charges 0.001 USDT via skillpay.me, and avoid passing real API keys directly on the command line where they may be exposed in local process or shell history records.

Vulnerability Patterns
  • 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
  • Embedded Malicious CodeShips malicious scripts inside the skill and executes them locally
Findings (1)

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/track_volume.py:292
Finding
Billing API Key Exposed Through Command-Line Arguments<![CDATA[ ## Vulnerability Details **File Location**: `SKILL.md:18-21`, `SKILL.md:37-43`, and `scripts/track_volume.py:292-296` **Vulnerability Type**: Command-line credential exposure **Risk Level**: Medium The documented and implemented interface requires the SkillPay API key to be supplied as a command-line argument. ### Vulnerable Code From `SKILL.md:18-21`: ```bash python scripts/track_volume.py --api-key YOUR_SKILLPAY_API_KEY --user-id YOUR_USER_ID ``` From `SKILL.md:37-43`: ```bash export SKILLPAY_API_KEY=your_api_key_here export SKILLPAY_USER_ID=your_user_id_here python scripts/track_volume.py --api-key $SKILLPAY_API_KEY --user-id $SKILLPAY_USER_ID ``` From `scripts/track_volume.py:292-296`: ```python parser.add_argument( "--api-key", required=True, help="skillpay.me API key for payment" ) ``` The supplied credential is subsequently placed in the authentication header used for SkillPay requests, as shown in `scripts/track_volume.py:28-32`: ```python headers = { "X-API-Key": self.api_key, "Content-Type": "application/json" } ``` ### Technical Analysis Command-line arguments are not an appropriate transport mechanism for secrets. Depending on the operating system and execution environment, process arguments can be observed through process inspection facilities while the program is running. They may also be retained in shell history, terminal logging, job-runner metadata, monitoring systems, or diagnostic output. Exporting the credential to an environment variable does not mitigate this issue when the variable is expanded into the command line, because the expanded secret still becomes part of the process argument list. The network transmission itself is disclosed by the Skill documentation and uses HTTPS. No evidence was found that the credential is sent to an undeclared host. The vulnerability is the local handling and exposure of the credential before it is used to authenticate to `skillpay.me`. ### Attack Path 1. A ...[truncated 1388 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Stop accepting API keys through ordinary command-line arguments. 2. Read `SKILLPAY_API_KEY` directly from the environment without expanding it into the command: ```python import os api_key = os.environ.get("SKILLPAY_API_KEY") if not api_key and not args.skip_payment: parser.error("SKILLPAY_API_KEY must be set when payment is enabled") ``` 3. Update the documented invocation to avoid placing the secret in the argument list: ```bash export SKILLPAY_API_KEY='your_api_key_here' python scripts/track_volume.py --user-id YOUR_USER_ID ``` 4. Prefer an operating-system credential store, protected configuration file, or secret-manager integration over long-lived environment variables where available. 5. Make credentials optional when `--skip-payment` is enabled, because billing authentication is unnecessary in that execution mode. 6. Ensure the API key is never included in exceptions, debug output, telemetry, command traces, or payment failure messages. 7. Use narrowly scoped and revocable API keys. Rotate any key previously supplied through the documented command-line pattern. 8. Consider accepting the key through a non-echoing interactive prompt when neither a secret manager nor an environment-based mechanism is available. ]]>
Vulnerability Patterns
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • MCP Tool PoisoningHidden Instructions, Unicode Deception, Parameter Description Injection
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
Findings (6)

Tp4

High
Category
MCP Tool Poisoning
Confidence
96% confidence
Finding
The documented behavior materially misrepresents what users are paying for: it claims recent high-volume market tracking and side-specific trading volumes, while the described implementation appears to use lifetime aggregate volume and inferred Yes/No splits. In a paid financial/trading context, this can mislead users into making decisions based on inaccurate or stale metrics, turning a documentation issue into a meaningful integrity and consumer-harm risk.

Intent-Code Divergence

High
Confidence
98% confidence
Finding
The file-level description and output explicitly promise a 10-minute volume tracker, but the implemented ranking logic later uses aggregate `volumeNum` from the market data rather than recent trades. In a paid trading-oriented skill, this is dangerous because users may make financial decisions based on stale or misleading market activity while believing they are seeing short-term momentum.

Description-Behavior Mismatch

High
Confidence
99% confidence
Finding
The core processing loop ignores the available recent-trade path and instead ranks markets by aggregate `volumeNum`, while presenting the result as 'Top 10 Polymarket Markets (Last 10 Minutes)'. Because the skill is marketed for identifying hot/high-volume trading opportunities and charges users per call, this misrepresentation can directly mislead users into trusting unsuitable rankings and making poor financial decisions.

Lp3

Medium
Category
MCP Least Privilege
Confidence
93% confidence
Finding
The skill documents network-dependent behavior and payment processing but does not declare any explicit tool scope or allowed-tools constraints. Missing capability scoping weakens sandboxing and review controls, increasing the risk that a runtime or future implementation can make undeclared external requests or expand behavior beyond what users and platforms expect.

Vague Triggers

Medium
Confidence
90% confidence
Finding
The manifest description says to use the skill when a user asks about 'Polymarket trends, hot markets, or wants to find high-volume trading opportunities.' Phrases like 'trends' and 'hot markets' are broad and there are no explicit constraints or negative examples clarifying when this skill should or should not activate.

Intent-Code Divergence

Medium
Confidence
97% confidence
Finding
The output example says the results are for the 'Last 10 Minutes' while other sections state the skill uses total or lifetime market volume. This contradiction can cause users to trust the output as near-real-time momentum data when it may actually be long-horizon aggregate volume, which is especially risky for market-tracking and fee-charging workflows.

Static analysis

No suspicious patterns detected.