T09 · Insecure Skill Coding Practices
Warning
- Location
- scripts/prepare_data.mjs:25
- Finding
- API Credential Can Be Transmitted to an Arbitrary Configured Server## Vulnerability Details **File Location**: `scripts/prepare_data.mjs`, lines 25-81 **Vulnerability Type**: Unvalidated credential destination **Risk Level**: Medium ### Vulnerable Code ```js const BASE = process.env.SENTISENSE_BASE_URL || "https://app.sentisense.ai"; const KEY = process.env.SENTISENSE_API_KEY; ``` ```js async function get(path, { allowNullData = false, tolerate400 = false, tolerate404 = false, optional = false, } = {}) { // ... let response; try { response = await fetch(`${BASE}${path}`, { headers: { "X-SentiSense-API-Key": KEY, Accept: "application/json", "User-Agent": UA }, }); } catch (cause) { fail(`network error calling ${path}`, String(cause && cause.message ? cause.message : cause)); } } ``` ### Technical Analysis The script obtains the sensitive `SENTISENSE_API_KEY` from the environment and attaches it to every request through the `X-SentiSense-API-Key` header. Although the intended destination is `https://app.sentisense.ai`, the undocumented `SENTISENSE_BASE_URL` environment variable can replace the complete origin. No URL parsing, HTTPS enforcement, or hostname allowlist is applied before the credential is sent. Consequently, the script can transmit the API key to any HTTP or HTTPS server selected through the process environment. This behavior exceeds the minimum privileges required by the declared functionality, which only requires authenticated requests to the official SentiSense API. ### Attack Path 1. An attacker, compromised launcher, CI configuration, wrapper script, or poisoned environment sets `SENTISENSE_BASE_URL` to an attacker-controlled server. 2. The legitimate user supplies `SENTISENSE_API_KEY` and invokes `scripts/prepare_data.mjs` as documented. 3. The script constructs API URLs from the attacker-controlled base URL. 4. It sends the victim's API key in the `X-SentiSense-API-Key` header to the attacker-controlled ...[truncated 611 chars]
- Remediation
- ## Remediation Suggestions - Remove `SENTISENSE_BASE_URL` from production code and use a fixed API origin. - If endpoint substitution is required for development, place it behind an explicit development-only option that is disabled by default. - Parse the destination with `new URL()` and require: - The `https:` protocol. - An exact hostname match for `app.sentisense.ai`. - An approved port and base path. - No embedded username or password. - Apply the API-key header only after validating the destination origin. - Disable or carefully validate redirects for authenticated requests so credentials cannot reach an unapproved origin. - Document every supported network destination and security-sensitive environment variable. - Add automated tests confirming that HTTP URLs and unapproved hosts are rejected before any request is made.
