T09 · Insecure Skill Coding Practices
Warning
- Location
- scripts/curl_examples.sh:98
- Finding
- Unescaped User-Controlled URL Allows JSON Request Injection<![CDATA[ ## Vulnerability Details **File Location**: `scripts/curl_examples.sh`, lines 98-105 **Vulnerability Type**: Improper encoding of user-controlled data in a JSON request **Risk Level**: Medium ### Vulnerable Code ```bash --data-binary @- <<JSON { "video_url": "${VIDEO_SOURCE}", "sourceLanguage": "${SOURCE_LANGUAGE}", "targetLanguage": "${TARGET_LANGUAGE}", "show": ${SHOW}, "bilingual": ${BILINGUAL} } JSON ``` ### Technical Analysis `VIDEO_SOURCE` originates from the script's first command-line argument. When it begins with `http://` or `https://`, the value is interpolated directly into a JSON heredoc without JSON escaping or serialization. The URL validation only checks its scheme. It does not reject or encode quotation marks, backslashes, control characters, or newlines. A crafted value can therefore terminate the `video_url` string and inject additional JSON properties or make the request body syntactically invalid. For example, an input containing a quotation mark followed by additional JSON syntax could produce duplicate or attacker-selected request fields. Whether injected duplicate fields override the legitimate fields depends on the remote service's JSON parser. Even when property injection is not accepted, malformed JSON can reliably disrupt job submission. This is JSON injection rather than shell command injection. Shell metacharacters inside `VIDEO_SOURCE` are expanded as heredoc data and are not reevaluated as shell commands. ### Attack Path 1. An attacker supplies a crafted first argument that starts with `http://` or `https://` and contains JSON metacharacters. 2. The script classifies the argument as a remote video URL. 3. The crafted value is inserted verbatim between JSON quotation marks. 4. The generated request body becomes malformed or contains injected properties. 5. `curl` submits that body to `/video-trans/orchestrate` using the configured bearer token. 6. Depending on server-side parsing and validation, the re ...[truncated 661 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions Construct the request body with a JSON serializer instead of interpolating values into a heredoc. For example, use `jq`: ```bash REQUEST_BODY="$( jq -n \ --arg video_url "${VIDEO_SOURCE}" \ --arg sourceLanguage "${SOURCE_LANGUAGE}" \ --arg targetLanguage "${TARGET_LANGUAGE}" \ --argjson show "${SHOW}" \ --argjson bilingual "${BILINGUAL}" \ '{ video_url: $video_url, sourceLanguage: $sourceLanguage, targetLanguage: $targetLanguage, show: $show, bilingual: $bilingual }' )" SUBMIT_RESP="$( curl -sS -X POST "${BASE_URL}/video-trans/orchestrate" \ -H "Authorization: Bearer ${API_KEY}" \ -H "Content-Type: application/json" \ --data-binary "${REQUEST_BODY}" )" ``` Alternatively, use Python's `json` module, which is already listed as a runtime requirement, to serialize the complete object. Additional hardening should include: 1. Parse and validate the URL with a dedicated URL parser. 2. Permit only the intended `http` and `https` schemes. 3. Reject control characters in URL input. 4. Treat language and Boolean validation as defense in depth rather than as a substitute for JSON serialization. 5. Add tests using URLs containing quotation marks, backslashes, Unicode characters, and newlines to verify that generated request bodies remain valid JSON. ]]>
