T09 · Insecure Skill Coding Practices
Warning
- Location
- scripts/analyzer.py:30
- Finding
- Unvalidated Marketplace Input Allows Requests to Attacker-Controlled Hosts## Vulnerability Details **File Locations**: - `scripts/analyzer.py:30-40` - `scripts/keyword_extractor.py:17-44` - `scripts/competitor_spy.py:15-26` **Vulnerability Type**: User-controlled network destination **Risk Level**: Medium ### Vulnerable Code `scripts/analyzer.py:30-40`: ```python def fetch_listing(asin, marketplace="com"): """Fetch an Amazon listing page.""" url = f"https://www.amazon.{marketplace}/dp/{asin}" headers = { "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36", "Accept-Language": "en-US,en;q=0.9", } req = urllib.request.Request(url, headers=headers) try: with urllib.request.urlopen(req, timeout=15) as resp: return resp.read().decode("utf-8", errors="ignore") ``` `scripts/keyword_extractor.py:17-44`: ```python def get_amazon_suggestions(keyword, marketplace="com"): """Get Amazon search autocomplete suggestions.""" encoded = urllib.parse.quote(keyword) url = ( f"https://completion.amazon.{marketplace}/api/2017/suggestions" f"?session-id=000-0000000-0000000" f"&customer-id=000000000" f"&request-id=000000000" f"&page-type=Gateway" f"&lop=en_US" f"&site-variant=desktop" f"&client-info=amazon-search-ui" f"&mid=ATVPDKIKX0DER" f"&alias=aps" f"&prefix={encoded}" f"&event=onKeyPress" f"&limit=11" f"&fb=1" f"&suggestion-type=KEYWORD" ) headers = { "User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7)", "Accept": "application/json", } try: req = urllib.request.Request(url, headers=headers) with urllib.request.urlopen(req, timeout=10) as resp: data = json.loads(resp.read().decode()) ``` `scripts/competitor_spy.py:15-26`: ```python def search_amazon(q ...[truncated 2725 chars]
- Remediation
- ## Remediation Suggestions Replace hostname interpolation with a fixed mapping from accepted marketplace identifiers to exact trusted hosts: ```python MARKETPLACE_HOSTS = { "com": "www.amazon.com", "co.uk": "www.amazon.co.uk", "de": "www.amazon.de", "fr": "www.amazon.fr", "it": "www.amazon.it", "es": "www.amazon.es", "ca": "www.amazon.ca", "com.au": "www.amazon.com.au", } def marketplace_host(marketplace): try: return MARKETPLACE_HOSTS[marketplace] except KeyError: raise ValueError("Unsupported Amazon marketplace") ``` Maintain a separate allowlist for autocomplete hosts where necessary. Additional hardening should include: - Rejecting marketplace values not present in the allowlist. - Parsing the final URL and verifying its exact hostname before each request. - Preventing redirects to hosts outside the allowlist with a restrictive redirect handler. - Applying response-size limits before loading remote content into memory. - Avoiding checks based only on hostname prefixes or the presence of the word `amazon`.
