Back to skill

Security audit

js-hanoi-air

Security checks for vulnerabilities and agentic risk

Overview

This AQI skill does what it claims, but it contains an exposed WAQI API token and sends city lookups to WAQI.

Before installing, be aware that city queries are sent to the WAQI API and the bundled WAQI token is exposed in the source. Prefer a version that uses a user-provided secret from the environment, rotates the exposed token, and adds request timeouts and response-size limits.

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

Warning
Location
aqi-hanoi.js:10
Finding

Hardcoded WAQI API Credential Exposed in Source Code and Request URL

Content
View full analysis
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Note
Location
aqi-hanoi.js:35
Finding

Unbounded Remote Response Buffering and Missing Request Timeout

Content
View full analysis
{ let data = ''; res.on('data', (chunk) => data += chunk); res.on('end', () => { ``` No response-size limit or request timeout is configured elsewhere in the request flow. ### Technical Analysis The implementation appends every response chunk to an in-memory string until the remote server ends the response. It does not impose a maximum response size, validate the response's `Content-Length`, or abort after a safe threshold. The request also lacks an explicit timeout. A malfunctioning or compromised upstream service could return an excessively large response or keep the connection open for a prolonged period. A trusted local proxy or other infrastructure component capable of influencing the HTTPS connection could produce the same effect. Because the response is concatenated repeatedly, memory consumption can grow with the response body and may also incur additional allocation overhead. This behavior creates a denial-of-service risk for the Node.js process. ### Attack Path 1. The Skill sends a request to the configured WAQI endpoint. 2. The upstream service, or infrastructure able to influence the trusted connection, returns an oversized response or streams data without terminating promptly. 3. The `data` event handler continuously appends chunks to the in-memory string. 4. The process consumes increasing memory or remains occupied waiting for completion. 5. The process may become unresponsive, be terminated by the operating system, or prevent the Skill from returning a result. Exploitation ordinarily requires control of the upstream service or a trusted network component because HTTPS protects the connection against a basic unauthenticated network attacker. ### Impact Assessment The primary impact is ...[truncated 392 chars]
Remediation
View remediation
{ const contentLength = Number(res.headers['content-length'] || 0); if (contentLength > MAX_RESPONSE_BYTES) { res.destroy(new Error("Response exceeds maximum size")); return; } if (res.statusCode !== 200) { res.resume(); console.log(JSON.stringify({ status: "error", message: `Unexpected HTTP status: ${res.statusCode}` })); return; } let size = 0; let data = ''; res.on('data', (chunk) => { size += chunk.length; if (size > MAX_RESPONSE_BYTES) { res.destroy(new Error("Response exceeds maximum size")); return; } data += chunk; }); res.on('end', () => { // Parse and validate the bounded response. }); }); req.setTimeout(10000, () => { req.destroy(new Error("WAQI request timed out")); }); req.on('error', (err) => { console.log(JSON.stringify({ status: "error", message: err.message })); }); ``` ]]>
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • MCP Tool PoisoningHidden Instructions, Unicode Deception, Parameter Description Injection
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
Findings (6)

Tp4

High
Category
MCP Tool Poisoning
Confidence
92% confidence
Finding

The documented behavior does not fully match the described capability and transparency expectations: the skill appears to rely on a hardcoded external API token, sends user-provided city data to a third-party service, and exposes CLI-style behavior not clearly disclosed in metadata. While this is not direct code execution, hidden credentials and undisclosed external data flow can mislead operators, complicate review, and create supply-chain or privacy risk if the skill is deployed in a managed agent environment.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The natural-language instructions and description are presented in Vietnamese, but the skill does not indicate that this language choice is optional or limited to a Vietnam-specific audience. This can violate language/locale policy when a skill implicitly forces one language without user opt-in.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
97% confidence
Finding

The script embeds a live WAQI API token directly in source code and automatically transmits it in every outbound request. Hardcoded secrets are easily exposed through source distribution, logs, or repository history, allowing unauthorized reuse of the token, quota exhaustion, billing impact, or account abuse.

Content

No source excerpt is available for this finding.

External Transmission

Medium
Category
Data Exfiltration
Confidence
60% 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 · aqi-hanoi.js (reported line 33)May include surrounding context.

js
function fetchAQI(cityInput) {
    const citySlug = cityMap[cityInput.toLowerCase()] || cityInput.toLowerCase();
    const url = `https://api.waqi.info/feed/${encodeURIComponent(citySlug)}/?token=${WAQI_TOKEN}`;

    https.get(url, (res) => {
        let data = '';

Missing User Warnings

Low
Category
Not specified by scanner
Confidence
89% confidence
Finding

The skill omits a clear user-facing notice that city queries are transmitted to an external API. This weakens informed consent and privacy transparency, especially in agent ecosystems where users may assume processing is local unless otherwise stated.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Low
Category
Not specified by scanner
Confidence
81% confidence
Finding

Natural-language strings and comments indicate the skill is designed around Vietnamese output and terminology, but there is no indication that users can choose another language or explicitly opt into Vietnamese. This can violate language/locale policy when a skill forces a specific language by default.

Content

No source excerpt is available for this finding.

Static analysis

No suspicious patterns detected.