Back to skill

Security audit

Java Maven Common

Security checks for vulnerabilities and agentic risk

Overview

The skill has a coherent Maven project-ingest purpose, but its helper script can delete a caller-selected work directory and does not enforce its documented GitLab/temp-directory limits.

Install only if you trust the workflows that call this helper and can ensure --work always points to a disposable temp directory. Treat ZIPs and repository URLs as untrusted input: use size limits, temp workspace isolation, approved GitLab-only sources, and explicit user authorization before git cloning. This looks under-scoped and unsafe rather than intentionally malicious.

Vulnerability Patterns
  • Unauthorized Access and Privilege EscalationObtains permissions beyond the task's legitimate needs
  • 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
Findings (3)

T09 · Insecure Skill Coding Practices

Error
Location
scripts/prepare_java_maven_project.py:22
Finding

Arbitrary Recursive Directory Deletion Through Unrestricted Work Path

Content
View full analysis
Path: if out_dir.exists(): shutil.rmtree(out_dir) out_dir.parent.mkdir(parents=True, exist_ok=True) subprocess.run(["git", "clone", repo_url, str(out_dir)], check=True) return out_dir ``` ```python work = Path(args.work).resolve() json_path = Path(args.json).resolve() ``` ### Technical Analysis The `--work` argument is resolved to an absolute path but is not constrained to an application-owned temporary directory. In Git mode, `clone_repo()` recursively deletes that path with `shutil.rmtree()` whenever it already exists. The implementation does not reject filesystem roots, parent directories, symbolic-link-derived destinations, or unrelated existing directories. The documentation describes the working directory as being under `temp`, but this requirement is not enforced in code. ### Attack Path 1. An attacker, unsafe wrapper, or operator supplies `--mode git`. 2. The `--work` argument is set to an existing valuable directory writable by the process. 3. `Path.resolve()` canonicalizes the supplied path without checking whether it is inside an approved temporary base. 4. `clone_repo()` detects that the directory exists. 5. `shutil.rmtree(out_dir)` recursively deletes its contents before Git cloning begins. 6. The deletion occurs even if the subsequent clone fails. For example, invoking the script with an existing application data directory as `--work` would cause that directory to be deleted before the repository is cloned. ### Impact Assessment Successful exploitation can delete arbitrary files and directories accessible to the executing account. The scope is bounded by operating-system permissions, but when the Skill runs under a broadly privileged user, the re ...[truncated 210 chars]
Remediation
View remediation

T05 · Unauthorized Access and Privilege Escalation

Warning
Location
scripts/prepare_java_maven_project.py:21
Finding

Unrestricted Git Clone Source Allows Undeclared Network and Local Repository Access

Content
View full analysis
Path: if out_dir.exists(): shutil.rmtree(out_dir) out_dir.parent.mkdir(parents=True, exist_ok=True) subprocess.run(["git", "clone", repo_url, str(out_dir)], check=True) return out_dir ``` ```python if args.mode == "zip": root = unzip(Path(args.input).resolve(), work) else: root = clone_repo(args.input, work) ``` ### Technical Analysis The Skill documentation declares support for GitLab repository URLs and requires confirmation that SSH authorization has been granted. The implementation does not enforce either restriction. It passes the caller-controlled `--input` value directly to `git clone` without validating the URL scheme, hostname, transport, or whether the value is a local filesystem path. Although the subprocess invocation uses an argument list and therefore does not introduce conventional shell command injection, Git still interprets the source according to its supported transports. The input may identify an arbitrary HTTP, HTTPS, SSH, Git, or locally accessible repository rather than an approved GitLab location. No explicit authorization signal is required or recorded before an SSH operation is initiated. ### Attack Path 1. An attacker or untrusted workflow controls the `--input` value while selecting Git mode. 2. The attacker supplies an SSH or HTTP URL for an unapproved host, or a path to an accessible local repository. 3. The script forwards the value unchanged to `git clone`. 4. Git contacts the specified remote service or copies the specified local repository. 5. For remote sources, the destination server can observe connection metadata and receive protocol-level requests. For local sources, accessible repository contents are copied into ...[truncated 722 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/prepare_java_maven_project.py:11
Finding

