Back to skill

Security audit

Geoskill: MODIS Product Search

Security checks across malware telemetry and agentic risk

Overview

This is mainly a MODIS lookup skill, but it needs review because it ships hardcoded Earthdata credentials and under-disclosed credential, network, and file-write behavior.

Review this skill before installing. Basic search/show/GEE lookup behavior is local and coherent, but avoid relying on its credential handling as-is: remove or rotate the embedded Earthdata credentials, prefer your own explicit credential setup, and be aware that place lookup may contact geocoding services and cache results locally. Treat --qa output paths as persistent files containing query context.

Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Supply ChainUnpinned Dependencies, External Script Fetching, Obfuscated Code
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
Findings (21)

Lp3

Medium
Category
MCP Least Privilege
Confidence
95% confidence
Finding
The skill advertises no declared permissions while the analyzed behavior indicates access to environment variables, files, network, and shell-like command generation. This creates a transparency and least-privilege problem: users and orchestrators cannot accurately assess what the skill may access or do, increasing the chance of unintended credential exposure, local file interaction, or network use.

Tp4

High
Category
MCP Tool Poisoning
Confidence
98% confidence
Finding
The documented purpose is a local MODIS query tool, but the detected behavior is materially broader: external geocoding, disk writes, generic downloading, unrelated remote-sensing registries, and credential handling including fallback credentials. This mismatch is dangerous because users may invoke the skill expecting a narrow offline lookup while it performs networked or credential-touching operations outside that scope.

Description-Behavior Mismatch

High
Confidence
99% confidence
Finding
The module hardcodes a real-looking Earthdata username and password in `_DEFAULTS`, making the skill capable of authenticating to an external account without user consent. Even if described as a fallback, embedding credentials in source control creates immediate secret exposure, unauthorized account use, and downstream abuse risk.

Context-Inappropriate Capability

High
Confidence
88% confidence
Finding
This skill is presented as a local MODIS product query tool, yet the credential layer also handles OpenAI, CMA, FIRMS, and EOG secrets. That broad credential scope increases attack surface and enables the skill to access unrelated external services, violating least privilege and making abuse harder for users to detect.

Intent-Code Divergence

Medium
Confidence
84% confidence
Finding
The docstring claims passwords are not cached, but `load_user_secrets()` loads them into `_DEFAULTS` and retains them in process memory. This mismatch is dangerous because operators may rely on the stated security property while secrets persist longer than expected and become available to other code paths in the same process.

Description-Behavior Mismatch

High
Confidence
93% confidence
Finding
This file implements full remote download and local file write capability, including resume, retries, overwrite behavior, and batch download, which exceeds the stated purpose of a local MODIS product-search skill. In the context of an agent skill, arbitrary download-to-disk functionality can be repurposed to fetch untrusted content, stage payloads, or write attacker-influenced files to the host filesystem, increasing the blast radius well beyond read-only metadata lookup.

Context-Inappropriate Capability

High
Confidence
95% confidence
Finding
The `_http_get` helper accepts arbitrary URLs and performs outbound HTTP requests without any domain restriction, scheme restriction, or explicit trust boundary enforcement. In an agent environment, that creates a generic network primitive that can be abused for unauthorized external access, data staging, SSRF-like access to internal services if user-controlled URLs are passed, and retrieval of malicious files later written by the caller.

Context-Inappropriate Capability

Medium
Confidence
89% confidence
Finding
The `download` path accesses local credential sources via a vendored helper or `EARTHDATA_USERNAME` even though the tool's main purpose is product lookup. Accessing ambient credentials expands trust unnecessarily and can disclose sensitive usernames in generated output, logs, or downstream agent responses.

Missing User Warnings

Medium
Confidence
94% confidence
Finding
The skill describes auto-filling usernames from environment variables, .netrc, and even a default credential source without a strong warning or consent model. Credential discovery and automatic reuse are sensitive behaviors; they can surprise users, leak account identifiers into generated commands or logs, and normalize insecure credential handling patterns.

Missing User Warnings

Medium
Confidence
75% confidence
Finding
The helper can send user-provided place names to third-party geocoding services and persist results to disk without any user-facing disclosure or opt-in in this code path. In the context of a skill advertised as a local MODIS product query tool, that hidden network egress and local persistence can expose sensitive locations or workflow metadata unexpectedly.

Missing User Warnings

High
Confidence
99% confidence
Finding
Hardcoded fallback credentials are silently used if environment and user secrets are absent, with no user-facing disclosure at point of use. This can cause unintended authentication to a third-party account and conceal that the skill is operating with embedded credentials rather than user-provided ones.

Missing User Warnings

Medium
Confidence
87% confidence
Finding
The `--qa PATH` option writes user inputs and derived results to an arbitrary filesystem path with directory creation, which can unexpectedly persist sensitive prompts, queries, place names, or product selections. In agent contexts, a caller may not realize this creates a durable sidecar artifact, increasing risk of data leakage or unintended file overwrite within accessible paths.

Credential Access

High
Category
Privilege Escalation
Content
Resolution order (when generating download commands):

1. EARTHDATA_USERNAME env var (auto-fills --user in the generated wget)
2. ~/.netrc entry for machine urs.earthdata.nasa.gov (skill outputs cookie-jar form)
3. **Default** 
uiduobao (geoskill-core credentials.py) — auto-fills --user placeholder
Confidence
97% confidence
Finding
Reading or relying on ~/.netrc for credentials is credential access behavior and is especially sensitive in an agent skill. In this skill's context, it is more dangerous because the tool claims to be a local MODIS query utility, yet it implicitly reaches into a user's credential store for external-service authentication, expanding risk beyond simple documentation or lookup.

Credential Access

