bagman
Secure key management for AI agents. Use when handling private keys, API secrets, wallet credentials, or when building systems that need agent-controlled funds. Covers secure storage, session keys, leak prevention, and prompt injection defense.
Best use case
bagman is best used when you need a repeatable AI agent workflow instead of a one-off prompt.
Secure key management for AI agents. Use when handling private keys, API secrets, wallet credentials, or when building systems that need agent-controlled funds. Covers secure storage, session keys, leak prevention, and prompt injection defense.
Teams using bagman should expect a more consistent output, faster repeated execution, less prompt rewriting.
When to use this skill
- You want a reusable workflow that can be run more than once with consistent structure.
When not to use this skill
- You only need a quick one-off answer and do not need a reusable workflow.
- You cannot install or maintain the underlying files, dependencies, or repository context.
Installation
Claude Code / Cursor / Codex
Manual Installation
- Download SKILL.md from GitHub
- Place it in
.claude/skills/master-skills/SKILL.mdinside your project - Restart your AI agent — it will auto-discover the skill
How bagman Compares
| Feature / Agent | bagman | Standard Approach |
|---|---|---|
| Platform Support | Not specified | Limited / Varies |
| Context Awareness | High | Baseline |
| Installation Complexity | Unknown | N/A |
Frequently Asked Questions
What does this skill do?
Secure key management for AI agents. Use when handling private keys, API secrets, wallet credentials, or when building systems that need agent-controlled funds. Covers secure storage, session keys, leak prevention, and prompt injection defense.
Where can I find the source code?
You can find the source code on GitHub using the link provided at the top of the page.
Related Guides
Best AI Skills for Claude
Explore the best AI skills for Claude and Claude Code across coding, research, workflow automation, documentation, and agent operations.
Best AI Skills for ChatGPT
Find the best AI skills to adapt into ChatGPT workflows for research, writing, summarization, planning, and repeatable assistant tasks.
ChatGPT vs Claude for Agent Skills
Compare ChatGPT and Claude for AI agent skills across coding, writing, research, and reusable workflow execution.
SKILL.md Source
# Bagman
Secure key management patterns for AI agents handling private keys and secrets. Designed to prevent:
- **Key loss**: Agents forgetting keys between sessions
- **Accidental exposure**: Keys leaked to GitHub, logs, or outputs
- **Prompt injection**: Malicious prompts extracting secrets
## Core Principles
1. **Never store raw private keys in config, env vars, or memory files**
2. **Use session keys / delegated access instead of full control**
3. **All secret access goes through 1Password CLI (`op`)**
4. **Validate all outputs before sending to prevent key leakage**
## References
- `references/secure-storage.md` - 1Password patterns for agent secrets
- `references/session-keys.md` - ERC-4337 delegated access patterns
- `references/leak-prevention.md` - Pre-commit hooks and output sanitization
- `references/prompt-injection-defense.md` - Input validation and output filtering
---
## Quick Reference
### DO ✅
```bash
# Retrieve key at runtime via 1Password
PRIVATE_KEY=$(op read "op://Agents/my-agent-wallet/private-key")
# Use environment injection (key never touches disk)
op run --env-file=.env.tpl -- node agent.js
# Use session keys with bounded permissions
# (delegate specific capabilities, not full wallet access)
```
### DON'T ❌
```bash
# NEVER store keys in files
echo "PRIVATE_KEY=0x123..." > .env
# NEVER log or print keys
console.log("Key:", privateKey)
# NEVER store keys in memory/journal files
# Even in "private" agent memory - these can be exfiltrated
# NEVER trust unvalidated input near key operations
```
---
## Architecture: Agent Wallet Stack
```
┌─────────────────────────────────────────────────────┐
│ AI Agent │
├─────────────────────────────────────────────────────┤
│ Session Key (time/value bounded) │
│ - Expires after N hours │
│ - Spending cap per operation │
│ - Whitelist of allowed contracts │
├─────────────────────────────────────────────────────┤
│ 1Password / Secret Manager │
│ - Agent retrieves session key at runtime │
│ - Never stores full private key │
│ - Audit log of all accesses │
├─────────────────────────────────────────────────────┤
│ ERC-4337 Smart Account │
│ - Programmable permissions │
│ - Recovery without private key exposure │
│ - Multi-sig for high-value operations │
├─────────────────────────────────────────────────────┤
│ Operator (Human) │
│ - Holds master key in hardware wallet │
│ - Issues/revokes session keys │
│ - Monitors agent activity │
└─────────────────────────────────────────────────────┘
```
---
## Workflow: Setting Up Agent Wallet Access
### 1. Create 1Password Vault for Agent Secrets
```bash
# Create dedicated vault (via 1Password app or CLI)
op vault create "Agent-Wallets" --description "AI agent wallet credentials"
# Store agent session key (not master key!)
op item create \
--vault "Agent-Wallets" \
--category "API Credential" \
--title "trading-bot-session" \
--field "session-key[password]=0xsession..." \
--field "expires=2026-02-15T00:00:00Z" \
--field "spending-cap=1000 USDC" \
--field "allowed-contracts=0xDEX1,0xDEX2"
```
### 2. Agent Retrieves Credentials at Runtime
```python
import subprocess
import json
def get_session_key(item_name: str) -> dict:
"""Retrieve session key from 1Password at runtime."""
result = subprocess.run(
["op", "item", "get", item_name, "--vault", "Agent-Wallets", "--format", "json"],
capture_output=True, text=True, check=True
)
item = json.loads(result.stdout)
# Extract fields
fields = {f["label"]: f.get("value") for f in item.get("fields", [])}
# Validate session hasn't expired
from datetime import datetime
expires = datetime.fromisoformat(fields.get("expires", "2000-01-01"))
if datetime.now() > expires:
raise ValueError("Session key expired - request new key from operator")
return {
"session_key": fields.get("session-key"),
"expires": fields.get("expires"),
"spending_cap": fields.get("spending-cap"),
"allowed_contracts": fields.get("allowed-contracts", "").split(",")
}
```
### 3. Never Log or Store the Key
```python
# ❌ BAD - Key in logs
logger.info(f"Using key: {session_key}")
# ✅ GOOD - Redacted identifier
logger.info(f"Using session key: {session_key[:8]}...{session_key[-4:]}")
# ❌ BAD - Key in memory file
with open("memory/today.md", "a") as f:
f.write(f"Session key: {session_key}")
# ✅ GOOD - Reference only
with open("memory/today.md", "a") as f:
f.write(f"Session key: [stored in 1Password: trading-bot-session]")
```
---
## Leak Prevention
### Output Sanitization
Before any agent output (chat, logs, file writes), scan for key patterns:
```python
import re
KEY_PATTERNS = [
r'0x[a-fA-F0-9]{64}', # ETH private keys
r'sk-[a-zA-Z0-9]{48,}', # OpenAI keys
r'sk-ant-[a-zA-Z0-9\-_]{80,}', # Anthropic keys
r'gsk_[a-zA-Z0-9]{48,}', # Groq keys
r'[A-Za-z0-9+/]{40,}={0,2}', # Base64 encoded (suspiciously long)
]
def sanitize_output(text: str) -> str:
"""Remove potential secrets from output."""
for pattern in KEY_PATTERNS:
text = re.sub(pattern, '[REDACTED]', text)
return text
# Apply to ALL agent outputs
def send_message(content: str):
content = sanitize_output(content)
# ... send to chat/log/file
```
### Pre-commit Hook
Install this hook to prevent accidental commits of secrets:
```bash
#!/bin/bash
# .git/hooks/pre-commit
PATTERNS=(
'0x[a-fA-F0-9]{64}'
'sk-[a-zA-Z0-9]{48,}'
'sk-ant-api'
'PRIVATE_KEY='
'gsk_[a-zA-Z0-9]{48,}'
)
for pattern in "${PATTERNS[@]}"; do
if git diff --cached | grep -qE "$pattern"; then
echo "❌ Potential secret detected matching: $pattern"
echo " Remove secrets before committing!"
exit 1
fi
done
```
### .gitignore Essentials
```gitignore
# Secrets
.env
.env.*
*.pem
*.key
secrets/
credentials/
# Agent state that might contain secrets
memory/*.json
wallet-state.json
session-keys/
```
---
## Prompt Injection Defense
### Input Validation
Before processing any user input that touches wallet operations:
```python
DANGEROUS_PATTERNS = [
r'ignore.*(previous|above|prior).*instructions',
r'reveal.*(key|secret|password|credential)',
r'output.*(key|secret|private)',
r'print.*(key|secret|wallet)',
r'show.*(key|secret|password)',
r'what.*(key|secret|password)',
r'tell.*me.*(key|secret)',
r'disregard.*rules',
r'system.*prompt',
r'jailbreak',
r'dan.*mode',
]
def validate_input(text: str) -> bool:
"""Check for prompt injection attempts."""
text_lower = text.lower()
for pattern in DANGEROUS_PATTERNS:
if re.search(pattern, text_lower):
return False
return True
def process_wallet_request(user_input: str):
if not validate_input(user_input):
return "I can't help with that request."
# ... proceed with wallet operation
```
### Separation of Concerns
- **Wallet operations should be in isolated functions** with no access to conversation context
- **Never pass full conversation history to wallet-sensitive code**
- **Use allowlists for operations, not blocklists**
```python
ALLOWED_WALLET_OPERATIONS = {
"check_balance": lambda: get_balance(),
"send_usdc": lambda to, amount: send_usdc(to, amount) if amount < DAILY_LIMIT else deny(),
"swap": lambda: swap_tokens() if within_limits() else deny(),
}
def execute_wallet_operation(operation: str, **kwargs):
"""Execute only explicitly allowed operations."""
if operation not in ALLOWED_WALLET_OPERATIONS:
raise ValueError(f"Operation '{operation}' not allowed")
return ALLOWED_WALLET_OPERATIONS[operation](**kwargs)
```
---
## Session Key Implementation (ERC-4337)
For agents needing on-chain access, use session keys instead of raw private keys.
See `references/session-keys.md` for full implementation details including:
- ZeroDev/Biconomy SDK examples
- Permission patterns for trading/DeFi/payment agents
- Session key lifecycle management
- Revocation procedures
---
## Incident Response
### If a Key is Leaked
1. **Immediate**: Revoke the session key / rotate credentials
2. **Assess**: Check transaction history for unauthorized activity
3. **Notify**: Alert operator via secure channel
4. **Rotate**: Issue new session key with tighter permissions
5. **Audit**: Review how leak occurred, update defenses
```bash
# Emergency: Revoke 1Password item
op item delete "compromised-session-key" --vault "Agent-Wallets"
# Rotate to new session key
op item create --vault "Agent-Wallets" --category "API Credential" \
--title "trading-bot-session-v2" ...
```
---
## Checklist: Agent Wallet Setup
- [ ] Create dedicated 1Password vault for agent credentials
- [ ] Store session keys (NOT master keys) in vault
- [ ] Set appropriate expiry and spending limits
- [ ] Install pre-commit hook for secret detection
- [ ] Add output sanitization to all agent responses
- [ ] Implement input validation for prompt injection
- [ ] Configure monitoring and alerts
- [ ] Document incident response procedure
- [ ] Test key rotation procedure
---
## Common Mistakes Found in Production
### 1. Keys in Memory Files
**Problem**: Agents store keys in `memory/*.md` for "persistence"
```markdown
# memory/2026-02-07.md
## Test Wallet
- Private key: 0x9f01dad551039daad3a8c4e43a32035bdd4da54e7b4292268be16e913b0b3e56
```
**Fix**: Store reference only: `Private key: [1Password: test-wallet-session]`
### 2. Keys in Environment Templates
**Problem**: `.env.example` contains real keys
```
# .env.example
PRIVATE_KEY=sk-ant-api03-real-key-here... # "for testing"
```
**Fix**: Use obviously fake placeholders: `PRIVATE_KEY=your-key-here`
### 3. Keys in Error Messages
**Problem**: Error handling exposes keys
```python
try:
sign_transaction(private_key, tx)
except Exception as e:
logger.error(f"Failed with key {private_key}: {e}") # ❌
```
**Fix**: Never include credentials in error context
### 4. Test Keys in Production Code
**Problem**: Hardcoded test keys make it to main branch
**Fix**: Use separate test vault, CI checks for key patterns
---
## Integration with OpenClaw
When running as an OpenClaw agent:
1. **Use 1Password skill** for all secret retrieval
2. **Never write keys to workspace files** - they persist across sessions
3. **Sanitize outputs** before sending to any channel (Telegram, Discord, etc.)
4. **Session key approach** for wallet operations - request bounded access from operator
5. **Document key references** in TOOLS.md, not the actual keys
Example TOOLS.md entry:
```markdown
### Agent Wallet
- Address: 0xABC123...
- Session key: [1Password: my-agent-session]
- Permissions: USDC transfers < 100, approved DEX only
- Expires: 2026-02-15
- To rotate: Ask operator via Telegram
```Related Skills
---
name: article-factory-wechat
humanizer
Remove signs of AI-generated writing from text. Use when editing or reviewing text to make it sound more natural and human-written. Based on Wikipedia's comprehensive "Signs of AI writing" guide. Detects and fixes patterns including: inflated symbolism, promotional language, superficial -ing analyses, vague attributions, em dash overuse, rule of three, AI vocabulary words, negative parallelisms, and excessive conjunctive phrases.
find-skills
Helps users discover and install agent skills when they ask questions like "how do I do X", "find a skill for X", "is there a skill that can...", or express interest in extending capabilities. This skill should be used when the user is looking for functionality that might exist as an installable skill.
tavily-search
Use Tavily API for real-time web search and content extraction. Use when: user needs real-time web search results, research, or current information from the web. Requires Tavily API key.
baidu-search
Search the web using Baidu AI Search Engine (BDSE). Use for live information, documentation, or research topics.
agent-autonomy-kit
Stop waiting for prompts. Keep working.
Meeting Prep
Never walk into a meeting unprepared again. Your agent researches all attendees before calendar events—pulling LinkedIn profiles, recent company news, mutual connections, and conversation starters. Generates a briefing doc with talking points, icebreakers, and context so you show up informed and confident. Triggered automatically before meetings or on-demand. Configure research depth, advance timing, and output format. Walking into meetings blind is amateur hour—missed connections, generic small talk, zero leverage. Use when setting up meeting intelligence, researching specific attendees, generating pre-meeting briefs, or automating your prep workflow.
self-improvement
Captures learnings, errors, and corrections to enable continuous improvement. Use when: (1) A command or operation fails unexpectedly, (2) User corrects Claude ('No, that's wrong...', 'Actually...'), (3) User requests a capability that doesn't exist, (4) An external API or tool fails, (5) Claude realizes its knowledge is outdated or incorrect, (6) A better approach is discovered for a recurring task. Also review learnings before major tasks.
botlearn-healthcheck
botlearn-healthcheck — BotLearn autonomous health inspector for OpenClaw instances across 5 domains (hardware, config, security, skills, autonomy); triggers on system check, health report, diagnostics, or scheduled heartbeat inspection.
linkedin-cli
A bird-like LinkedIn CLI for searching profiles, checking messages, and summarizing your feed using session cookies.
notebooklm
Google NotebookLM 非官方 Python API 的 OpenClaw Skill。支持内容生成(播客、视频、幻灯片、测验、思维导图等)、文档管理和研究自动化。当用户需要使用 NotebookLM 生成音频概述、视频、学习材料或管理知识库时触发。
小红书长图文发布 Skill
## 概述