Unbounded ZIP Extraction Enables Resource Exhaustion

Content
View full analysis
Path: out_dir.mkdir(parents=True, exist_ok=True) with zipfile.ZipFile(zip_path, "r") as zf: zf.extractall(out_dir) children = [p for p in out_dir.iterdir()] if len(children) == 1 and children[0].is_dir(): return children[0] return out_dir ``` ### Technical Analysis The script extracts every archive member with `ZipFile.extractall()` without checking the number of entries, declared uncompressed sizes, aggregate expanded size, compression ratios, or available storage. A maliciously compressed archive can have a small input size while expanding into a very large amount of data. Because extraction occurs before Maven module discovery, the attacker can consume substantial disk space and processing time regardless of whether the archive contains a valid Java project. The implementation also performs no explicit per-entry destination validation or rejection of special archive entries. Modern Python versions include some filename sanitization in `zipfile`, but security should not rely solely on library-version-specific behavior. ### Attack Path 1. An attacker submits a ZIP archive through the supported ZIP input mode. 2. The archive contains highly compressed data, an excessive number of entries, or entries with very large aggregate uncompressed size. 3. The script opens the archive and calls `extractall()` without preflight validation. 4. Extraction consumes disk space and CPU until it finishes, encounters an error, or exhausts system resources. 5. Other Agent tasks may fail because storage is exhausted or the worker becomes unavailable. ### Impact Assessment Exploitation can cause denial of service within the execution environment. Potential effects include full temporar ...[truncated 342 chars]
Remediation
View remediation
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Behavioral ASTexec() Call, eval() Call, Dynamic Import
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
Findings (6)

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
92% confidence
Finding

The skill describes operations that require filesystem writes and shell-capable actions, including unpacking archives, cloning repositories, and scanning project files, but it does not declare any explicit tool scope such as allowed-tools or permissions. This creates an authorization gap where an agent may execute broader-than-intended file or shell actions during project ingestion, increasing the risk of unsafe command execution, path misuse, or repository/archive handling abuse.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The function unconditionally deletes the requested output directory before cloning, with no safety check that the path is within an expected workspace or that it is non-empty and intended for removal. If an attacker or upstream component can influence '--work', this can cause destructive deletion of arbitrary directories accessible to the process.

Content

No source excerpt is available for this finding.

subprocess module call

Medium
Category
Dangerous Code Execution
Confidence
70% confidence
Finding

subprocess module calls execute external commands. Without careful input validation, this enables command injection.

Content

Scanner excerpt · scripts/prepare_java_maven_project.py (reported line 26)May include surrounding context.

python
if out_dir.exists():
        shutil.rmtree(out_dir)
    out_dir.parent.mkdir(parents=True, exist_ok=True)
    subprocess.run(["git", "clone", repo_url, str(out_dir)], check=True)
    return out_dir

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The script emits Chinese-only natural-language messages for limitedReason and failure reporting, which imposes a specific language on users. There is no opt-in, fallback, or documented justification for a Chinese-only locale in this file.

Content

No source excerpt is available for this finding.

Natural-Language Policy Violations

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The failure message prefix is hard-coded in Chinese, creating a language policy issue for users who are not expecting Chinese output. The file does not provide any mechanism to select language or explain that the tool is region/language-specific.

Content

No source excerpt is available for this finding.

Missing User Warnings

Low
Category
Not specified by scanner
Confidence
83% confidence
Finding

This subprocess invokes git clone against a user-supplied repository URL, which causes network access and transmits system/repository access context. The file contains no user-facing print/log statement or explanatory comment warning that remote network access will occur.

Content

No source excerpt is available for this finding.

Static analysis

No suspicious patterns detected.