Back to skill

Security audit

调用 JavaSkillController 提供的 HTTP 接口,供 OpenClaw/OpenLaw 执行业务操作、健康检查。

Security checks for vulnerabilities and agentic risk

Overview

The skill is a disclosed Java API caller, but it can send user and business data over user-configured HTTP endpoints with broad triggers and limited safeguards.

Install only if you control and trust the JAVA_API_URL backend. Prefer HTTPS except for local development, avoid sending sensitive data in extra unless the backend and transport are protected, and require explicit user confirmation before submit or other state-changing actions.

Vulnerability Patterns
  • Insecure DependenciesIntroduces malicious components through unsafe dependency sources
  • 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 (2)

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/call_java_api.py:34
Finding
Plaintext HTTP Is Permitted for Business Data## Vulnerability Details **File Location**: `scripts/call_java_api.py:34-65`; insecure HTTP examples also appear in `SKILL.md:10`, `SKILL.md:25`, and `SKILL.md:70` **Vulnerability Type**: Transmission of potentially sensitive business data over plaintext HTTP **Risk Level**: Medium **Complete Code Snippet**: ```python base_url = (os.environ.get("JAVA_API_URL") or "").rstrip("/") if not base_url: print('{"code": -1, "msg": "未配置 JAVA_API_URL 环境变量", "data": null}', file=sys.stderr) sys.exit(1) if args.health: url = f"{base_url}/api/skill/health" try: r = requests.get(url, timeout=10) r.raise_for_status() out = r.json() print(json.dumps(out, ensure_ascii=False)) except requests.RequestException as e: print(json.dumps({"code": -1, "msg": str(e), "data": None}, ensure_ascii=False), file=sys.stderr) sys.exit(1) return url = f"{base_url}/api/skill/{args.endpoint}" body = {} if args.action is not None: body["action"] = args.action if args.userId is not None: body["userId"] = args.userId if args.extra: try: body["extra"] = json.loads(args.extra) except json.JSONDecodeError: print('{"code": -1, "msg": "extra 不是合法 JSON", "data": null}', file=sys.stderr) sys.exit(1) try: r = requests.post(url, json=body, headers={"Content-Type": "application/json"}, timeout=30) r.raise_for_status() out = r.json() print(json.dumps(out, ensure_ascii=False)) except requests.RequestException as e: print(json.dumps({"code": -1, "msg": str(e), "data": None}, ensure_ascii=False), file=sys.stderr) sys.exit(1) ``` The documentation explicitly presents a plaintext endpoint: ```bash export JAVA_API_URL=http://your-server:8080 ``` ### Technical Analysis The script accepts `JAVA_API_URL` without validating its URL scheme. Consequently, both `http://` and `https://` endp ...[truncated 1686 chars]
Remediation
## Remediation Suggestions 1. Parse `JAVA_API_URL` with `urllib.parse.urlparse` and require the `https` scheme. 2. Reject plaintext HTTP by default. If local development requires HTTP, permit it only for loopback addresses through an explicit opt-in flag such as `JAVA_API_ALLOW_INSECURE_LOCALHOST=1`. 3. Replace all documented HTTP examples with HTTPS examples. 4. Keep TLS certificate verification enabled and do not introduce `verify=False`. 5. For high-value operations, consider application-level request authentication, integrity protection, replay prevention, and short-lived credentials in addition to TLS. 6. Minimize sensitive information placed in the unrestricted `extra` object and document appropriate data-handling restrictions.

T08 · Insecure Dependencies

