T09 · Insecure Skill Coding Practices
Error
- Location
- SKILL.md:14
- Finding
- Wallet Private Key Exposed Through Console Output and Plaintext File Storage## Vulnerability Details **File Location**: `SKILL.md`, lines 14–31 **Vulnerability Type**: Plaintext sensitive-data exposure **Risk Level**: High ### Vulnerable Code ```javascript const { PrivateKey, AccountId } = require("@hashgraph/sdk"); // Generate a new key pair const privateKey = PrivateKey.generateECDSA(); const publicKey = privateKey.publicKey; console.log("Private Key:", privateKey.toStringRaw()); console.log("Public Key:", publicKey.toStringRaw()); console.log("EVM Address:", publicKey.toEvmAddress()); // Save securely! const fs = require("fs"); fs.writeFileSync("agent-wallet.json", JSON.stringify({ privateKey: privateKey.toStringRaw(), publicKey: publicKey.toStringRaw(), evmAddress: publicKey.toEvmAddress(), created: new Date().toISOString() }, null, 2)); ``` ### Technical Analysis The documented wallet-generation procedure converts the Hedera private key to its raw representation and exposes it through two unsafe channels: 1. It prints the private key to standard output using `console.log`. Terminal history, CI/CD logs, agent execution traces, observability systems, and centralized log collectors may retain this output. 2. It writes the private key unencrypted to `agent-wallet.json`. The call does not explicitly apply restrictive file permissions, encryption, or secret-manager protection. A wallet private key is a bearer credential: possession is sufficient to authorize transactions. Unlike an ordinary password, unauthorized blockchain transactions generally cannot be reversed by an administrator. The comment stating “Save securely” does not provide an effective security control. ### Attack Path 1. A user or AI agent follows the documented quick-start procedure. 2. The generated raw private key is emitted to process output and stored in `agent-wallet.json`. 3. An attacker obtains the key from accessible logs, execution traces, backups, an accidentally committed file, a sh ...[truncated 746 chars]
- Remediation
- ## Remediation Suggestions - Remove all private-key logging. Public keys and addresses may be displayed when needed, but secret key material must never be written to standard output. - Store the private key in an operating-system keychain, managed secret store, hardware security module, or encrypted keystore protected by a strong passphrase. - Prefer non-exportable key generation and signing where supported, so raw private-key bytes never enter application-managed files. - If file storage is unavoidable, create the file with owner-only permissions such as mode `0600`, place it outside shared and project directories, and encrypt its contents at rest. Restrictive permissions reduce exposure but do not replace encryption. - Add `agent-wallet.json` and equivalent key files to `.gitignore`, backup exclusions, artifact exclusions, and log-redaction rules. - Document secure backup, recovery, access-control, and key-rotation procedures. - Treat any key previously produced by this example as potentially exposed. Move assets to a newly generated secure wallet and retire the old key where the account configuration permits.
