T09 · Insecure Skill Coding Practices
- Location
scripts/log-trade.sh:5- Finding
Unsafe Trade Metadata Interpolation into JSON and jq Filter
- Content
View full analysis
"${TRADES_FILE}.tmp" && mv "${TRADES_FILE}.tmp" "$TRADES_FILE" else echo "[$TRADE]" > "$TRADES_FILE" fi ``` ### Technical Analysis All six command-line arguments are interpolated into a JSON document without type validation or JSON escaping. The resulting document is subsequently interpolated into the jq program: ```bash jq ". += [$TRADE]" ... ``` Consequently, quotes, backslashes, control characters, jq operators, or malformed numeric expressions supplied through the arguments can change the jq filter's syntax or make the generated journal invalid. `AMOUNT_USD` and `PRICE` are especially exposed because they are inserted as raw expressions rather than strings. This flaw does not, by itself, establish shell command execution: shell metacharacters introduced by ordinary parameter expansion are not recursively evaluated by Bash. The demonstrated security boundary is journal integrity. Crafted input can cause jq processing to fail, corrupt the journal, or produce unintended jq data transformations. The fallback branch is also unsafe because it writes the manually constructed, unvalidated value directly to `trades.json`. ### Attack Path 1. An attacker-controlled token name, transaction identifier, reason, amount, or price reaches the Agent through a t ...[truncated 1189 chars]- Remediation
View remediation
&2; exit 1 ;; esac jq -e -n --argjson value "$AMOUNT_USD" '$value | numbers' >/dev/null jq -e -n --argjson value "$PRICE" '$value | numbers' >/dev/null TRADES_FILE="$(dirname "$0")/../data/trades.json" TIMESTAMP=$(date -u +"%Y-%m-%dT%H:%M:%SZ") TMP_FILE=$(mktemp "${TRADES_FILE}.tmp.XXXXXX") trap 'rm -f "$TMP_FILE"' EXIT if [ -f "$TRADES_FILE" ]; then jq -e 'type == "array"' "$TRADES_FILE" >/dev/null else printf '[]\n' > "$TRADES_FILE" fi jq \ --arg timestamp "$TIMESTAMP" \ --arg action "$ACTION" \ --arg token "$TOKEN" \ --argjson amount_usd "$AMOUNT_USD" \ --argjson price "$PRICE" \ --arg reason "$REASON" \ --arg tx "$TX" \ '. += [{ timestamp: $timestamp, action: $action, token: $token, amount_usd: $amount_usd, price: $price, reason: $reason, tx: $tx }]' "$TRADES_FILE" > "$TMP_FILE" mv "$TMP_FILE" "$TRADES_FILE" trap - EXIT ``` ]]>
