Back to skill

Security audit

CORS Tester

Security checks for vulnerabilities and agentic risk

Overview

This is a straightforward CORS testing skill with user-directed network probes and config generation, and I found no hidden persistence, credential access, or deceptive behavior.

Install only if you need a CLI-style CORS tester. Expect it to contact the URLs you provide, including multiple audit probes, and avoid running it against third-party systems without permission. Treat generated server configuration as a draft: review it, validate it with the target framework's config checker, and do not feed attacker-controlled values into the generator.

Vulnerability Patterns
  • Insecure Skill Coding PracticesFinds exploitable flaws such as hardcoded secrets or command injection
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • Embedded Malicious CodeShips malicious scripts inside the skill and executes them locally
Findings (2)

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/cors_tester.py:225
Finding
Unsafe Input Interpolation in Generated Server Configurations<![CDATA[ ## Vulnerability Details **File Location**: `scripts/cors_tester.py:225-257`, `scripts/cors_tester.py:278-297` **Vulnerability Type**: Configuration and code injection through unsafe string interpolation **Risk Level**: Medium ### Vulnerable Code ```python "nginx": lambda o, m, h, c, ma: dedent(f"""\ # Nginx CORS configuration location / {{ if ($request_method = 'OPTIONS') {{ add_header 'Access-Control-Allow-Origin' '{o}'; add_header 'Access-Control-Allow-Methods' '{m}'; add_header 'Access-Control-Allow-Headers' '{h}'; {"add_header 'Access-Control-Allow-Credentials' 'true';" if c else ""} add_header 'Access-Control-Max-Age' {ma}; add_header 'Content-Type' 'text/plain; charset=utf-8'; add_header 'Content-Length' 0; return 204; }} add_header 'Access-Control-Allow-Origin' '{o}'; {"add_header 'Access-Control-Allow-Credentials' 'true';" if c else ""} }}"""), "apache": lambda o, m, h, c, ma: dedent(f"""\ # Apache .htaccess CORS configuration <IfModule mod_headers.c> Header set Access-Control-Allow-Origin "{o}" Header set Access-Control-Allow-Methods "{m}" Header set Access-Control-Allow-Headers "{h}" {"Header set Access-Control-Allow-Credentials true" if c else ""} Header set Access-Control-Max-Age "{ma}" </IfModule>"""), ``` ```python "rails": lambda o, m, h, c, ma: dedent(f"""\ # config/initializers/cors.rb Rails.application.config.middleware.insert_before 0, Rack::Cors do allow do origins {', '.join(f"'{x.strip()}'" for x in o.split(','))} resource '*', headers: :any, methods: [{', '.join(f':{x.strip().lower()}' for x in m.split(','))}], credentials: {'true' if c else 'false'}, max_age: {ma} end end"""), } def cmd_config(args): framework = args.framework if framework not in ...[truncated 3037 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Parse origins as structured URLs and allow only expected schemes such as `https` and, where explicitly required, `http`. 2. Reject origin values containing control characters, whitespace outside valid URL syntax, quotation marks, semicolons, braces, backticks, or line breaks. 3. Validate methods against an explicit allowlist of legitimate HTTP method tokens. 4. Validate header names against the HTTP field-name token grammar rather than accepting arbitrary text. 5. Use framework-specific string serialization instead of manually adding quotation marks. For Rails, generate valid escaped Ruby string literals. 6. Do not rely on generic escaping across all frameworks; Nginx, Apache, and Ruby have different grammars. 7. Refuse wildcard origins when credentials are enabled, or require an explicit override with a security warning. 8. Add negative tests using quotation marks, CR/LF characters, semicolons, braces, and embedded framework directives. 9. Clearly state that generated output must be reviewed and validated with the target server's configuration checker before deployment. ]]>

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/cors_tester.py:25
Finding
Case-Sensitive CORS Header Parsing Can Produce Audit False Negatives<![CDATA[ ## Vulnerability Details **File Location**: `scripts/cors_tester.py:25-66`, `scripts/cors_tester.py:94-113`, `scripts/cors_tester.py:166-185` **Vulnerability Type**: Incorrect handling of case-insensitive HTTP response header names **Risk Level**: Medium ### Vulnerable Code ```python resp_headers = dict(resp.headers) # CORS headers cors_keys = [ "Access-Control-Allow-Origin", "Access-Control-Allow-Credentials", "Access-Control-Expose-Headers", "Access-Control-Allow-Methods", "Access-Control-Allow-Headers", "Access-Control-Max-Age", "Vary", ] found_any = False for key in cors_keys: val = resp_headers.get(key) if val: found_any = True print(f" {key}: {val}") if not found_any: print(" ⚠ No CORS headers found in response.") print(" The server may not support CORS or doesn't allow this origin.") else: acao = resp_headers.get("Access-Control-Allow-Origin", "") ``` ```python resp_headers = dict(resp.headers) status = resp.status if hasattr(resp, "status") else resp.code acao = resp_headers.get("Access-Control-Allow-Origin", "") acam = resp_headers.get("Access-Control-Allow-Methods", "") acah = resp_headers.get("Access-Control-Allow-Headers", "") acma = resp_headers.get("Access-Control-Max-Age", "") acac = resp_headers.get("Access-Control-Allow-Credentials", "") ``` ```python resp_headers = dict(resp.headers) acao = resp_headers.get("Access-Control-Allow-Origin", "") acac = resp_headers.get("Access-Control-Allow-Credentials", "") vary = resp_headers.get("Vary", "") if acao == test_origin: issues.append(f"CRITICAL: Server reflects arbitrary origin '{test_origin}' — origin reflection vulnerability") if acac and acac.lower() == "true": issues.append(f"CRITICAL: Credentials allowed with reflected origin '{test_origin}' — full CORS bypass") if acao == "*": if acac and acac.lower() == "true": issues.append("HIGH: Wildcard origin (*) with credentials — browsers ...[truncated 2218 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Preserve the case-insensitive header interface and query it directly: ```python acao = resp.headers.get("Access-Control-Allow-Origin", "") acac = resp.headers.get("Access-Control-Allow-Credentials", "") vary = resp.headers.get("Vary", "") ``` 2. Alternatively, normalize all field names before lookup: ```python resp_headers = {name.lower(): value for name, value in resp.headers.items()} acao = resp_headers.get("access-control-allow-origin", "") ``` 3. Apply one shared normalization helper consistently in the `test`, `preflight`, and `audit` commands. 4. Parse `Vary` as a comma-separated, case-insensitive token list rather than using the case-sensitive expression `"Origin" not in vary`. 5. Add unit tests for canonical, lowercase, uppercase, and mixed-case CORS field names. 6. Add regression tests confirming that reflected origins and credential-enabled policies are detected regardless of header capitalization. ]]>
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
Findings (6)

Lp3

Medium
Category
MCP Least Privilege
Confidence
88% confidence
Finding
The skill clearly describes and demonstrates live network access to arbitrary URLs, but it declares no explicit tool scope or permissions. In an agent environment, this creates a capability mismatch that can enable unintended outbound requests and weakens policy enforcement, review, and user awareness about network use.

External Transmission

Medium
Category
Data Exfiltration
Content
```bash
# Test CORS headers on a URL
python3 scripts/cors_tester.py test https://api.example.com/data --origin https://myapp.com

# Test preflight (OPTIONS) request
python3 scripts/cors_tester.py preflight https://api.example.com/data --origin https://myapp.com --method POST --header "Content-Type"
Confidence
50% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

External Transmission

Medium
Category
Data Exfiltration
Content
```bash
# Test CORS headers on a URL
python3 scripts/cors_tester.py test https://api.example.com/data --origin https://myapp.com

# Test preflight (OPTIONS) request
python3 scripts/cors_tester.py preflight https://api.example.com/data --origin https://myapp.com --method POST --header "Content-Type"
Confidence
50% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

External Transmission

Medium
Category
Data Exfiltration
Content
```bash
# Test CORS headers on a URL
python3 scripts/cors_tester.py test https://api.example.com/data --origin https://myapp.com

# Test preflight (OPTIONS) request
python3 scripts/cors_tester.py preflight https://api.example.com/data --origin https://myapp.com --method POST --header "Content-Type"
Confidence
50% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Missing User Warnings

Low
Confidence
78% confidence
Finding
This code performs outbound HTTP requests to user-specified targets, sending request metadata such as the supplied Origin header. While the script's purpose is testing CORS, the code itself does not include an explicit warning, confirmation, or disclosure that it will contact remote servers and transmit these values.

Missing User Warnings

Low
Confidence
88% confidence
Finding
The audit command automatically sends several test requests, including origins like 'https://evil.com' and a preflight OPTIONS probe, to the target URL. Although this behavior aligns with the audit feature, there is no clear user warning in code comments or CLI help that the tool will actively probe the remote service in this way.

Static analysis

No suspicious patterns detected.