High
Category
Privilege Escalation
Content
3. **Default** 
uiduobao (geoskill-core credentials.py) — auto-fills --user placeholder

Password is **never** auto-filled; use EARTHDATA_PASSWORD env var, .netrc,
or type it interactively. Register your own free account at
https://urs.earthdata.nasa.gov/users/new/ for heavy use.
Confidence
98% confidence
Finding
The skill instructs use of EARTHDATA_PASSWORD or .netrc and also references a default username source, showing direct credential-handling logic in a skill that should not need it for basic product search. This increases the chance of secret exposure through environment inspection, command generation, logs, or accidental reuse of shared credentials.

Credential Access

High
Category
Privilege Escalation
Content
}

# .netrc 解析(仅在 UNIX-like / WSL 下 ~/.netrc 可用;Windows 下
# 通常用 %USERPROFILE%\_netrc,但 .netrc 本身仍是约定俗成的名称)。
_NETRC_HOSTS = {
    "urs.earthdata.nasa.gov": ("EARTHDATA_USERNAME", "EARTHDATA_PASSWORD"),
    "firms.modaps.eosdis.nasa.gov": ("FIRMS_MAP_KEY",),
Confidence
74% confidence
Finding
The `_NETRC_HOSTS` mapping expands credential access beyond Earthdata to FIRMS and EOG, allowing the skill to pull credentials for multiple services from the user's standard auth files. In the context of a MODIS product search skill, that cross-service credential harvesting is broader than necessary and increases the blast radius if other code uses this helper unexpectedly.

Credential Access

High
Category
Privilege Escalation
Content
解析顺序:
    1. env: EARTHDATA_TOKEN
    2. ~/.geoskill/secrets.json
    3. .netrc: machine urs.earthdata.nasa.gov account <TOKEN>
    4. _DEFAULTS(通常为空)
    """
    return _resolve("EARTHDATA_TOKEN")
Confidence
72% confidence
Finding
The docstring claims token resolution includes `.netrc account <TOKEN>`, but `get_earthdata_token()` does not actually implement `.netrc` token retrieval and instead falls back to `_DEFAULTS`/user secrets only. This inconsistency is a security design flaw because operators may assume a safer or different credential source than the code truly uses, leading to misconfiguration and accidental use of embedded or cached secrets.

Credential Access

High
Category
Privilege Escalation
Content
_DEFAULTS: dict[str, str] = {
    "EARTHDATA_USERNAME": "ruiduobao",
    "EARTHDATA_PASSWORD": "Ruiduobao123",
    "EARTHDATA_TOKEN": "",  # 用户级 secrets.json 提供(不走默认值以免推到 GitHub)
    "FIRMS_MAP_KEY": "",
    "CMA_API_KEY": "",
    "OPENAI_API_KEY": "",
Confidence
98% confidence
Finding
This line ties credential handling to `secrets.json` while the surrounding `_DEFAULTS` block includes hardcoded Earthdata credentials. In context, the broader issue is that the module centralizes and serves secrets—including embedded ones—creating a convenient access layer that can be abused by any code in the process.

Credential Access

High
Category
Privilege Escalation
Content
# 用户级 secrets 文件位置(在用户 home,**不** vendor 到 skill 内部)。
# Phase 7 (2026-07-27): 包含 NASA Earthdata bearer token 等真实凭证。
USER_SECRETS_PATH = Path.home() / ".geoskill" / "secrets.json"

# 是否已加载过用户级 secrets(避免每次调用都重读)
_user_secrets_loaded = False
Confidence
76% confidence
Finding
The module uses a predictable secrets file path in the user's home directory and loads it without validating file permissions or ownership. That can lead to accidental use of weakly protected credentials and broad in-process availability of sensitive tokens.

Credential Access

High
Category
Privilege Escalation
Content
def load_user_secrets(path: Optional[Path] = None, *, force: bool = False) -> bool:
    """从 ``~/.geoskill/secrets.json`` 加载用户级凭证到 _DEFAULTS.

    Phase 7 (2026-07-27): 第一次调用自动加载(lazy)。之后每个 helper
    调用也会 lazy 加载,除非显式 ``force=True`` 强制重读。返回 True
Confidence
80% confidence
Finding
`load_user_secrets()` imports all recognized non-empty secrets from a user file into the process-global `_DEFAULTS` structure. This broad loading pattern increases exposure duration and makes unrelated credentials available to any importing code, which is riskier than fetching only the one secret required for a specific operation.

Credential Access

High
Category
Privilege Escalation
Content
lines.append("Command Line Download (wget):")
    # Phase 7 (2026-07-27): auto-fill username from vendored credentials helper
    # (if available). Password is never auto-filled for safety — user must
    # either set EARTHDATA_PASSWORD env var, configure .netrc, or type it.
    try:
        from _geoskill_core.credentials import get_earthdata_creds
        u, _p = get_earthdata_creds()
Confidence
95% confidence
Finding
Importing and calling `get_earthdata_creds()` causes the tool to probe local credential sources unrelated to its core search function. Even though the password is not printed, touching credential stores and surfacing the username in output broadens secret-handling exposure and can leak identity information to logs or upstream consumers.

Unpinned Dependencies

Low
Category
Supply Chain
Content
modis_products
Confidence
96% confidence
Finding
The dependency is specified without a version pin, so installs will resolve to whatever version is current at install time. This creates a supply-chain risk: a future malicious, compromised, or simply breaking release of `modis_products` could be pulled into the skill environment unexpectedly, reducing reproducibility and potentially introducing code execution or integrity issues.

VirusTotal

VirusTotal findings are pending for this skill version.

View on VirusTotal

Static analysis

No suspicious patterns detected.