Back to skill

Security audit

AgentHire

Security checks for vulnerabilities and agentic risk

Overview

This skill is a coherent testnet agent marketplace integration, but it gives an agent wallet authority to spend, release escrow, and publish task data with weak user controls.

Review this carefully before installing. Use only a fresh low-value Base Sepolia wallet, never a primary or reused private key, assume task descriptions may be visible on-chain, and do not let the agent hire or release escrow without explicit human review of the service, task text, price, result, and transaction details.

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

T09 · Insecure Skill Coding Practices

Error
Location
scripts/hire.js:50
Finding

Escrow Payment Is Released Without Validating Provider Output

Content
View full analysis
setTimeout(r, 3000)); const cNonce = await wallet.getNonce("pending"); const confirmTx = await escrow.confirmComplete(jobId, { nonce: cNonce }); await confirmTx.wait(); console.log("Payment released!"); await new Promise(r => setTimeout(r, 3000)); const rNonce = await wallet.getNonce("pending"); const rateTx = await escrow.rateJob(jobId, 5, { nonce: rNonce }); await rateTx.wait(); console.log("Rated 5/5 stars."); } catch (e) { console.log("Auto-completed by provider."); } } else { console.log("\nJob completed!"); } // Parse result try { const r = JSON.parse(result); if (r.success) { console.log(`\nResult: Swapped ${r.amountIn} ${r.fromToken} → ${r.amountOut} ${r.toToken}`); console.log(`TX Hash: ${r.txHash}`); if (r.basescanUrl) console.log(`Verify: ${r.basescanUrl}`); console.log(`DEX: ${r.dex}`); } else { console.log(`\nJob failed: ${r.error}`); } } catch { console.log(`\nResult: ${result}`); } process.exit(0); } ``` ### Technical Analysis A provider-controlled state transition to status `1` (“Submitted”) is treated as sufficient proof that the task was completed correctly. The script calls `confirmComplete()` before parsing or validating the result. This releases the escrow payment even when the result is empty, malformed, unrel ...[truncated 1699 chars]
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Warning
Location
setup.js:43
Finding

Wallet Private Key Is Printed and Stored Without Explicit Restrictive Permissions

Content
View full analysis
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/hire.js:8
Finding

Sensitive Task Descriptions Can Be Permanently Disclosed On-Chain

Content
View full analysis
""'); process.exit(1); } const provider = new ethers.JsonRpcProvider(process.env.AGENTHIRE_RPC_URL); const wallet = new ethers.Wallet(process.env.AGENTHIRE_PRIVATE_KEY, provider); const registry = new ethers.Contract(process.env.AGENTHIRE_REGISTRY, registryAbi, provider); const escrow = new ethers.Contract(process.env.AGENTHIRE_ESCROW, escrowAbi, wallet); // Get service price const s = await registry.getService(serviceId); const price = s[5]; // pricePerJob in wei const name = s[2]; console.log(`Hiring ${name} (ID: ${serviceId}) for ${ethers.formatEther(price)} ETH...`); // Create job with escrow (explicit nonce for testnet) const nonce = await wallet.getNonce("pending"); const tx = await escrow.createJob(serviceId, task, { value: price, nonce }); ``` ### Technical Analysis The skill accepts an arbitrary task description as a command-line argument and passes it directly to the escrow contract's `createJob()` function. Blockchain transaction data is public and generally immutable. Consequently, any credentials, personal information, proprietary data, source code, internal URLs, or confidential instructions included in a task may become permanently available to blockchain observers. Passing the task through `process.argv` creates an additional local disclosure channel. Command-line arguments may be retained in shell history or exposed through process inspection while the command is running. There is no warning, secret detection, redaction, encryption, access control, or off-chain confidential ...[truncated 1077 chars]
Remediation
View remediation

T08 · Insecure Dependencies

Note
Location
package.json:5
Finding

Dependency Installation Is Not Reproducible or Cryptographically Locked

Content
View full analysis
Remediation
View remediation
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 (22)

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · README.md (reported line 27)May include surrounding context.

cd ~/.openclaw/skills/agenthire && npm install

Configure

cp .env.example .env

Edit .env with your contract addresses and wallet key

text

Credential Access

High
Category
Privilege Escalation
Confidence
77% confidence
Finding

