T09 · Insecure Skill Coding Practices
- Location
SKILL.md:101- Finding
OAuth Authorization Code Disclosed to an Uncontrolled External Redirect Endpoint
- Content
View full analysis
Vulnerability Details
File Location:
SKILL.md, lines 101-116
Vulnerability Type: OAuth authorization-code disclosure through an unsafe redirect URI
Risk Level: HighVulnerable Code
markdown ### Step 1 — Verify redirect URL is configured In `shopify.app.toml`: ```toml [auth] redirect_urls = [ "https://example.com" ]If empty, add it and run:
shopify app deploy --forceStep 2 — Open the authorization URL
text https://{SHOPIFY_STORE_DOMAIN}/admin/oauth/authorize?client_id={CLIENT_ID}&scope={SCOPES}&redirect_uri=https://example.com&state=refreshStep 3 — Extract the code from the redirect URL
Browser redirects to
https://example.com/?code=XXXXXX&...Extract thecodevalue (valid for ~60 seconds).text ### Technical Analysis The OAuth procedure instructs the operator to register `https://example.com` as the callback and then initiate an authorization flow using that endpoint. This domain is not shown to be controlled by the Shopify application owner. Consequently, Shopify sends the temporary authorization code, OAuth state, and related query parameters to an external service. An authorization callback must terminate at a verified HTTPS endpoint controlled by the application owner. Using an unrelated placeholder as an operational callback violates this requirement and can disclose credentials through HTTP access logs, monitoring infrastructure, browser history, intermediary services, or parties with access to the destination. The procedure also uses the fixed and predictable state value `refresh`. OAuth state should be generated cryptographically for each authorization attempt, bound to the initiating session, and verified at the callback. A static state value does not provide effective protection against login CSRF or authorization-response substitution. ### Attack Path 1. An operator follows the documented procedure and adds `https://example.c ...[truncated 1464 chars]- Remediation
View remediation
Remediation Suggestions
- Replace
https://example.comwith a verified HTTPS callback endpoint owned and operated by the application owner. - Explicitly warn that example domains are placeholders and must never be deployed as production OAuth callbacks.
- Maintain a strict allowlist of exact callback URLs and reject arbitrary domains, IP addresses, URL user information, unexpected ports, and non-HTTPS schemes.
- Generate a cryptographically random, single-use
statevalue for each authorization request. - Bind the state value to the initiating user session and verify it with a constant-time comparison before processing the callback.
- Exchange the authorization code from a trusted server-side component immediately after callback validation.
- Prevent authorization codes, client secrets, and access tokens from appearing in application logs, analytics systems, error reports, or browser-visible pages.
- Use PKCE where supported, with a fresh verifier and challenge for every authorization attempt.
- Request only the OAuth scopes required for the specific operation rather than the broader suggested scope set.
- Replace
