Back to skill

Security audit

Uptime Checker

Security checks for vulnerabilities and agentic risk

Overview

This uptime-checking skill does what it claims, but its documented Authorization-header support can expose sensitive tokens through command-line use and default redirect handling.

Install only if you are comfortable with it making outbound requests to URLs you provide. Avoid passing real bearer tokens, cookies, or API keys in --header unless you trust the endpoint and redirects; prefer disabling redirects or using non-sensitive health-check credentials. Store history files in a deliberate location because they may retain endpoint URLs, statuses, timings, and errors.

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 (1)

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/uptime_check.py:34
Finding
Sensitive Custom Headers May Be Disclosed Through Cross-Origin Redirects<![CDATA[ ## Vulnerability Details **File Location**: `scripts/uptime_check.py`, lines 34–54 **Vulnerability Type**: Sensitive credential disclosure through unrestricted redirect handling **Risk Level**: Medium ### Vulnerable Code ```python req_headers = {"User-Agent": "UptimeChecker/1.0"} if headers: req_headers.update(headers) request = urllib.request.Request(url, method=method, headers=req_headers) # SSL context ctx = None if url.startswith("https://"): ctx = ssl.create_default_context() if not verify_ssl: ctx.check_hostname = False ctx.verify_mode = ssl.CERT_NONE start = time.monotonic() try: if not follow_redirects: # Build opener without redirect handler class NoRedirect(urllib.request.HTTPRedirectHandler): def redirect_request(self, req, fp, code, msg, hdrs, newurl): result["redirect_url"] = newurl return None opener = urllib.request.build_opener(NoRedirect, urllib.request.HTTPSHandler(context=ctx) if ctx else urllib.request.HTTPHandler()) response = opener.open(request, timeout=timeout) else: response = urllib.request.urlopen(request, timeout=timeout, context=ctx) ``` ### Technical Analysis The checker accepts arbitrary custom request headers and attaches them directly to the `urllib.request.Request`. The documented usage explicitly supports authentication headers such as: ```text --header "Authorization:Bearer token123" ``` Redirects are followed by default through `urllib.request.urlopen`, but the code does not check whether a redirect remains on the same origin. It also does not remove sensitive headers when the destination scheme, hostname, or port changes. Because user-provided headers are regular request headers, redirect processing may propagate them to the redirected request. Consequently, an endpoint that is compromised, malicious, or capable of controlling its redirect response can direct the checker to another orig ...[truncated 1505 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Implement a custom redirect handler that compares the original and redirected URL origins. 2. Strip sensitive headers whenever the scheme, hostname, or effective port changes. At minimum, remove: - `Authorization` - `Proxy-Authorization` - `Cookie` - API-key headers such as `X-API-Key` - Any caller-designated sensitive headers 3. Prefer disabling redirect following by default when authentication headers are present, unless the user explicitly authorizes cross-origin redirects. 4. Reject redirects to a less secure scheme, particularly HTTPS-to-HTTP redirects. 5. Consider maintaining sensitive headers separately and adding them only to requests whose origin exactly matches the originally requested origin. 6. Add tests covering same-origin redirects, cross-origin redirects, port changes, scheme changes, and sensitive custom headers. A secure policy should follow this pattern: ```python from urllib.parse import urlsplit SENSITIVE_HEADERS = { "authorization", "proxy-authorization", "cookie", "x-api-key", } def same_origin(first_url, second_url): first = urlsplit(first_url) second = urlsplit(second_url) def effective_port(parts): if parts.port is not None: return parts.port return 443 if parts.scheme.lower() == "https" else 80 return ( first.scheme.lower() == second.scheme.lower() and first.hostname == second.hostname and effective_port(first) == effective_port(second) ) class SafeRedirectHandler(urllib.request.HTTPRedirectHandler): def redirect_request(self, req, fp, code, msg, headers, newurl): redirected = super().redirect_request( req, fp, code, msg, headers, newurl ) if redirected is not None and not same_origin(req.full_url, newurl): for name in list(redirected.headers): if name.lower() in SENSITIVE_HEADERS: redirected.remove_heade ...[truncated 191 chars]
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 (3)

Lp3

Medium
Category
MCP Least Privilege
Confidence
91% confidence
Finding
The skill advertises and documents capabilities that perform network access and local file writes, but it does not declare any corresponding tool scope or permissions boundary. This is dangerous because users and hosting systems cannot easily understand or constrain what the skill is allowed to do, increasing the chance of unintended outbound requests or file modifications when the skill is invoked.

Missing User Warnings

Medium
Confidence
90% confidence
Finding
The documentation encourages passing an Authorization header directly on the command line without warning that secrets may be exposed to shell history, process listings, logs, or sent to arbitrary external endpoints. In an uptime-checking context, this is particularly risky because the skill is designed to make outbound requests, so misuse could easily leak bearer tokens to the wrong destination.

Missing User Warnings

Low
Confidence
80% confidence
Finding
The skill documents saving history to a local file but does not warn that files will be created or potentially overwritten. While this appears intended functionality rather than malicious behavior, it can still cause accidental data loss or unexpected persistence of endpoint metadata on disk.

Static analysis

No suspicious patterns detected.