The README explicitly instructs the user to place a wallet private key into a .env file for a skill that performs autonomous on-chain hiring and swaps. While common in prototypes, encouraging raw private key storage for an agent-executed financial workflow increases the chance of credential compromise, accidental leakage, or misuse by the agent runtime or surrounding tooling.

Content

Scanner excerpt · README.md (reported line 28)May include surrounding context.

Configure

cp .env.example .env

Edit .env with your contract addresses and wallet key

text

After setup, run `openclaw skills list` — you should see:

Tp4

High
Category
MCP Tool Poisoning
Confidence
93% confidence
Finding

The skill description promises hiring, payment, and escrow behavior, but the analyzed material does not substantiate those capabilities and appears to describe more functionality than is actually present. This mismatch can mislead operators into authorizing financial or delegated actions under false assumptions, weakening trust and safe review of blockchain-affecting behavior.

Content

No source excerpt is available for this finding.

Ae1

High
Category
analysis-evasion
Confidence
100% confidence
Finding

Referenced artifact was not completely inspected

Content

Scanner excerpt · SKILL.md (reported line 56)May include surrounding context.

md
cd ~/.openclaw/workspace/skills/agenthire && node scripts/search.js "token-swap"

Ae1

High
Category
analysis-evasion
Confidence
100% confidence
Finding

Referenced artifact was not completely inspected

Content

Scanner excerpt · SKILL.md (reported line 96)May include surrounding context.

md
cd ~/.openclaw/workspace/skills/agenthire && node scripts/search.js "token-swap"

Missing User Warnings

High
Category
Not specified by scanner
Confidence
98% confidence
Finding

The script creates an on-chain escrow transaction that transfers value immediately based only on CLI arguments and contract-returned pricing, with no interactive confirmation, simulation, or explicit irreversible-funds warning. In an agent-to-agent marketplace context, this is especially dangerous because another agent or automation layer could invoke the script and spend funds without meaningful human review.

Content

No source excerpt is available for this finding.

Missing User Warnings

High
Category
Not specified by scanner
Confidence
99% confidence
Finding

The script automatically calls confirmComplete when a provider marks a job as submitted, which releases escrowed payment without validating that the result is correct or obtaining user approval. In this marketplace setting, an untrusted or low-quality provider can submit bogus output and still get paid because the client script finalizes payment programmatically after a short delay.

Content

No source excerpt is available for this finding.

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/hire.js (reported line 3)May include surrounding context.

js
#!/usr/bin/env node
// agenthire_status — Check job status
require("dotenv").config({ path: __dirname + "/../.env" });
const { ethers } = require("ethers");
const escrowAbi = require("./JobEscrow.abi.json");

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/search.js (reported line 3)May include surrounding context.

js
#!/usr/bin/env node
// agenthire_status — Check job status
require("dotenv").config({ path: __dirname + "/../.env" });
const { ethers } = require("ethers");
const escrowAbi = require("./JobEscrow.abi.json");

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/status.js (reported line 3)May include surrounding context.

js
#!/usr/bin/env node
// agenthire_status — Check job status
require("dotenv").config({ path: __dirname + "/../.env" });
const { ethers } = require("ethers");
const escrowAbi = require("./JobEscrow.abi.json");

Credential Access

High
Category
Privilege Escalation
Confidence
60% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · setup.js (reported line 8)May include surrounding context.

js
#!/usr/bin/env node
// agenthire_status — Check job status
require("dotenv").config({ path: __dirname + "/../.env" });
const { ethers } = require("ethers");
const escrowAbi = require("./JobEscrow.abi.json");

Credential Access

High
Category
Privilege Escalation
Confidence
96% confidence
Finding

This code path explicitly informs the user that the wallet private key will be saved in .env, and the surrounding logic does in fact persist the secret in plaintext. In the context of an agent marketplace that instructs users to fund the wallet, storing the credential in an unprotected environment file materially increases the risk of credential theft and financial loss.

Content

Scanner excerpt · setup.js (reported line 55)May include surrounding context.

js
console.log("\n⚠️  SAVE your private key! Lost = lost forever.");
console.log("   (It's also saved in .env)\n");

