Back to skill

Security audit

PanSou 网盘搜索

Security checks for vulnerabilities and agentic risk

Overview

The skill appears purpose-built for PanSou searching, but it handles credentials and cached tokens without enforcing secure transport or private token-file permissions.

Install only if you control and trust the PanSou service you configure. Prefer an HTTPS PANSOU_URL, avoid sending PANSOU_USER/PANSOU_PWD to any third-party or plaintext endpoint, avoid the --get option for sensitive searches, and restrict permissions on ~/.config/pansou/token.json if you use authenticated mode.

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

T09 · Insecure Skill Coding Practices

Error
Location
scripts/pansou.py:29
Finding

Credentials and bearer tokens may be transmitted over plaintext HTTP

Content
View full analysis
Dict[str, str]: """Return request headers containing authentication.""" return { "Content-Type": "application/json", "Accept": "application/json", "Authorization": f"Bearer {token}", } ``` The documentation also gives a plaintext HTTP endpoint as an example: ```text PANSOU_URL service address (for example, http://localhost:8888) ``` ### Technical Analysis The Skill reads `PANSOU_URL` directly from the environment and does not validate its URL scheme or destination before transmitting authentication information. The login request sends the configured username and password in a JSON body, while subsequent authenticated requests send a reusable JWT bearer token in the `Authorization` header. Network transmission is necessary for the declared PanSou search functionality, and the code does not contain evidence of a covert or hardcoded recipient. However, allowing credentials and tokens to be sent through an arbitrary endpoint without requiring TLS creates an insecure transport path. This is particularly risky because the documentation explicitly permits an `http://` endpoint without limiting that exception to loopback addresses. ### Attack Path 1. A user or deployment configures `PANSOU_URL` with an unencrypted HTTP endpoint, or an attacker influences that configuration to reference an attacker-controlled server. 2. The user invokes `login`, `verify`, or ...[truncated 960 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/pansou.py:52
Finding

Persistent JWT token file does not enforce restrictive permissions

Content
View full analysis
None: TOKEN_FILE.parent.mkdir(parents=True, exist_ok=True) TOKEN_FILE.write_text(json.dumps({"token": token}, ensure_ascii=False, indent=2)) ``` ### Technical Analysis The Skill persists a reusable JWT at `~/.config/pansou/token.json`. The parent directory and token file are created using default permission behavior and therefore depend on the process's ambient `umask`. The code does not explicitly enforce a private directory mode such as `0700` or a token file mode such as `0600`. On a system with permissive defaults, the file or its parent directory may permit access by other local users. Because the token is used as a bearer credential, possession can be sufficient to authenticate to the configured PanSou API; no knowledge of the account password is necessarily required. ### Attack Path 1. The victim invokes a command that causes `login()` to authenticate and call `save_token()`. 2. The script creates `~/.config/pansou/token.json` using ambient filesystem permissions. 3. On a multi-user system with a permissive `umask` or pre-existing permissive directory permissions, another local account reads the token file. 4. The attacker extracts the JWT from the JSON document. 5. The attacker submits the token as `Authorization: Bearer ` to the victim's PanSou service. 6. The attacker retains the victim's PanSou API privileges until the token expires or is revoked. ### Impact Assessment Exploitation requires local filesystem access under another account and permissions that allow the token to be read. If successful, the attacker can impersonate the victim to the PanSou API within the authorization scope of the stolen JWT. This may expose authenticated search functionality, search-related data, and any other ...[truncated 110 chars]
Remediation
View remediation
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • Taint TrackingDirect Taint Flow, Variable-Mediated Taint Flow, Credential Exfiltration Chain
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • MCP Tool PoisoningHidden Instructions, Unicode Deception, Parameter Description Injection
Findings (15)

Tainted flow: 'PANSOU_URL' from os.environ.get (line 29, credential/environment) → requests.post (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Content

Scanner excerpt · scripts/pansou.py (reported line 58)May include surrounding context.

python
print("错误: 服务启用了认证,但未配置 PANSOU_USER / PANSOU_PWD", file=sys.stderr)
        sys.exit(1)
    try:
        resp = requests.post(
            f"{PANSOU_URL}/api/auth/login",
            json={"username": PANSOU_USER, "password": PANSOU_PWD},
            headers={"Content-Type": "application/json"},

Tainted flow: 'PANSOU_URL' from os.environ.get (line 29, credential/environment) → requests.get (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Content

Scanner excerpt · scripts/pansou.py (reported line 105)May include surrounding context.

python
print("错误: 请设置环境变量 PANSOU_URL", file=sys.stderr)
        sys.exit(1)
    try:
        resp = requests.get(f"{PANSOU_URL}/api/health", timeout=TIMEOUT)
        resp.raise_for_status()
        return resp.json()
    except requests.RequestException as e:

Tainted flow: 'PANSOU_URL' from os.environ.get (line 29, credential/environment) → requests.post (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Content

Scanner excerpt · scripts/pansou.py (reported line 121)May include surrounding context.

python
login()
        return {"valid": True, "message": "登录成功"}
    try:
        resp = requests.post(
            f"{PANSOU_URL}/api/auth/verify",
            headers={"Content-Type": "application/json", "Authorization": f"Bearer {token}"},
            timeout=TIMEOUT,

Tainted flow: 'PANSOU_URL' from os.environ.get (line 29, credential/environment) → requests.get (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

In GET mode, user search terms and filters are embedded directly into the URL query string, which is more likely to be logged by proxies, terminals, browser history, reverse proxies, or upstream infrastructure. Because this skill is specifically for searching potentially sensitive or pirated content, leaking queries can expose user interests and operational metadata.

Content

Scanner excerpt · scripts/pansou.py (reported line 183)May include surrounding context.

python
params["filter"] = json.dumps(f, ensure_ascii=False)

        try:
            resp = requests.get(
                f"{PANSOU_URL}/api/search?{urlencode(params, doseq=True)}",
                headers={},
                timeout=TIMEOUT,

Tainted flow: 'PANSOU_URL' from os.environ.get (line 29, credential/environment) → requests.get (network output)

Critical
Category
Data Flow
Confidence
91% confidence
Finding

This authenticated GET request places search parameters in the URL while also attaching a bearer token in headers. Even though the token is not in the URL, the query string can still leak via logs and intermediaries, creating unnecessary privacy exposure in a resource-searching skill where user queries may be sensitive.

Content

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

python
if resp.status_code == 401:
            try:
                token = get_token()
                resp = requests.get(
                    f"{PANSOU_URL}/api/search?{urlencode(params, doseq=True)}",
                    headers=auth_header(token),
                    timeout=TIMEOUT,

Tainted flow: 'PANSOU_URL' from os.environ.get (line 29, credential/environment) → requests.post (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Content

Scanner excerpt · scripts/pansou.py (reported line 235)May include surrounding context.

python
# 优先尝试无认证请求(服务未启用认证时使用)
    headers_no_auth = {"Content-Type": "application/json", "Accept": "application/json"}
    try:
        resp = requests.post(
            f"{PANSOU_URL}/api/search",
            json=payload,
            headers=headers_no_auth,

Tainted flow: 'PANSOU_URL' from os.environ.get (line 29, credential/environment) → requests.post (network output)

Critical
Category
Data Flow
Confidence
90% confidence
Finding

Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Content

Scanner excerpt · scripts/pansou.py (reported line 249)May include surrounding context.

python
if resp.status_code == 401:
        try:
            token = get_token()
            resp = requests.post(
                f"{PANSOU_URL}/api/search",
                json=payload,
                headers=auth_header(token),

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
93% confidence
Finding

The skill invokes a Python script with access to environment variables, reads and writes a token file under the user's home directory, and performs outbound HTTP requests, yet it does not declare an explicit tool scope such as permissions or allowed-tools. This weakens least-privilege controls and makes it easier for the skill to access network, filesystem, and secrets-related capabilities without clear policy boundaries, especially since PANSOU_URL is user-controlled and the script persists authentication material.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
97% confidence
Finding

The skill manifest lists multiple trigger phrases, including "找资源", which is generic and could match many ordinary user requests unrelated to this specific网盘搜索 skill. The description does not provide exclusion conditions or negative examples to narrow when this trigger should and should not activate.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The module docstring and user-facing CLI messages are written in Chinese, which effectively constrains interaction to a specific language. The file does not provide any opt-in, fallback, or explanation that this skill is intentionally region- or locale-specific, so it matches the language/locale policy violation category.

Content

No source excerpt is available for this finding.

External Transmission

Medium
Category
Data Exfiltration
Confidence
87% confidence
Finding

The login call transmits username and password to an externally configured endpoint without enforcing HTTPS or verifying that the destination is trusted. If PANSOU_URL is misconfigured to an attacker-controlled or plaintext HTTP service, credentials can be intercepted or harvested.

Content

Scanner excerpt · scripts/pansou.py (reported line 58)May include surrounding context.

python
print("错误: 服务启用了认证,但未配置 PANSOU_USER / PANSOU_PWD", file=sys.stderr)
        sys.exit(1)
    try:
        resp = requests.post(
            f"{PANSOU_URL}/api/auth/login",
            json={"username": PANSOU_USER, "password": PANSOU_PWD},
            headers={"Content-Type": "application/json"},

External Transmission

Medium
Category
Data Exfiltration
Confidence
80% confidence
Finding

Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Content

Scanner excerpt · scripts/pansou.py (reported line 235)May include surrounding context.

python
# 优先尝试无认证请求(服务未启用认证时使用)
    headers_no_auth = {"Content-Type": "application/json", "Accept": "application/json"}
    try:
        resp = requests.post(
            f"{PANSOU_URL}/api/search",
            json=payload,
            headers=headers_no_auth,

External Transmission

Medium
Category
Data Exfiltration
Confidence
84% confidence
Finding

This authenticated external transmission sends a bearer token to the configured backend without any visible requirement that the connection be encrypted or the host be trusted. A malicious or intercepted endpoint could capture the token and impersonate the user against the service.

Content

Scanner excerpt · scripts/pansou.py (reported line 249)May include surrounding context.

python
if resp.status_code == 401:
        try:
            token = get_token()
            resp = requests.post(
                f"{PANSOU_URL}/api/search",
                json=payload,
                headers=auth_header(token),

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
91% confidence
Finding

The file title and all parameter documentation are written entirely in Chinese, which imposes a specific language on users. Under the policy criteria, language constraints should either offer user choice or be clearly documented as justified for a region-specific tool.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
86% confidence
Finding

This markdown file presents all user-facing instructions and descriptions exclusively in Chinese. Under the policy rules, forcing a specific language without user opt-in can be a natural-language policy violation unless the locale restriction is explicitly justified.

Content

No source excerpt is available for this finding.

Static analysis

No suspicious patterns detected.