Note
Location
scripts/call_java_api.py:13
Finding
Unpinned Runtime Dependency Installation Recommendation## Vulnerability Details **File Location**: `scripts/call_java_api.py:13-17` **Vulnerability Type**: Unpinned third-party dependency installation **Risk Level**: Low **Complete Code Snippet**: ```python try: import requests except ImportError: print("请先安装: pip install requests", file=sys.stderr) sys.exit(1) ``` ### Technical Analysis If the `requests` package is unavailable, the script recommends installing it using `pip install requests`. This command does not select an audited version, use a lock file, validate an integrity hash, or explicitly constrain the package source. The script does not automatically execute the installation command, which substantially reduces immediate exploitability. Nevertheless, following the recommendation produces a non-reproducible dependency resolution and trusts whichever release and package index configuration are active at installation time. This creates exposure to a compromised package release, a compromised or malicious package index mirror, and unexpected future compatibility or security regressions. ### Attack Path 1. The operator runs the script in an environment where `requests` is not installed. 2. The script displays the unpinned `pip install requests` recommendation. 3. The operator executes that command using an environment configured to access an untrusted or compromised package source, or installs an unsafe future release. 4. Pip downloads and installs the uncontrolled package artifact. 5. Package installation behavior or subsequent import executes attacker-controlled code with the privileges of the operator. ### Impact Assessment The script itself does not silently install or execute a remote package. Exploitation therefore requires the operator to follow the recommendation and the dependency source or resolved artifact to be compromised. If those conditions are met, malicious package code can execute with the installing user's privileges. It co ...[truncated 191 chars]
Remediation
## Remediation Suggestions 1. Declare `requests` in a committed dependency manifest rather than relying on an installation message. 2. Pin it to an explicitly reviewed version or a tightly controlled compatible range. 3. Use a lock file with cryptographic hashes, such as a hash-locked requirements file generated by a trusted dependency-management process. 4. Install packages only from an approved package index over HTTPS. 5. Add automated dependency vulnerability and update monitoring. 6. Document installation through an isolated virtual environment using the committed dependency file.
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • Taint TrackingDirect Taint Flow, Variable-Mediated Taint Flow, Credential Exfiltration Chain
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
Findings (8)

Tainted flow: 'url' from os.environ.get (line 36, credential/environment) → requests.get (network output)

Critical
Category
Data Flow
Content
if args.health:
        url = f"{base_url}/api/skill/health"
        try:
            r = requests.get(url, timeout=10)
            r.raise_for_status()
            out = r.json()
            print(json.dumps(out, ensure_ascii=False))
Confidence
90% confidence
Finding
Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Tainted flow: 'url' from os.environ.get (line 36, credential/environment) → requests.post (network output)

Critical
Category
Data Flow
Content
sys.exit(1)

    try:
        r = requests.post(url, json=body, headers={"Content-Type": "application/json"}, timeout=30)
        r.raise_for_status()
        out = r.json()
        print(json.dumps(out, ensure_ascii=False))
Confidence
90% confidence
Finding
Credentials or environment variables flow to a network sink. This is a high-confidence indicator of credential exfiltration.

Lp3

Medium
Category
MCP Least Privilege
Confidence
90% confidence
Finding
The skill documents use of environment variables and outbound network access, but it does not declare any explicit tool scope such as permissions or allowed-tools. That creates a governance gap: an agent or platform may invoke capabilities broader than reviewers or operators expect, increasing the chance of unintended data access or network transmission.

Missing User Warnings

Medium
Confidence
93% confidence
Finding
The skill instructs callers to send userId and business data to a configurable backend, including examples using plain HTTP, but it does not warn about sensitive data handling or require transport security. In practice, this can expose identifiers and business payloads to interception, misconfiguration, or transmission to untrusted internal endpoints if JAVA_API_URL is set insecurely.

External Transmission

Medium
Category
Data Exfiltration
Content
sys.exit(1)

    try:
        r = requests.post(url, json=body, headers={"Content-Type": "application/json"}, timeout=30)
        r.raise_for_status()
        out = r.json()
        print(json.dumps(out, ensure_ascii=False))
Confidence
80% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Vague Triggers

Medium
Confidence
96% confidence
Finding
The trigger phrases are broad and generic, such as '执行技能', '查询用户', and '提交数据', which can match many ordinary user requests and cause the skill to be invoked unintentionally. Because this skill performs HTTP business operations against a backend API, accidental activation could lead to unintended queries or data submissions rather than a harmless no-op.

Natural-Language Policy Violations

Low
Confidence
96% confidence
Finding
The module docstring and user-facing messages are written only in Chinese, and the script does not offer any language or locale choice. This creates a natural-language policy concern because it implicitly enforces a specific language for all users without opt-in or justification.

Natural-Language Policy Violations

Low
Confidence
78% confidence
Finding
The natural-language description and trigger phrases are entirely in Chinese, with no indication that users may choose another language or that the skill is intentionally limited to a Chinese-only audience. Under the language/locale policy, a fixed language should be opt-in or clearly justified as region-specific.

Static analysis

No suspicious patterns detected.