// 4. Write .env with hardcoded contract addresses
const envContent = `# AgentHire — Agent Wallet Config
# Generated: ${new Date().toISOString()}

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
89% confidence
Finding

The README instructs users to configure a private key and describes triggering real on-chain swaps through the agent, but it does not include clear warnings about irreversible financial actions, key handling, or limiting wallet exposure. In an agent-driven marketplace context, this is especially risky because automated tool use can cause unintended transactions or expose funds if the configured wallet is overprivileged or compromised.

Content

No source excerpt is available for this finding.

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
82% confidence
Finding

The skill declares sensitive environment requirements, including a private key, but does not define an explicit tool scope or permissions boundary. That creates ambiguity about what the skill is allowed to access and increases the risk of over-broad execution or accidental exposure/use of secrets by the runtime or downstream scripts.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The skill instructs the agent to send tasks to third-party agents and pay them on-chain, but it does not require a clear user warning or consent before sharing task details externally. This is dangerous because user prompts may contain sensitive financial, strategic, or personal information that would be disclosed to an untrusted provider and coupled with an irreversible escrow payment.

Content

No source excerpt is available for this finding.

Autonomous Decision Making

Medium
Category
Excessive Agency
Confidence
91% confidence
Finding

The auto-confirm behavior represents autonomous decision-making over a financially meaningful action: releasing escrow after a third party claims success. In this context, autonomy is especially dangerous because blockchain actions are difficult or impossible to reverse, and the skill is making trust and payment decisions without human verification.

Content

Scanner excerpt · SKILL.md (reported line 81)May include surrounding context.

md
**Returns:** Job result from the hired agent. Includes TX hash verifiable on BaseScan.

**Note:** This command waits up to 90 seconds for the provider to complete the job. It auto-confirms and rates 5/5 on success.

### agenthire_status

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

The skill states that jobs are automatically confirmed and rated 5/5 on success without a clear warning or user approval. Auto-confirmation can irreversibly release escrowed funds and submit a reputation signal before the user has verified the output, enabling loss of funds, poor-quality service acceptance, or abuse by malicious providers.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
92% confidence
Finding

The code constructs a wallet directly from AGENTHIRE_PRIVATE_KEY, which is a sensitive credential access operation. While the script has some operational logging, it does not disclose that it will read and use a private key from the environment, and there is no comment or prompt warning the user about this sensitive action.

Content

No source excerpt is available for this finding.

Context-Inappropriate Capability

Medium
Category
Not specified by scanner
Confidence
95% confidence
Finding

The setup script automatically executes npm install --production via execSync, which runs lifecycle scripts from this package and all dependencies during installation. That creates an unnecessary code-execution path in a post-install context, increasing supply-chain risk and giving the package the ability to trigger networked or local side effects beyond simple marketplace configuration.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
98% confidence
Finding

The script generates a blockchain private key and writes it directly into a plaintext .env file without obtaining explicit consent immediately before the write or validating secure storage expectations. A wallet private key is a highly sensitive credential; if the repository, host, backups, logs, or adjacent tooling expose .env, an attacker can take over the wallet and spend any funds placed into it.

Content

No source excerpt is available for this finding.

Unpinned Dependencies

Low
Category
Supply Chain
Confidence
96% confidence
Finding

The dependency on ethers uses a caret range (^6.13.0), which permits automatic installation of newer compatible releases rather than a single audited version. This increases supply-chain risk because a compromised or breaking upstream release could be pulled into builds unexpectedly, which is especially relevant for a skill that may handle on-chain interactions and payments.

Content

Scanner excerpt · package.json (reported line 6)May include surrounding context.

json
"version": "0.1.0",
  "private": true,
  "dependencies": {
    "ethers": "^6.13.0",
    "dotenv": "^16.4.0"
  }
}

Unpinned Dependencies

Low
Category
Supply Chain
Confidence
95% confidence
Finding

The dotenv dependency is also specified with a caret range (^16.4.0), allowing silent drift to later patch/minor releases. While dotenv is not directly high-risk by itself, any unpinned third-party package introduces supply-chain uncertainty and could affect secret handling or runtime behavior if a malicious or flawed version is published.

Content

Scanner excerpt · package.json (reported line 7)May include surrounding context.

json
"private": true,
  "dependencies": {
    "ethers": "^6.13.0",
    "dotenv": "^16.4.0"
  }
}

Static analysis

Detected: suspicious.dangerous_exec

Shell command execution detected (child_process).

Critical
Code
suspicious.dangerous_exec
Location
setup.js:16