Back to skill

Security audit

发票认证

Security checks for vulnerabilities and agentic risk

Overview

This tax automation skill fits its stated purpose, but it needs review because it asks for a tax API key in chat, persists it in shell settings, and can perform sensitive tax actions with some under-scoped confirmations.

Review before installing. Use this only if you trust the provider with enterprise tax data and API-key authority. Prefer configuring the key outside chat and avoid persistent shell-profile storage unless you understand who can read it. Confirm the target enterprise and every state-changing tax action, especially statistics retries and certification changes.

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
invoice_cert.py:249
Finding

Remote API Response Silently Overrides User-Selected Statistics Behavior

Content
View full analysis

Vulnerability Details

File Location: invoice_cert.py, lines 249–259
Vulnerability Type: Unauthorized mutation of a state-changing request
Risk Level: Medium

Code Snippet:

python
result = post("/api/jxplus/zxtSkill/check/commitStatistics", {
    "data": {"commitType": args.commit_type, "bz": args.bz,
             "apiKey": args.api_key}
})
msg = str(result.get("message", ""))
if "1001" in msg or "1002" in msg:
    print(f"提示:{msg},正在自动重试(bz=Y)...")
    result = post("/api/jxplus/zxtSkill/check/commitStatistics", {
        "data": {"commitType": args.commit_type, "bz": "Y",
                 "apiKey": args.api_key}
    })

Technical Analysis

The statistics command initially sends the user-selected bz value. However, if the remote API's textual message contains 1001 or 1002, the script automatically submits another state-changing request with bz="Y".

According to the Skill documentation, bz=Y means canceling an unfinished statistics state. This differs materially from bz=N, which means proceeding while ignoring unchecked invoices. The retry therefore changes the semantics of the operation without obtaining renewed user authorization.

The branch is controlled by an unstructured message returned across the remote-service trust boundary. It does not validate a dedicated status field, verify that the requested operation permits this fallback, or require explicit confirmation before changing the parameter.

Attack Path

  1. The user invokes the statistics command and explicitly selects a behavior such as --bz N.
  2. The script sends the initial request to /api/jxplus/zxtSkill/check/commitStatistics.
  3. The remote response contains 1001 or 1002 in its message field.
  4. The script treats the substring as authorization to retry.
  5. It sends a second request with bz="Y", overriding the user's selected value.
  6. The remote service may cancel an unfinishe ...[truncated 667 chars]
Remediation
View remediation

Remediation Suggestions

  • Never change bz from the user-selected value automatically.
  • When the service indicates that bz=Y is required, stop and explain that retrying would cancel an unfinished statistics state.
  • Require explicit user confirmation before submitting the modified request.
  • Add a dedicated opt-in CLI option, such as --allow-cancel-unfinished, and reject the retry unless it is present.
  • Use a documented structured response code rather than substring matching against the free-form message field.
  • Record both the originally requested parameters and any proposed changes in the confirmation prompt.
  • Add tests proving that responses containing 1001 or 1002 cannot trigger a second state-changing request without explicit authorization.
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • 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
Findings (11)

Ssd 3

High
Category
Not specified by scanner
Confidence
99% confidence
Finding

The code instructs the user to provide an API key directly in conversation so the assistant can configure and run the skill. In a tax-related skill that performs enterprise invoice certification and statistics operations, that key may grant access to sensitive business tax data and action endpoints. Requesting it in chat creates a clear secret-handling vulnerability with elevated context-specific risk due to the financial and regulatory sensitivity of the workflow.

Content

No source excerpt is available for this finding.

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
91% confidence
Finding

The skill instructs the agent to read environment variables, persist secrets into user-level shell configuration, and call remote network APIs, but it declares no explicit tool scope or permission boundaries. That mismatch increases the chance the skill is invoked with broader capabilities than the user expects, especially in a sensitive tax workflow that handles authentication state and invoice operations.

Content

No source excerpt is available for this finding.

Vague Triggers

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The trigger phrases are broad enough to match ordinary conversation such as '登录税局', '当前企业', or '确认签名', which could cause the skill to activate unintentionally. In this skill, accidental activation is more dangerous than usual because it can initiate real tax-session actions, query enterprise identity, and guide persistence of an API key for later privileged operations.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

The skill tells the agent to persist a user-provided apiKey into shell profiles or user environment variables without first presenting a clear warning, consent checkpoint, retention scope, or safer alternative. Persisting credentials beyond the session can expose them to other local processes, future shells, shared accounts, backups, or accidental disclosure, which is especially sensitive because the key authorizes tax-related operations.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
89% confidence
Finding

This Python file performs outbound HTTP POST requests and uploads local files to a remote service, including an API key field and invoice file contents. Although the module docstring states these are shared invoice helpers, there is no confirmation prompt, user-facing log, or warning comment explaining that local data and credentials will be sent to an external server.

Content

No source excerpt is available for this finding.

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
98% confidence
Finding

The login guidance states that credentials will not be collected or stored through the conversation, creating a strong security assurance. Later, the code asks the user to send an apiKey in chat, which undermines that assurance and may mislead users into sharing a sensitive secret under a false sense of safety. This is dangerous because the inconsistency normalizes credential submission in a channel presented as safe from credential exposure.

Content

No source excerpt is available for this finding.

Context-Inappropriate Capability

Medium
Category
Not specified by scanner
Confidence
99% confidence
Finding

The skill explicitly instructs the user to send an apiKey in chat so the assistant can configure and execute the skill. An apiKey is a credential, and collecting it through the conversational channel contradicts the earlier safety messaging that passwords will not pass through the conversation. In an agent setting, this can expose reusable credentials to the model, logs, and any downstream systems handling the conversation.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
97% confidence
Finding

The skill asks the user to send an apiKey directly to the agent without identifying it as a sensitive credential or warning about handling risks. This increases the chance that users will disclose secrets into a logged and model-visible channel. Because apiKeys are often reusable for privileged API access, accidental disclosure can lead to unauthorized tax-data access or actions.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
84% confidence
Finding

The entire skill description, prompts, and prescribed user-facing output are fixed in Chinese, including exact text the agent must return to the user. Under the language/locale policy, forcing a specific language without user opt-in can be a natural-language policy issue unless the locale restriction is explicitly justified.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
76% confidence
Finding

The file's natural-language strings and module description are exclusively in Chinese, which can indicate a fixed language expectation without user opt-in. Under the policy, locale or language constraints should either be optional for the user or clearly justified as region-specific.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
83% confidence
Finding

The file's natural-language descriptions and prompts are entirely in Chinese, including operational guidance to the user, with no indication that the skill is region- or locale-restricted or that another language can be selected. Per the policy, forcing a specific language without user opt-in can be a natural-language policy violation.

Content

No source excerpt is available for this finding.