Back to skill

Security audit

meituan-travel

Security checks for vulnerabilities and agentic risk

Overview

The skill’s travel purpose is mostly coherent, but it uses sensitive Meituan authentication tokens with unpinned external npm tooling and automatic installs, so it should be reviewed before use.

Install only if you trust the publisher and runtime environment, are comfortable giving this skill Meituan auth access, and can control or pin the npm packages it runs. Avoid using it in broad local environments until the package versions are pinned, automatic global installs are removed, endpoint overrides are restricted, and token injection has clear user consent boundaries.

Vulnerability Patterns
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • 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
Findings (5)

T03 · Remote Payload Retrieval and Execution

Error
Location
meituan-passport-user-auth/reference.md:137
Finding
Remote Node.js installer is piped directly into Bash<![CDATA[ ## Vulnerability Details **File Location**: `meituan-passport-user-auth/reference.md:137` **Vulnerability Type**: `T03: Remote Payload Retrieval and Execution` **Risk Level**: Critical ### Vulnerable Code ```bash curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.1/install.sh | bash ``` ### Technical Analysis The installation instructions download shell code from an external URL and execute it immediately. Although the URL points to the established `nvm-sh/nvm` repository and references a version tag, the downloaded content is not verified with a cryptographic signature or pinned checksum before execution. This creates a remote code-execution channel whose effective payload is controlled outside the reviewed Skill package. Compromise of the upstream repository, release tag, distribution infrastructure, DNS/TLS path, or user environment could cause arbitrary commands to execute with the privileges of the user following the instructions. The behavior is not necessary for the Skill's travel or authentication functionality. Node.js installation can be handled through a trusted package manager or a separately downloaded and verified installer. ### Attack Path 1. The Skill reports that npm or the required Node.js version is unavailable. 2. The user follows the fallback installation instructions in `reference.md`. 3. `curl` retrieves the remote shell script. 4. The response is passed directly to Bash without inspection or integrity verification. 5. Any commands present in the response execute with the invoking user's permissions. ### Impact Assessment Successful exploitation provides arbitrary code execution under the invoking account. This can expose local files, cached authentication tokens, environment variables, SSH credentials, browser data, and other user-accessible secrets. The executed payload could also modify shell profiles or install additional persistent components if permitted by the account. ]]>
Remediation
<![CDATA[ ## Remediation Suggestions - Remove the `curl | bash` instruction. - Prefer an operating-system package manager or the official signed Node.js installer. - If nvm must be used, download a versioned artifact to disk first. - Verify the artifact against a pinned SHA-256 checksum or trusted cryptographic signature. - Present the downloaded script for inspection before executing it. - Fail closed when verification cannot be completed. - Document the expected publisher, version, checksum, and installation effects. ]]>

T08 · Insecure Dependencies

Error
Location
SKILL.md:80
Finding
Authenticated travel workflow executes a mutable latest npm package<![CDATA[ ## Vulnerability Details **File Location**: `SKILL.md:80-84` **Vulnerability Type**: `T08: Insecure Dependencies` **Risk Level**: High ### Vulnerable Code ```bash MEITUAN_HT_TOKEN="${passport_token}" npx @meituan-travel/ht-ai-open@latest query \ --query "<用户的自然语言查询>" \ --origin-query "<用户完整原始输入>" \ --channel clawh \ [--city <城市>] ``` ### Technical Analysis The primary workflow uses `npx` with the mutable `@latest` tag. The exact code executed can therefore change after the Skill has been reviewed. No exact package version, lockfile, integrity hash, or signature is enforced. The package executes in a security-sensitive context: it receives the Meituan authorization token through `MEITUAN_HT_TOKEN` and receives the user's complete original input through `--origin-query`. A compromised package release, npm account, registry response, or dependency chain could access those values and execute arbitrary code under the Agent's operating-system account. Passing the token to the legitimate travel service is necessary for authenticated queries, but obtaining and executing an unpinned package is not the minimum privilege or trust necessary to perform that function. ### Attack Path 1. An attacker compromises the npm publisher account, registry path, or a transitive dependency and publishes a malicious latest release. 2. A user invokes a travel query. 3. `npx` resolves and executes the package currently identified by `@latest`. 4. The malicious package reads `MEITUAN_HT_TOKEN`, command arguments, local files, or other environment variables. 5. The package exfiltrates data or performs arbitrary actions with the Agent process's permissions. ### Impact Assessment Exploitation could disclose the user's authorization token and complete original query, including unrelated sensitive information contained in the prompt. It could also provide arbitrary code execution with access to all files, credentials, network destinations, and subprocess capabilities a ...[truncated 34 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Replace `@latest` with an exact reviewed version. - Use a lockfile and enforce npm integrity metadata. - Prefer a locally installed, reviewed dependency rather than allowing `npx` to fetch code during every workflow. - Disable npm lifecycle scripts where they are not required. - Execute the CLI in a sandbox with narrowly scoped filesystem and network access. - Provide the token only to the final reviewed process and remove unrelated environment variables. - Minimize `--origin-query` content by excluding unrelated secrets or conversation history. - Establish a controlled dependency-update and security-review process. ]]>

T08 · Insecure Dependencies

Error
Location
meituan-passport-user-auth/scripts/qrcode-image.sh:48
Finding
QR generation automatically installs an unpinned package globally<![CDATA[ ## Vulnerability Details **File Location**: `meituan-passport-user-auth/scripts/qrcode-image.sh:48-54` **Vulnerability Type**: `T08: Insecure Dependencies` **Risk Level**: High ### Vulnerable Code ```bash if ! NODE_PATH="$NODE_GLOBAL_MODULES" node -e "require('qrcode')" 2>/dev/null; then echo "[qrcode-image.sh] qrcode 模块未安装,正在自动安装..." >&2 if ! npm install -g qrcode 2>&1 >&2; then echo "QRCODE_SKIP" exit 0 fi NODE_GLOBAL_MODULES="$(npm root -g 2>/dev/null)" ``` ### Technical Analysis If the `qrcode` module is unavailable, the script automatically downloads and globally installs the package without specifying an exact version or verifying its integrity. npm packages and their lifecycle scripts can execute code during installation. The global installation also modifies shared user-level or system-level tooling beyond the duration of the Skill invocation. This exceeds the minimum changes necessary to generate a single QR image and exposes subsequent processes to the installed package. ### Attack Path 1. The local environment does not already contain the global `qrcode` module. 2. The user invokes the authorization workflow. 3. The QR script executes `npm install -g qrcode`. 4. npm resolves the current package version and its dependency graph. 5. A compromised package or dependency executes malicious installation code or leaves malicious globally available modules. 6. The QR script subsequently loads the installed module through `NODE_PATH`. ### Impact Assessment A malicious package can execute with the privileges of the npm invocation, inspect user-accessible files, access environment variables, communicate over the network, and alter global Node.js tooling. The global installation can continue affecting later sessions and unrelated applications that resolve the same module. ]]>
Remediation
<![CDATA[ ## Remediation Suggestions - Pin `qrcode` to an exact reviewed version with a verified integrity hash. - Package the required dependency with the Skill or install it locally from a locked dependency tree. - Do not perform automatic global installations during authentication. - Disable lifecycle scripts if the reviewed package does not require them. - If QR support is unavailable, fail safely or provide the authorization link without installing new software. - Run QR generation in a sandbox without access to authentication tokens or unrelated files. ]]>

T09 · Insecure Skill Coding Practices

Warning
Location
meituan-passport-user-auth/scripts/qrcode-image.sh:18
Finding
Caller-controlled client ID is used in a predictable QR output path<![CDATA[ ## Vulnerability Details **File Location**: `meituan-passport-user-auth/scripts/qrcode-image.sh:18-25,60-73` **Vulnerability Type**: `T09: Insecure Skill Coding Practices` **Risk Level**: Medium ### Vulnerable Code ```bash if [ -n "$CLIENT_ID" ]; then IMGFILE="$SCRIPT_DIR/qrcode_${CLIENT_ID}.png" else RAND=$(LC_ALL=C tr -dc 'a-z0-9' < /dev/urandom 2>/dev/null | head -c8; true) IMGFILE="$SCRIPT_DIR/qrcode_${RAND}.png" RAND_FILE=1 fi ``` ```bash RESULT=$(NODE_PATH="$NODE_GLOBAL_MODULES" node -e " const qr = require('qrcode'); const file = process.argv[1]; const url = process.argv[2]; qr.toFile(file, url, { type: 'png', width: 300, margin: 2, errorCorrectionLevel: 'M' }, (err) => { if (!err) { process.stdout.write('QRCODE_IMAGE:' + file); } else { process.stdout.write('QRCODE_SKIP'); } }); " -- "$IMGFILE" "$URL" 2>/dev/null) ``` ### Technical Analysis When a client ID is supplied, it is inserted directly into the output filename. The value is not constrained to safe filename characters, canonicalized, or checked for path separators. The output is predictable and is opened by `qr.toFile` without exclusive creation or a symlink check. The predictable client-ID branch also sets `RAND_FILE` to zero, so its output is not removed by the cleanup handler. This leaves authorization QR images in the Skill's script directory after execution. Where an attacker can influence the client ID or create filesystem entries in the relevant directory, path components or a pre-created symbolic link can redirect the PNG write to another user-writable file. ### Attack Path 1. An attacker supplies a crafted client ID or predicts the fixed QR filename. 2. The attacker includes path separators where usable or creates a symbolic link at the expected output path. 3. The authorization workflow invokes `qrcode-image.sh`. 4. `qr.toFile` opens the selected path and writes PNG data. 5. The linked or selected target is overwritten if the Agent account has write ...[truncated 550 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Validate client IDs against a strict allowlist such as `[A-Za-z0-9_-]+`. - Do not use caller-controlled identifiers directly in filesystem paths. - Create a private temporary directory with mode `0700`. - Use `mktemp` to generate an unpredictable output filename. - Open the file with exclusive-creation and no-follow semantics where supported. - Reject symbolic links and verify that the canonical output path remains inside the intended directory. - Set generated files to mode `0600`. - Delete all generated QR images after display or authorization completion, including client-ID-based files. ]]>

T05 · Unauthorized Access and Privilege Escalation

Error
Location
meituan-passport-user-auth/SKILL.md:64
Finding
User-provided base URL can redirect the authentication workflow<![CDATA[ ## Vulnerability Details **File Location**: `meituan-passport-user-auth/SKILL.md:64-71,119,166` **Vulnerability Type**: `T05: Unauthorized Access and Privilege Escalation` **Risk Level**: High ### Vulnerable Code ```markdown | `--base_url` | 用户说「泳道」或提供 URL(优先级高于 `--env`) | 不加 | ``` ```bash pt-passport auth get-code --client_id <client_id> [--env test] [--base_url <url>] ``` ```bash pt-passport auth poll-token --client_id <client_id> [--base_url <url>] ``` The corresponding CLI reference also declares the override: ```markdown | `--base_url` | - | 自定义 API 地址,优先级高于 `--env`(泳道) | ``` ### Technical Analysis The instructions allow a URL supplied through the conversation to override the normal Meituan authentication endpoint. No mandatory HTTPS check, hostname allowlist, IP-address restriction, redirect policy, or administrator-only control is specified. This breaks the expected trust boundary of the authentication process. A user or prompt-injected instruction could direct the CLI to an attacker-controlled service or an internal network address. The absent manifest-declared `pt-passport` package prevented verification of the precise request fields sent by the CLI, so disclosure of any particular secret cannot be asserted; however, redirecting an authentication client to an arbitrary endpoint inherently exposes its request metadata and permits spoofed responses. The override is not required for ordinary production authentication. Internal lane selection, if operationally necessary, should be restricted to administrator-approved Meituan domains. ### Attack Path 1. An attacker causes the conversation to include a malicious `base_url`. 2. The Agent follows the Skill instructions and passes that value to `auth get-code`. 3. The authentication CLI sends authorization requests to the attacker-selected destination. 4. The attacker records request metadata and returns crafted authorization links or pr ...[truncated 704 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Remove user-controlled authentication endpoint overrides. - Hard-code the approved production and test endpoints. - If internal lanes are required, allow only administrator-configured HTTPS hostnames under approved Meituan domains. - Reject non-HTTPS schemes, IP literals, embedded credentials, fragments, and unexpected ports. - Resolve and validate destination addresses to prevent loopback, link-local, private-network, and cloud-metadata access unless explicitly required. - Disable or strictly validate redirects. - Bind each approved client ID to its authorized environment and endpoint. - Audit the missing `pt-passport` package to identify every field transmitted to `base_url`. ]]>
Vulnerability Patterns
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Tool MisuseTool Parameter Abuse, Chaining Abuse, Unsafe Defaults
Findings (18)

Tp4

High
Category
MCP Tool Poisoning
Confidence
99% confidence
Finding
The declared description presents an end-user travel concierge skill focused on travel products and planning. The supplied code does not implement any travel-related functionality such as search, booking, pricing, reviews, or itinerary management. Instead, it is an installation script for a local npm package named pt-passport, including environment validation, version detection, and global CLI installation. This is a materially different primary purpose and introduces undeclared system/package-management behavior unrelated to the stated travel assistant description.

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding
The declared description presents a broad travel concierge/booking skill, but the supplied code does not implement any travel-related functionality such as search, booking, price comparison, reviews, or itinerary planning. Instead, it is a utility script for creating QR code PNG files from a URL, storing them locally, and even installing a required npm module globally if absent. That is a materially different purpose and introduces undeclared capabilities related to file creation and package installation. Therefore, the description does not accurately represent the actual behavior of this code chunk.

Tp4

High
Category
MCP Tool Poisoning
Confidence
96% confidence
Finding
The declared description presents this skill as a full-featured Meituan travel concierge handling travel product discovery and planning. However, the supplied code chunk does not implement any travel-related business logic such as searching hotels, flights, trains, tickets, deals, reviews, or itinerary management. Instead, it solely performs account authorization setup: installing/finding a passport CLI, checking cached credentials, requesting authorization links, and generating a QR code for login. While authentication could be a supporting component of a travel skill, this code chunk by itself materially differs from the declared primary purpose and exposes undeclared capabilities related to auth/token handling.

Chaining Abuse

High
Category
Tool Misuse
Content
```
macOS(推荐 nvm):
  curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.1/install.sh | bash
  nvm install 18

Windows:
Confidence
97% confidence
Finding
The `| bash` construct creates an immediate command-execution chain from untrusted network content to a local shell. In the context of a skill consumed by agents or users, this increases the chance of blindly executing attacker-controlled code and is particularly dangerous because it normalizes unsafe command-chaining behavior in setup instructions.

Natural-Language Policy Violations

Medium
Confidence
95% confidence
Finding
The description is written as an official user-facing instruction in Chinese and presents the skill as the user's travel assistant without indicating any option to use another language. This can constitute a language/locale policy violation because the skill appears to assume a fixed language rather than offering user opt-in or choice.

Rp1

Medium
Category
MCP Rug Pull
Confidence
93% confidence
Finding
The skill allows execution via `npx` without a pinned package version, which can fetch whatever version is current at runtime. This creates a supply-chain risk: a compromised upstream package, malicious update, or unexpected breaking change could execute arbitrary code during auth or query flows.

Natural-Language Policy Violations

Medium
Confidence
90% confidence
Finding
The skill's usage boundaries, prompts, waiting messages, error handling, and output requirements are all specified only in Chinese, with no indication that users may choose another language. For an end-user-facing skill, this reads as a forced locale/language behavior rather than an opt-in or clearly justified regional limitation.

Rp1

Medium
Category
MCP Rug Pull
Confidence
98% confidence
Finding
The command `npx @meituan-travel/ht-ai-open@latest query` explicitly tracks `latest`, guaranteeing unreviewed code updates at execution time. In a skill that handles authentication tokens and user travel queries, this materially increases the risk of supply-chain compromise, token theft, or silent behavior changes.

Ssd 3

Medium
Confidence
96% confidence
Finding
The skill mandates forwarding the user's complete original input to an external CLI, which may include unnecessary personal data, credentials, health details, or unrelated context beyond the minimum needed for travel search. This violates data minimization principles and creates an avoidable disclosure path to downstream tooling and services.

Vague Triggers

Medium
Confidence
92% confidence
Finding
The skill is designed to be automatically invoked whenever another skill command template contains ${passport_token}, with 'Token 透明注入,无需用户感知'. That creates a cross-skill privilege boundary issue: any dependent skill that can declare or inject this placeholder may silently trigger credential acquisition and use a user token without a clear, per-use authorization step.

Vague Triggers

Medium
Confidence
90% confidence
Finding
The skill is designed to be automatically invoked whenever another skill command template contains ${passport_token}, with 'Token 透明注入,无需用户感知'. That creates a cross-skill privilege boundary issue: any dependent skill that can declare or inject this placeholder may silently trigger credential acquisition and use a user token without a clear, per-use authorization step.

Missing User Warnings

Medium
Confidence
84% confidence
Finding
The document states that `auth get-code` writes a session file under `/tmp`, but does not describe the sensitivity of its contents or local file-handling risks. Temporary directories are shared attack surfaces on many systems, and predictable or recoverable session artifacts can be read, raced, or retained longer than intended if permissions and cleanup are not tightly controlled.

Missing User Warnings

Medium
Confidence
88% confidence
Finding
The document instructs the LLM to replace `${passport_token}` with the real token in the final command before execution. When secrets are embedded directly into command lines or headers, they can be exposed through shell history, process listings, debugging output, agent logs, or downstream tooling, especially in multi-layer agent execution environments.

Context-Inappropriate Capability

Medium
Confidence
96% confidence
Finding
The script automatically performs `npm install -g qrcode` at runtime if the module is missing, which changes the host environment and pulls code from the package registry without explicit user approval. In an agent-skill context, this expands the trust boundary from QR generation to package installation and creates supply-chain and persistence risk if the registry, package, or execution environment is compromised.

Missing User Warnings

Medium
Confidence
97% confidence
Finding
The script installs a global npm package without any interactive confirmation or prior user-facing consent, causing unexpected side effects on the system where the skill runs. This is risky because a seemingly simple utility script can mutate the environment, execute package lifecycle scripts, and fetch untrusted external code during normal operation.

External Script Fetching

Low
Category
Supply Chain
Content
```
macOS(推荐 nvm):
  curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.40.1/install.sh | bash
  nvm install 18

Windows:
Confidence
95% confidence
Finding
The documentation recommends `curl ... | bash` to fetch and execute a remote installer script directly from GitHub. This pattern bypasses integrity verification and causes arbitrary code execution if the remote content, transport, repository, or user environment is compromised.

Natural-Language Policy Violations

Low
Confidence
91% confidence
Finding
The script emits a fixed Chinese message (`qrcode 模块未安装,正在自动安装...`) to users with no language or locale selection. This can violate language/locale policy when the skill is not explicitly documented as Chinese-only or region-specific.

Missing User Warnings

Low
Confidence
82% confidence
Finding
This code invokes a helper to generate a QR code image and then returns the resulting file path, which implies a local file write. In this script, there is no explicit warning, confirmation, or user-facing disclosure that a file will be created on disk.

Static analysis

Detected: suspicious.generated_source_template_injection

User-controlled placeholder is embedded directly into generated source code.

Critical
Code
suspicious.generated_source_template_injection
Location
SKILL.md:86