T09 · Insecure Skill Coding Practices
- Location
scripts/vendor/weryai-text/cli.js:11- Finding
Unrestricted API endpoint override can disclose credentials and request content
- Content
View full analysis
Vulnerability Details
File Location:
scripts/vendor/weryai-text/cli.js:11-15;scripts/vendor/weryai-core/client.js:14-17, 39-43
Vulnerability Type: Unvalidated service endpoint configuration causing credential and data disclosure
Risk Level: HighVulnerable Code
From
scripts/vendor/weryai-text/cli.js:js const ctx = { apiKey: process.env.WERYAI_API_KEY || '', baseUrl: process.env.WERYAI_BASE_URL || 'https://api.weryai.com', verbose: flags.verbose, dryRun: flags.dryRun, requestTimeoutMs: Number(process.env.WERYAI_REQUEST_TIMEOUT_MS) || 30_000, };From
scripts/vendor/weryai-core/client.js:js const url = `${baseUrl}${path}`; const headers = { Authorization: `Bearer ${apiKey}`, 'Content-Type': 'application/json', };js const res = await fetch(url, { method, headers, body: body ? JSON.stringify(body) : undefined, signal: controller.signal, });Technical Analysis
The destination URL is derived directly from the
WERYAI_BASE_URLenvironment variable without URL validation, an HTTPS requirement, or a trusted-host allowlist. The HTTP client then sends theWERYAI_API_KEYas a bearer credential to that destination.For write requests, the body also contains the generated chat messages, including the user's prompt, source material, campaign details, and other supplied options. Therefore, control over the process environment is sufficient to redirect credentials and request content to an arbitrary endpoint.
This is a trust-boundary failure: a security-sensitive credential is attached to requests whose origin can be changed through untrusted configuration. A plaintext
http://destination is also accepted, allowing exposure through network interception.Attack Path
- An attacker gains the ability to influence the environment of the process invoking the skill, such as through a compromised launcher, CI configuration, shell profile, container configuration, or deployment manifest. ...[truncated 1160 chars]
- Remediation
View remediation
Remediation Suggestions
- Remove the endpoint override in production and use a fixed WeryAI API origin where possible.
- If an override is operationally necessary, parse it with
new URL()and require:- The
https:protocol. - An exact trusted-host allowlist.
- An expected port.
- No embedded username or password.
- The
- Reject malformed URLs and unapproved hosts before constructing the client.
- Attach the authorization header only after confirming that the final request origin is trusted.
- Configure redirect behavior defensively. Reject cross-origin redirects or ensure credentials are never forwarded to a different origin.
- Separate development credentials from production credentials and issue least-privilege, revocable API keys.
- Document
WERYAI_BASE_URLas security-sensitive configuration and prevent untrusted users or jobs from setting it. - Add automated tests confirming rejection of HTTP URLs, lookalike domains, embedded credentials, unexpected ports, and cross-origin redirects.
A hardened configuration could follow this pattern:
js const allowedOrigins = new Set(['https://api.weryai.com']); const configuredUrl = new URL( process.env.WERYAI_BASE_URL || 'https://api.weryai.com' ); if ( configuredUrl.protocol !== 'https:' || !allowedOrigins.has(configuredUrl.origin) || configuredUrl.username || configuredUrl.password ) { throw new Error('Untrusted WeryAI API endpoint.'); }
