T09 · Insecure Skill Coding Practices
Error
- Location
- scripts/common.js:160
- Finding
- Global Basic Auth credentials may be disclosed to unrelated Prometheus instances<![CDATA[ ## Vulnerability Details **File Location**: `scripts/common.js:160-169` **Related Request Sites**: `scripts/query.js:27-29`, `55-57`, `86-88`, `108-110`, `140-142`, `166-168`, `196-198`, `224-226`, `249-251`, `274-276`, `300-302`, `331-333`, and `362-364` **Vulnerability Type**: Cross-instance credential disclosure caused by unsafe environment-variable fallback **Risk Level**: High ### Vulnerable Code ```js export function createAuthHeader(instance = null) { const headers = { 'Accept': 'application/json' }; const user = instance?.user || process.env.PROMETHEUS_USER; const password = instance?.password || process.env.PROMETHEUS_PASSWORD; if (user && password) { const auth = Buffer.from(`${user}:${password}`).toString('base64'); headers['Authorization'] = `Basic ${auth}`; } return headers; } ``` Every outgoing request passes its selected instance to this function, for example: ```js const response = await fetch(`${url}?${params}`, { headers: createAuthHeader(targetInstance) }); ``` ### Technical Analysis When a configured Prometheus instance does not have its own `user` or `password`, `createAuthHeader()` silently substitutes the global `PROMETHEUS_USER` and `PROMETHEUS_PASSWORD` values. This behavior crosses instance trust boundaries. In a multi-instance deployment, global credentials intended for a legacy or trusted Prometheus endpoint can consequently be attached to requests sent to another configured endpoint. That other endpoint may be operated by a different party, compromised, or deliberately configured by an attacker. HTTP Basic Auth only Base64-encodes credentials; it does not encrypt them. If the destination URL uses plain HTTP, a network observer may also recover the credentials in transit. ### Attack Path 1. The victim environment or loaded `.env` file defines `PROMETHEUS_USER` and `PROMETHEUS_PASSWORD`. 2. An attacker adds, modifies, or convinces the user to configure a Prometheus instance who ...[truncated 1180 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions 1. Do not use global credentials when an explicit instance object is supplied: ```js export function createAuthHeader(instance) { const headers = { Accept: 'application/json' }; const user = instance?.user; const password = instance?.password; if (user && password) { const auth = Buffer.from(`${user}:${password}`).toString('base64'); headers.Authorization = `Basic ${auth}`; } return headers; } ``` 2. Preserve legacy environment-variable support only by converting those variables into the single fallback instance inside `loadConfig()`. Do not make them implicit credentials for file-configured instances. 3. Validate that credentials are either both present or both absent for each instance. 4. Require HTTPS for authenticated remote instances. If plain HTTP must be supported for localhost or isolated networks, require an explicit insecure-transport opt-in and display a warning. 5. Document credential scoping clearly and add tests confirming that an unauthenticated instance never receives environment credentials. 6. Consider supporting per-instance environment-variable references or a secret store instead of embedding credentials directly in configuration. ]]>
