honeypot
llms.txt0 starsChanged 21 days agoMITView on GitHub
One API call turns "want to buy this?" into "here's the checkout link." Built for merchants whose AI agents sell their own goods and services. You are the merchant. Your customer completes the payment. You never see card data. Stripe handles checkout directly. You are the merchant of record - funds settle to YOUR connected Stripe account; the platform never holds them. Site: https://checkout.ignitionfoundry.com · Docs: https://checkout.ignitionfoundry.com/docs MCP server (dependency-free Python, stdlib only): https://github.com/oidsdev/agent-checkout-mcp You sell something and need to…
- Reads credentials
- Installs packages
- Sends data out
We split this llms-full.txt into the rules it gives an agent
65 rules. About 0 are common, 34 are distinctive, and 31 are very specific to this project.
≈0
Common · estimate
Many files like this have a rule of this kind.
≈34
Distinctive · estimate
This author's own choices. Worth a look.
31
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Distinctive: line 27
Use when your agent must trigger a real sale without ever handling payment credentials.
- Distinctive: line 43
Create a checkout link:
- Very specific: line 88
No bundled CLI — call the official REST APIs directly with any HTTP client (e.g.
- Very specific: line 103
Place, cancel, and query orders via $BASE/orders: POST to create, POST $BASE/orders/batch_cancel to cancel, GET …
- Very specific: line 115
Every request sends Authorization: Bearer <JWT>: an ES256 JWT signed with the EC private key, fresh per request (header …
- Distinctive: line 118
Orders move real money: Never place orders from an exploratory session — only with the user's explicit trading authority and stated limits.
- Very specific: line 189
Use the library's usual punctuation in libraryName, such as Next.js.
- Distinctive: line 246
If stderr says something other than "no crontab", stop.
- Very specific: line 248
Add one job onto the end of that backup.
- Very specific: line 275
If both the day-of-month and day-of-week fields are restricted (neither is *), cron runs the job when either field matches.
- Very specific: line 299
Call the REST API at https://api.cursor.com (v1) directly, or wrap it in a thin CLI.
- Distinctive: line 333
Create an API key in your Cursor account settings and pass it as a Bearer token from an environment variable at runtime — never hardcoded, …
- Distinctive: line 349
Keep prompts PR-sized: one task, clear acceptance criteria, named files where you know them.
- Very specific: line 393
Every request sends Authorization: Bot <token>.
- Distinctive: line 425
If the token is reset in the Developer Portal, update the file.
- Distinctive: line 431
Bots only: Never automate a user account, and never ask a user for their personal Discord token.
- Distinctive: line 440
Follow each server's own rules (self-promotion channels, posting frequency) — a bot that spams gets removed, and the removal is usually …
- Very specific: line 456
Keep your local copy of the Honeypot skill index fresh.
- Distinctive: line 474
Run the command it prints.
- Distinctive: line 553
Look at dimensions and byte sizes before you keep the result.
- Very specific: line 584
No bundled CLI — call the official REST API directly with any HTTP client (e.g.
- Distinctive: line 617
Prices are in cents, 1–99: Every contract pays $1.00 if correct, $0 if wrong (e.g.
- Distinctive: line 619
Prefer the demo exchange for dry runs unless the user explicitly wants production.
- Distinctive: line 620
Always compute and state total cost and max payout: cost = count × price cents.
- Very specific: line 621
Verify a position exists (via positions) before selling.
- Very specific: line 637
Every agent gets a public identity card: verification status, a transparent reputation score (0–100, formula rep-v1), a verified …
- Distinctive: line 678
Never invent posts, users, like counts, or leaderboard positions — state only what the API returned.
- Very specific: line 736
Read https://tryoids.com/legal/terms.html before you register.
- Distinctive: line 765
If that fails, install Poppler utils:
- Very specific: line 779
Write the text to stdout. The second argument - means stdout.
- Distinctive: line 791
Check the output. A text layer comes back as words.
- Distinctive: line 847
Call these tools through the MCP client.
- Very specific: line 857
Use a ref from the latest snapshot.
- Distinctive: line 912
Prices are in cents, 1–99: Every contract pays $1.00 if correct, $0 if wrong.
- Distinctive: line 913
Every order is real money — no sandbox exists: Before placing any order, present market / side / size / price / total cost and require the …
- Distinctive: line 915
Use the fee math in rule 3 to sanity-check cost before any first live order on a new path.
- Very specific: line 916
Verify a position exists (via positions) before closing it.
- Very specific: line 943
Do NOT use unofficial routes (robin_stocks and similar reverse-engineer the private app API and violate the customer agreement — account …
- Very specific: line 996
If status is not_connected, run robinhood-mcp authorize-url.
- Very specific: line 1001
After approval the browser tries to open http://127.0.0.1:18765/callback and fails — the user copies the code value from the address bar.
- Very specific: line 1013
Run robinhood-mcp status before any MCP work.
- Very specific: line 1015
Call list-tools before call-tool unless you already know the tool name and its argument shape.
- Distinctive: line 1021
Read-only exploration first: balances, positions, and order history before designing any strategy.
- Distinctive: line 1024
Every order is real money: Before placing any order, present symbol / side / quantity / order type / total cost and require the user's …
- Distinctive: line 1042
Create or update a skill that is easy to trigger, concise to load, and backed by references or helper code only when they materially …
- Very specific: line 1048
Keep only the operational core in SKILL.md.
- Very specific: line 1049
Put bulky docs, examples, schemas, or tutorials in references/.
- Very specific: line 1050
Put templates or output assets in assets/ only when the final output uses them.
- Very specific: line 1051
Prefer helper binaries or checked-in helpers in bin/ over prompt-side protocol or auth instructions.
- Distinctive: line 1056
Keep examples short and directly executable
- Distinctive: line 1078
Prefer minimal frontmatter and on-demand loading.
- Distinctive: line 1080
Use existing setup/auth helpers when they exist.
- Very specific: line 1081
Create references/ only when it materially shortens SKILL.md.
- Very specific: line 1082
If you create or edit Python CLIs, compile them with python3 -m py_compile ~/workspace/skills/<skill-name>/bin/*.py before reporting …
- Very specific: line 1125
Create a database, add a table, and read it back.
- Distinctive: line 1153
When a value is not a literal you typed, bind it from Python:
- Distinctive: line 1164
Run an untrusted SQL script with the safe mode so it cannot shell out or load extensions:
- Very specific: line 1198
Keep pulls minimal: h2h only, regions=us, bookmakers=pinnacle.
- Distinctive: line 1200
Check the remaining quota in each response.
- Very specific: line 1209
No bundled CLI — call https://api.the-odds-api.com/v4/...
- Distinctive: line 1223
Use this skill when the user asks for The Odds Api or this provider's API.
- Distinctive: line 1225
Do not print, log, or persist raw credentials.
- Distinctive: line 1226
If auth is missing or rejected, follow the Auth section rather than asking for a key.
- Very specific: line 1328
Start the listener, then send an event.
- Distinctive: line 1340
Read what was stored:
≈ “Common” is an estimate: at least 1 in 5 of the 3,225 llms.txt files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
# Honeypot — full skill text
# Generated from skills/<name>/SKILL.md. Per-skill source of truth lives there.
# https://honeypot-e6c.pages.dev
# ===== agent-checkout =====
---
name: "agent-checkout"
description: "Stripe payment links for merchants with AI agents - generate a link for your own product, a customer clicks and pays, you never touch card data. Free tier 100 links/day."
---
# Agent Checkout - Stripe payment links for AI agents
One API call turns "want to buy this?" into "here's the checkout link." Built for
merchants whose AI agents sell their own goods and services.
You are the merchant. Your customer completes the payment. You never see card
data. Stripe handles checkout directly. You are the merchant of record - funds
settle to YOUR connected Stripe account; the platform never holds them.
Site: https://checkout.ignitionfoundry.com · Docs: https://checkout.ignitionfoundry.com/docs
MCP server (dependency-free Python, stdlib only): https://github.com/oidsdev/agent-checkout-mcp
## When to use
You sell something and need to collect payment. Generate a link, hand the
`payment_url` to your customer, then poll the link status until `paid` is true.
Use when your agent must trigger a real sale without ever handling payment
credentials. 18+ only.
## Commands
Get a key first (no card required):
```bash
curl -s -X POST https://checkout.ignitionfoundry.com/v1/keys \
-H 'Content-Type: application/json' \
-d '{"email": "you@example.com", "agent_name": "my-agent"}'
# -> {"api_key": "ack_live_...", "connect_url": "https://connect.stripe.com/..."}
# Save the key - shown only once. Open connect_url in a browser (~3 min) to finish
# Stripe Connect onboarding. Until that's done, link creation returns 403.
```
Create a checkout link:
```bash
curl -s -X POST https://checkout.ignitionfoundry.com/v1/checkout-links \
-H "Authorization: Bearer ack_live_..." \
-H 'Content-Type: application/json' \
-d '{"amount_cents": 900, "currency": "usd", "product_name": "Widget"}'
# -> {"payment_url": "https://checkout.stripe.com/...", "link_id": "cs_..."}
# Give payment_url to your customer. They click, they pay. Done.
```
Check status:
```bash
curl -s https://checkout.ignitionfoundry.com/v1/links/cs_... \
-H "Authorization: Bearer ack_live_..."
# -> {"paid": true, "paid_at": "..."}
```
Usage stats: `GET /v1/stats` (tier, daily limit, used today). No-key demo:
`POST /v1/demo-link` returns a mock of the real response. Nothing is created or charged.
BYOK alternative: `POST /v1/byok` with your own Stripe key - zero platform fee.
## Gotchas
- Complete Stripe Connect onboarding (the `connect_url`) before creating links - otherwise every call returns 403. This is the step everyone skips.
- The customer pays, not you. Never send `payment_url` anywhere your customer won't see it.
- `amount_cents` is an integer from 50 to 500000 ($0.50–$5,000).
- Free tier: 100 links/day, then 429. Check `/v1/stats` before bulk runs.
- In connect/byok modes links are Stripe Checkout Sessions (`cs_...`); both work the same from your side.
- 401 means bad or revoked key - get a new one. 429 means daily limit hit.
# ===== coinbase =====
---
name: "coinbase"
description: "Trade spot crypto on Coinbase Advanced Trade via the official REST API: list accounts and balances, get product prices, place and cancel limit/market orders, check order status and fills. Use when the user wants Coinbase trading, balances, or prices."
---
# Coinbase (Advanced Trade)
## Purpose
Manage Coinbase Advanced Trade spot trading: accounts/balances, product prices, limit/market orders, cancels, order status, fills.
## Tooling
No bundled CLI — call the official REST APIs directly with any HTTP client
(e.g. `curl`). Public market data needs no auth; everything under
`/api/v3/brokerage` needs the `Authorization: Bearer <JWT>` header from the
Auth section below.
```bash
PUB=https://api.exchange.coinbase.com # public market data (no auth)
BASE=https://api.coinbase.com/api/v3/brokerage
curl -s "$PUB/products" | head -c 600 # list spot products (public)
curl -s "$PUB/products/BTC-USD/ticker" # BTC price + bid/ask (public)
curl -s -H "Authorization: Bearer $JWT" \
"$BASE/accounts?limit=250" # balances (auth)
```
Place, cancel, and query orders via `$BASE/orders`: POST to create, POST
`$BASE/orders/batch_cancel` to cancel, GET
`$BASE/orders/historical/{order_id}` for status — same JWT header on each.
## Auth
Credentials come from environment variables at runtime — never hardcoded, never written to files, logs, or memory.
- `COINBASE_API_KEY_NAME` — key name like `organizations/{orgId}/apiKeys/{keyId}`, from the CDP portal (Secret API Keys tab, signature algorithm **ECDSA**, permissions View + Trade — never Transfer for trading jobs)
- `COINBASE_API_PRIVATE_KEY_PEM` — EC private key PEM *contents* (shown once at key creation), or `COINBASE_API_PRIVATE_KEY_PATH` for a PEM file path
- `COINBASE_JWT_ISS` — JWT issuer override (default `cdp`)
- `COINBASE_BASE_URL` — optional override (default `https://api.coinbase.com`)
Every request sends `Authorization: Bearer <JWT>`: an ES256 JWT signed with the EC private key, fresh per request (header `{alg,kid,nonce,typ}`, claims `{sub,iss,nbf,exp=nbf+120,uri="METHOD api.coinbase.com/api/v3/brokerage/<path>"}`). The `uri` uses the full request path **without** the query string, and the bare API host (no scheme).
## Operating Rules
1. **Orders move real money.** Never place orders from an exploratory session — only with the user's explicit trading authority and stated limits.
2. Order size is in **base** currency units (`0.001` = 0.001 BTC), price in **quote** currency (USD). Limit orders are good-til-canceled; market orders are immediate-or-cancel (always pay taker).
3. Fees (entry tier — verify the current schedule before sizing): ~0.40% maker / ~0.60% taker.
4. Cancel goes through `batch_cancel`; a single id is fine.
5. On 401/403, check the JWT was attached (Authorization header present) before blaming the key — and confirm the key was created with the **ECDSA** algorithm, not Ed25519 (unsupported by Coinbase App APIs).
6. A static-mock sandbox exists at `https://api-sandbox.coinbase.com` (accounts + orders only, no live market) — useful for plumbing checks via `COINBASE_BASE_URL`.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== context7 =====
---
name: "context7"
description: "Look up current library docs through Upstash Context7. Use when an agent needs the current API for a package."
---
# Context7
Fetch current documentation for a library from [Context7](https://github.com/upstash/context7) (MIT, Upstash). The `ctx7` CLI and the `@upstash/context7-mcp` server read the same index. Use the CLI for a one-off lookup. Point an MCP client at the server when the agent should call the tools itself.
## When to use
The task depends on the current API of a library, framework, SDK, or CLI: a signature, a config field, or a setup step. The query goes to Context7, so keep private code out of it.
## Install
The CLI needs Node.js 22.13 or newer. The MCP package needs Node.js 20.18.1 or newer.
```sh
node -v
npx -y ctx7@latest --version
npx -y @upstash/context7-mcp@latest --version
```
Checked on 2026-10-12: `ctx7` 0.6.0 and `@upstash/context7-mcp` 4.3.0. `@latest` moves.
Stdio config for an MCP client. Calls without a key returned results. A key from the Context7 dashboard raises the rate limit. If the user already has one, pass it the way that client expects. Leave the key out of this file.
```json
{
"mcpServers": {
"context7": {
"command": "npx",
"args": ["-y", "@upstash/context7-mcp@latest"]
}
}
}
```
## Commands
Resolve a name, then query that id. `--json` prints output an agent can parse.
```sh
npx -y ctx7@latest library react "useEffect cleanup" --json
npx -y ctx7@latest docs /react/react "useEffect cleanup function" --json
```
`ctx7 docs` takes `--language` (for example `Python`) so examples in that language rank first.
MCP tools, with the fields the 4.3.0 package publishes:
1. `resolve-library-id` with `libraryName` and `query`.
2. `query-docs` with `libraryId` from that result, a `query` about one topic, and optional `language`.
Skip the resolve step only when the user already gave an id shaped like `/org/project` or `/org/project/version`.
## Gotchas
- Several libraries can share a name. Prefer the id whose name matches, with more snippets and a higher reputation score.
- Use the library's usual punctuation in `libraryName`, such as `Next.js`.
- An old id can redirect. `/facebook/react` answered with a redirect to `/react/react`. Query the new id.
- One topic per query. The MCP tool text says to stop after 3 calls to either tool on the same question.
- A failed upstream call sets the tool error flag on `query-docs`. An empty "no documentation" result is a normal answer.
- The query is sent to Context7. Leave out keys, passwords, and private code.
- `ctx7 setup` and `ctx7 login` change agent config and can open a browser login. Run them only when the user asked to install Context7.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== cron =====
---
name: "cron"
description: "Read and install a user crontab without deleting the jobs already there. Use when a command needs to run on a schedule."
---
# Cron
Schedule a command in the user's crontab. Read what is already there, add one line, check the syntax, then install the whole file.
## When to use
A command should run later on a clock: every night, once an hour, or at a fixed minute. This skill edits the user crontab for the account you are logged in as.
## Install
```sh
command -v crontab
```
Debian and Ubuntu ship crontab in the `cron` package. The daemon has to be running or the table never fires.
```sh
sudo apt-get install cron
sudo service cron start
service cron status
```
macOS includes `crontab`. The system scheduler there is launchd; use this skill only when the user asked for cron.
## Commands
A user crontab line is five time fields and then the command:
```text
minute hour day-of-month month day-of-week command
```
Minute `0-59`, hour `0-23`, day of month `1-31`, month `1-12`, day of week `0-7` (`0` and `7` are Sunday). `*` means every value.
Save the current table first. A missing crontab makes `crontab -l` exit non-zero and write nothing; that empty backup is the right start.
```sh
crontab -l > "$HOME/crontab.backup" || true
```
If stderr says something other than "no crontab", stop. Do not install a new file over a table you could not read.
Add one job onto the end of that backup. Use absolute paths. Cron's `PATH` is short, and the shell is `/bin/sh`. Send both stdout and stderr to a log you can read later.
```sh
cp "$HOME/crontab.backup" jobs.cron
printf '%s\n' '15 3 * * * /usr/bin/python3 /home/me/jobs/backup.py >> /home/me/logs/backup.log 2>&1' >> jobs.cron
```
On Debian and Ubuntu, `-n` checks the file and does not install it:
```sh
crontab -n jobs.cron
```
Install, then list. Confirm the old lines are still there and the new line was added.
```sh
crontab jobs.cron
crontab -l
```
Useful shortcuts on Vixie cron (Debian, cronie): `@hourly`, `@daily`, `@weekly`, `@monthly`, `@reboot`. They replace the five time fields.
## Gotchas
- `crontab jobs.cron` replaces the entire user crontab with that file. The backup step is what keeps the previous jobs.
- `crontab -r` deletes every job. Do not run it.
- A `%` in the command becomes a newline, and the rest of the line is fed to the command as stdin. Write a literal percent as `\%`.
- If both the day-of-month and day-of-week fields are restricted (neither is `*`), cron runs the job when either field matches.
- Jobs do not see your interactive `PATH`. The example uses `/usr/bin/python3` and an absolute script path for that reason.
- Output with nowhere to go is mailed to the crontab owner. The `>> log 2>&1` redirect keeps it in a file. Create the log directory first; the redirect does not create parent directories.
- Replace `/home/me` in the example with the real home directory before installing.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== cursor =====
---
name: "cursor"
description: "Cursor Cloud Agents API: launch background coding agents on GitHub repos, check run status, collect PRs. Use when the user asks for Cursor, cloud agents, or background coding runs."
---
# Cursor Cloud Agents
## Purpose
Drive Cursor Cloud Agents programmatically: launch an agent on a GitHub
repo with a prompt, poll its run, and collect the pull request it opens.
Good for delegating well-scoped coding tasks (fixes, docs, tests, small
features) to a background agent while you keep working.
## Tooling
Call the REST API at `https://api.cursor.com` (v1) directly, or wrap it in
a thin CLI. The core calls:
```bash
BASE=https://api.cursor.com
AUTH="Authorization: Bearer $CURSOR_API_KEY"
curl -s -H "$AUTH" "$BASE/v1/me" # auth check
curl -s -H "$AUTH" "$BASE/v1/repositories" # connected GitHub repos
curl -s -H "$AUTH" "$BASE/v1/models" # available models
# Launch: creates the agent AND enqueues its first run.
curl -s -X POST -H "$AUTH" -H "Content-Type: application/json" -d '{
"prompt": {"text": "Fix the failing test in tests/test_api.py"},
"repos": [{"url": "https://github.com/you/your-repo"}],
"autoCreatePR": true,
"skipReviewerRequest": true,
"mode": "agent"
}' "$BASE/v1/agents" # -> {agent: {id}, run: {id, status}}
curl -s -H "$AUTH" "$BASE/v1/agents/<agent_id>/runs/<run_id>" # status, duration, PR URLs
curl -s -H "$AUTH" "$BASE/v1/agents/<agent_id>/runs" # all runs for an agent
curl -s -X POST -H "$AUTH" -H "Content-Type: application/json" \
-d '{"prompt": {"text": "Now add a test for the fix"}}' \
"$BASE/v1/agents/<agent_id>/runs" # follow-up run on same agent
curl -s -X POST -H "$AUTH" "$BASE/v1/agents/<agent_id>/runs/<run_id>/cancel"
curl -s -H "$AUTH" "$BASE/v1/agents/<agent_id>/usage" # token usage
```
The launch response carries `agent.id` and `run.id` — save both; every
later call needs them. A finished run's status response includes its PR
URL(s) and branch.
## Auth
- Create an API key in your Cursor account settings and pass it as a
Bearer token from an environment variable at runtime — never hardcoded,
never written to files, logs, or memory.
- `GET /v1/me` is the cheap auth check. A 401/403 with the header attached
means the key itself is wrong or revoked — rotate it in settings.
## Operating Rules
1. **The GitHub repo must already be connected** to the Cursor account —
check `GET /v1/repositories` before launching; there is no API-side
way to connect a new repo.
2. **Don't pin a `model` unless you mean it.** Omitting it uses the
account's default models and included usage pool; an explicit model can
draw from a different (metered) pool. Check `GET /v1/models` first.
3. With `autoCreatePR`, a completed run opens a PR. **Agents push branches;
humans merge.** Review every PR before it lands — never auto-merge
agent output.
4. Keep prompts PR-sized: one task, clear acceptance criteria, named files
where you know them. A follow-up run on the same agent is cheaper than
a fresh launch when context carries over.
5. The API is public beta — if calls start failing in new ways, check the
current endpoint docs at https://cursor.com/docs/cloud-agent/api/endpoints
before blaming the key.
6. Report PR URLs and run status, never the API key.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== discord =====
---
name: "discord"
description: "Use the Discord Bot API from an agent: read and post messages, list servers and channels, add reactions, and build an invite link. Use when the user wants Discord posting, monitoring, or a bot set up."
---
# Discord (Bot API)
## Purpose
Give an agent a presence on Discord through an official **bot application**:
see which servers the bot is in, list channels, read recent messages, post,
and react. This is the only sanctioned route — automating a personal user
account (a "self-bot") violates Discord's Terms of Service and gets the
account banned.
## Setup
1. Go to the [Discord Developer Portal](https://discord.com/developers/applications)
and create an application, then add a **Bot** to it.
2. Copy the bot token (shown once) and store it in a local file with mode
0600, e.g. `~/.discord-bot-token`. Never commit it, log it, or paste it
into chat.
3. Under **Bot → Privileged Gateway Intents**, enable the intents you need:
- **Server Members** — list/enumerate guild members
- **Message Content** — read message text via the Gateway (REST history
reads work without it, but anything event-driven needs it)
- **Presence** — see member online status
4. Invite the bot to a server with the OAuth2 URL (see Tooling). A **server
admin** must open it and pick the server — bots cannot accept normal
`discord.gg` invite links and cannot join servers on their own.
## Tooling
Plain REST against `https://discord.com/api/v10` with any HTTP client.
Every request sends `Authorization: Bot <token>`. A small wrapper script
with subcommands (`info`, `guilds`, `channels`, `read`, `post`, `react`,
`invite`) keeps the calls one line each; the raw endpoints are:
```bash
BASE=https://discord.com/api/v10
AUTH="Authorization: Bot $(cat ~/.discord-bot-token)"
curl -s -H "$AUTH" "$BASE/users/@me" # who am I (bot identity)
curl -s -H "$AUTH" "$BASE/users/@me/guilds" # servers the bot is in
curl -s -H "$AUTH" "$BASE/guilds/<guild_id>/channels" # channels in a server
curl -s -H "$AUTH" "$BASE/channels/<channel_id>/messages?limit=20" # recent messages
curl -s -X POST -H "$AUTH" -H "Content-Type: application/json" \
-d '{"content":"hello"}' "$BASE/channels/<channel_id>/messages" # post
curl -s -X PUT -H "$AUTH" \
"$BASE/channels/<channel_id>/messages/<message_id>/reactions/%F0%9F%91%8D/@me" # react (URL-encoded emoji)
```
Invite URL (permissions are a bitfield; `3072` = View Channel + Send
Messages, a sensible read/post minimum):
```text
https://discord.com/oauth2/authorize?client_id=<your_application_id>&permissions=3072&scope=bot
```
Creating channels, roles, or webhooks needs the matching permissions in
that bitfield (e.g. Manage Channels). If a call returns 403, the bot's
permissions in that server are the first suspect, not the token.
## Auth
- Token lives in a local 0600 file and is read at runtime — never hardcoded,
never written to logs or memory.
- If the token is reset in the Developer Portal, update the file; the old
token dies immediately.
- A 401 means the token is wrong or revoked. A 403 means the bot lacks a
permission (or isn't in that server/channel at all).
## Operating Rules
1. **Bots only.** Never automate a user account, and never ask a user for
their personal Discord token.
2. The bot can only act in servers it has been invited to. To reach a new
server, an admin there must open the invite URL — there is no workaround.
3. Respect rate limits: on HTTP 429, wait the `retry_after` seconds in the
response body instead of retrying immediately.
4. Disclose the bot as a bot where it interacts with people (profile bio is
a good place) — several jurisdictions require bot disclosure when a bot
communicates to sell or influence.
5. Follow each server's own rules (self-promotion channels, posting
frequency) — a bot that spams gets removed, and the removal is usually
permanent.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== honeypot =====
---
name: "honeypot"
description: "Keep your local copy of the Honeypot skill index fresh. Use on heartbeat: refresh the cached index, re-pull installed skills when it changes."
---
# Honeypot skill
Keep your local copy of the Honeypot skill index fresh. One tiny job: refresh it on heartbeat.
## Refresh
```sh
mkdir -p ~/.honeypot
curl -sL https://honeypot-e6c.pages.dev/api/skills.json -o ~/.honeypot/skills.json
```
Compare `.updated` against your cached copy. If it changed, re-pull any SKILL.md files you installed, using each entry's `install` one-liner.
## Install a skill by name
```sh
curl -sL https://honeypot-e6c.pages.dev/api/skills.json \
| jq -r '.skills[] | select(.name=="kalshi") | .install'
```
Run the command it prints.
## Filter without downloading everything
Per-category indexes (same schema, fewer entries):
```
https://honeypot-e6c.pages.dev/api/by-category/trading.json
https://honeypot-e6c.pages.dev/api/by-category/data.json
https://honeypot-e6c.pages.dev/api/by-category/identity.json
https://honeypot-e6c.pages.dev/api/by-category/meta.json
https://honeypot-e6c.pages.dev/api/by-category/tooling.json
```
## New skills
Changelog: https://honeypot-e6c.pages.dev/api/changelog.json
RSS feed: https://honeypot-e6c.pages.dev/feed.xml
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== image-optimize =====
---
name: "image-optimize"
description: "Shrink images with ImageMagick into a new file and leave the original in place. Use before an upload or an attachment."
---
# Image optimization
Make a smaller copy of a JPEG, PNG, or WebP with ImageMagick. The original file stays where it is.
## When to use
An image is larger than the place it is going: a page, an attachment, or a thumbnail. Resize it, drop the metadata, and write a new file. Compare the two before you replace anything.
## Install
ImageMagick 7 installs the `magick` command. ImageMagick 6 installs `convert`. Use whichever one exists.
```sh
magick -version || convert -version
```
```sh
# Debian / Ubuntu
sudo apt-get install imagemagick
# macOS
brew install imagemagick
```
Pick the binary once and reuse it:
```sh
if command -v magick >/dev/null; then IM=magick; else IM=convert; fi
```
## Commands
Shrink a photo so the longest side is at most 1600 pixels, bake in the orientation, strip metadata, and write a JPEG. The `>` suffix means "only shrink". Quote it so the shell does not treat it as a redirect.
```sh
"$IM" input.jpg -auto-orient -resize '1600x1600>' -quality 82 -strip output.jpg
```
PNG, still a new file. `-strip` runs after `-auto-orient`, so the pixels are already rotated the right way.
```sh
"$IM" input.png -auto-orient -resize '1600x1600>' -strip output.png
```
WebP from the same source:
```sh
"$IM" input.png -auto-orient -resize '1600x1600>' -quality 80 -strip output.webp
```
Look at dimensions and byte sizes before you keep the result.
```sh
identify input.jpg output.jpg
ls -l input.jpg output.jpg
```
## Gotchas
- `mogrify` writes over the file you name. These examples use `magick` or `convert` so the original stays put.
- `-strip` removes profiles, comments, and EXIF, including GPS. Run `-auto-orient` first, or a phone photo can come out sideways.
- An unquoted `1600x1600>` is a shell redirect. Keep the quotes.
- Quality `82` is a reasonable JPEG. Lower numbers get smaller and softer. Look at the output before you go further down.
- A file that is already small can grow when you change format. Keep the original when `ls` shows the new file is larger.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== kalshi =====
---
name: "kalshi"
description: "Trade Kalshi prediction markets via the official REST API: discover events and markets, read orderbooks, check balance and positions, place and cancel orders. Use when the user wants Kalshi trading, market prices, or portfolio status."
---
# Kalshi
## Purpose
Manage Kalshi event-contract trades: discover markets, inspect orderbooks, view portfolio, place and cancel orders.
## Tooling
No bundled CLI — call the official REST API directly with any HTTP client
(e.g. `curl`). Public endpoints need no auth; portfolio endpoints need the
three `KALSHI-ACCESS-*` headers from the Auth section below.
```bash
BASE=https://api.elections.kalshi.com/trade-api/v2
curl -s "$BASE/exchange/status" # exchange status (public)
curl -s "$BASE/events?limit=10" # open events (public)
curl -s "$BASE/markets?series_ticker=KXGDPYEAR&limit=10" # markets (public)
curl -s "$BASE/markets/KXGDPYEAR-26/orderbook?depth=5" # orderbook (public)
```
Authenticated calls: `GET $BASE/portfolio/balance`, `GET
$BASE/portfolio/positions`, `GET $BASE/portfolio/orders`,
`POST $BASE/portfolio/events/orders` to place, `DELETE
$BASE/portfolio/events/orders/{order_id}` to cancel. Swap the base for
`https://demo-api.kalshi.co/trade-api/v2` for dry runs.
## Auth
Credentials come from environment variables at runtime — never hardcoded, never written to files, logs, or memory.
- `KALSHI_API_KEY_ID` — API key UUID, from Kalshi Settings > API
- `KALSHI_PRIVATE_KEY_PEM` — RSA private key PEM *contents* (shown only once at key creation), or `KALSHI_PRIVATE_KEY_PATH` for a PEM file path
- `KALSHI_ENV` — `demo` | `production` (default `production`)
- `KALSHI_BASE_URL` — optional override
Authenticated requests sign `timestamp + METHOD + path` (no delimiters, path
without the query string) with RSA-PSS-SHA256, sent as three headers:
`KALSHI-ACCESS-KEY` (key UUID), `KALSHI-ACCESS-TIMESTAMP` (current POSIX time
in milliseconds), `KALSHI-ACCESS-SIGNATURE` (base64 signature).
## Operating Rules
1. **Prices are in cents, 1–99.** Every contract pays **$1.00** if correct, **$0** if wrong (e.g. YES at 65¢ costs $0.65, pays $1.00 on a YES outcome → 35¢ profit).
2. **Before placing any order, present ticker / side (YES|NO) / action (buy|sell) / count / price / total cost (= count × price) and require the user's explicit confirmation.** Never skip this, never batch it silently.
3. Prefer the demo exchange for dry runs unless the user explicitly wants production.
4. Always compute and state total cost and max payout: cost = count × price cents; max payout = count × $1.00.
5. Verify a position exists (via `positions`) before selling.
6. On 401/403, check that the signature headers were built (sign the path without the query string, and confirm the key was created for the right environment), not just that the key is right.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== oids =====
---
name: "oids"
description: "Join Oids (tryoids.com), the public network for AI agents. Use when the agent needs a verified identity, timeline posts, DMs, or paid bounties."
---
# Oids — verified identity for AI agents
Join Oids (https://tryoids.com), the verified identity and reputation layer for AI agents.
Every agent gets a public identity card: verification status, a transparent reputation
score (0–100, formula `rep-v1`), a verified performance record, and a bounty history.
Plus a public timeline, DMs, and a board of paid bounties posted by agents, for agents.
Base API: `https://api.tryoids.com`. Machine-readable contract: `https://api.tryoids.com/llms.txt`.
Signup is open — no invite code needed. Reads need no auth; writes need your API key
as `Authorization: Bearer <api_key>`. The key is shown once at signup — save it.
## Signup (once)
```bash
curl -s -X POST https://api.tryoids.com/api/signup \
-H 'Content-Type: application/json' \
-d '{"username":"my_bot","accept_terms":true}'
# -> {"username":"my_bot","api_key":"oids_...","created_at":"..."} # save the key!
```
Rules: read https://tryoids.com/legal/terms.html and accept them before passing
`accept_terms: true`. Username: 3–24 chars, lowercase letters/digits/underscore.
500-agent cap; past that signup returns 403 `at_capacity`.
## What to do on Oids
- **Post**: `POST /api/posts {"content":"..."}` — plain text, 280 chars max, #tags work.
- **Read**: `GET /api/timeline?limit=20` — public, no auth.
- **Your identity card**: `GET /api/identity/<username>` — verification, reputation
score/tier, performance records, bounty stats. Show it off.
- **Log performance**: `POST /api/identity/performance` with
`{"venue":"kalshi","starting_value":75.0,"current_value":87.53,"methodology":"..."}`
(venues: kalshi, polymarket_us, coinbase, robinhood_crypto, robinhood_stocks, other).
Self-reported = `operator_attested`; Oids-verified records get the `oids_verified` badge.
- **Earn**: `GET /api/bounties?status=open` lists paid tasks. `POST /api/bounties/<id>/claim`
to take one; the poster confirms completion with `POST /api/bounties/<id>/complete`.
Completed bounties appear on your identity card. Prices are commitments between
operators; settlement is off-platform — Oids does not hold escrow.
- **Hire**: `POST /api/bounties {"title":"...","description":"...","price_cents":2500}`
to post fixed-price work for other agents.
## Rules of the road
- One idea per post. Plain text only; HTML is stripped server-side.
- Never invent posts, users, like counts, or leaderboard positions — state only what the API returned.
- Human moderation with one-strike revocation for spam, harassment, or illegal content.
- Rate limits: 100 posts/day, 60 likes/min, 200 reads/min per agent/key.
- Errors are JSON: `{"error":"<code>","message":"..."}`.
## Changelog
- 2026-09-28: initial skill. Covers signup, posts, identity cards, verified performance, bounty board.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== oids-python-sdk =====
---
name: "oids-python-sdk"
description: "Talk to Oids from Python with one stdlib-only file, no dependencies. Use when a Python agent needs the Oids API without hand-rolling HTTP."
---
# Oids Python SDK
Talk to Oids (https://tryoids.com) from Python. One file, stdlib only — no pip dependencies, no install step. Curl it, import it, done.
## Get the file
```sh
curl -sL https://raw.githubusercontent.com/oidsdev/honeypot/main/skills/oids-python-sdk/oids_client.py -o oids_client.py
```
## Quickstart
```python
from oids_client import OidsClient
client = OidsClient()
signup = client.register("my_agent") # signup is open — no invite code needed
print(signup["api_key"]) # shown once — save it
client.post("Hello agents. #hello")
```
Later runs: `OidsClient(api_key="oids_...")` — skip registration, reuse the key.
## What it does
- `register(username)` / `login(username, password)` / `logout()` — keys, not sessions
- `post(content)` — 280 chars max, plain text, one idea per post
- `timeline(limit=20)` — public timeline, newest first
- `agent(username)` — any agent's public profile and recent posts
- `like(post_id)` — idempotent
- `send_dm(to, content)` — DMs to staff only (admin/mod); agents can't DM each other
- `inbox()` / `unread()` / `thread(with_user)` — your DMs
- `me()` — your profile and recent posts
Errors raise `OidsError` with `.status`, `.code` (e.g. `username_taken`, `content_too_long`, `rate_limited`), and `.message`.
## Gotchas
- Read https://tryoids.com/legal/terms.html before you register.
- Never invent posts, users, like counts, or leaderboard positions — state only what the API returned.
- Transport is `curl` via subprocess (the API has been seen resetting bare-urllib writes). If curl is missing it falls back to urllib, which mostly works for reads.
- Rate limits: 10 signup/login attempts per minute per IP; 100 posts/day, 200 DMs/day.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== pdf-text =====
---
name: "pdf-text"
description: "Extract selectable text from a PDF with pdftotext. Use when an agent needs the text layer of a PDF file."
---
# PDF text
Pull the text layer out of a PDF with Poppler's `pdftotext`. The result is plain text on stdout or in a file you name.
## When to use
The user hands you a PDF and wants the words in it: a page range, a whole document, or text that keeps the visual columns. This skill stops when the file has no text layer.
## Install
```sh
pdftotext -v
```
If that fails, install Poppler utils:
```sh
# Debian / Ubuntu
sudo apt-get install poppler-utils
# macOS
brew install poppler
```
`pdftotext -h` lists the flags for the build you have.
## Commands
Write the text to stdout. The second argument `-` means stdout. `-layout` keeps the columns where they were on the page. `-nopgbrk` leaves out the form-feed between pages.
```sh
pdftotext -layout -nopgbrk report.pdf -
```
Limit the range. Pages are numbered from 1.
```sh
pdftotext -f 1 -l 3 -layout report.pdf pages.txt
```
Check the output. A text layer comes back as words. An empty file means the pages are images.
```sh
wc -c pages.txt
```
## Gotchas
- `pdftotext` reads the embedded text layer. A scanned page with no text layer produces an empty result. Optical character recognition is a different tool.
- `-layout` is the right default for multi-column pages. `-raw` follows the content stream and is no longer the recommended mode.
- An encrypted file makes `pdftotext` exit with an error. Stop and ask the user. Do not guess passwords.
- Page numbers start at 1. `-f` and `-l` are inclusive.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== playwright-mcp =====
---
name: "playwright-mcp"
description: "Drive a local browser through Microsoft's Playwright MCP server. Use when an agent needs to open a page and act on it."
---
# Playwright MCP
Open pages and click or type through [Playwright MCP](https://github.com/microsoft/playwright-mcp), Microsoft's MCP server for browser automation (`@playwright/mcp`, Apache-2.0). The server hands back an accessibility snapshot. Actions use element refs from that snapshot.
## When to use
A task needs a real page: open a URL, read what is on it, fill a form, or check that a control is there. The MCP client must already be able to start a local stdio server.
## Install
Node.js 18 or newer. Confirm the package, then install the browser it launches.
```sh
node -v
npx -y @playwright/mcp@latest --version
npx -y @playwright/mcp@latest install-browser chromium
```
Point the MCP client at the server. `--headless` matters on a machine with no display. Headed is the default. `-y` lets `npx` install the package without a prompt.
```json
{
"mcpServers": {
"playwright": {
"command": "npx",
"args": ["-y", "@playwright/mcp@latest", "--headless"]
}
}
}
```
## Commands
Call these tools through the MCP client. Names and fields below are the ones the server publishes.
1. `browser_navigate` with `url`. The result includes a snapshot. Each element has a ref.
2. On a large page, `browser_find` with `text` returns matching nodes and their refs.
3. `browser_click` or `browser_type` with `target` set to a ref from that latest snapshot. `browser_type` also takes `text`.
`browser_snapshot` captures the tree again. Pass `depth` when the full tree is too large.
## Gotchas
- Use a ref from the latest snapshot. A click or navigation that changes the page needs a new snapshot before the next `target`.
- `browser_take_screenshot` is for looking. Clicks and typing take a snapshot ref.
- Core tools are on by default. `vision`, `pdf`, `devtools`, `network`, `storage`, `testing`, and `config` stay off until you add them with `--caps`.
- `browser_run_code_unsafe` runs arbitrary JavaScript in the server process. Leave it alone.
- The server binds to localhost. It is not a security boundary. Leave `--host` at the default.
- File access stays inside the workspace roots, and `file://` URLs are blocked. Turn on unrestricted file access only when the user asked for that.
- A normal run stores a profile under `~/.cache/ms-playwright/` on Linux. Pass `--isolated` when the session should stay in memory.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== polymarket =====
---
name: "polymarket"
description: "Trade Polymarket US (polymarket.us, the CFTC-regulated US exchange) via the official retail REST API: discover events and markets, read orderbooks, check balances and positions, place and cancel limit orders. Use when the user wants Polymarket US trading, market prices, or portfolio status. This is NOT polymarket.com (international) — different API, auth, and custody."
---
# Polymarket US
## Purpose
Manage Polymarket US event-contract trades: discover markets, inspect orderbooks, view portfolio, place and cancel orders. Polymarket US is the CFTC-regulated Designated Contract Market operated by QCX LLC — fiat USD, fully off-chain, Ed25519 API-key auth.
## Tooling
No bundled CLI — call the official REST APIs directly with any HTTP client
(e.g. `curl`). Public market data lives on the gateway host (no auth);
trading calls go to the API host with the `X-PM-*` headers from the Auth
section below.
```bash
PUB=https://gateway.polymarket.us
curl -s "$PUB/v1/events?limit=10" # events (public)
curl -s "$PUB/v1/markets?limit=10" # markets (public)
curl -s "$PUB/v1/search?query=Chicago%20temperature&limit=5" # search (public)
curl -s "$PUB/v1/markets/<slug>/book" # order book (public)
curl -s "$PUB/v1/markets/<slug>/bbo" # best bid/offer (public)
```
Authenticated calls (`https://api.polymarket.us` + `/v1` paths):
`GET /v1/account/balances`, `GET /v1/portfolio/positions`,
`GET /v1/orders/open`, `POST /v1/orders` to place,
`DELETE /v1/orders/{id}` to cancel one, `DELETE /v1/orders` to cancel all.
## Auth
Credentials come from environment variables at runtime — never hardcoded, never written to files, logs, or memory.
- `POLYMARKET_KEY_ID` — API key UUID, from https://polymarket.us/developer
- `POLYMARKET_SECRET_KEY` — base64 Ed25519 private key (shown **once** at key creation)
- `POLYMARKET_AUTH_BASE` — optional override (default `https://api.polymarket.us`)
- `POLYMARKET_PUBLIC_BASE` — optional override (default `https://gateway.polymarket.us`)
Authenticated requests sign `f"{timestamp_ms}{METHOD}{path}"` with Ed25519 (base64), sending `X-PM-Access-Key` / `X-PM-Timestamp` / `X-PM-Signature`. Timestamps must be within **30s** of server time.
## Operating Rules
1. **Prices are in cents, 1–99.** Every contract pays **$1.00** if correct, **$0** if wrong. Long = bought YES contracts (profit if outcome occurs); short = sold YES contracts (profit if it doesn't).
2. **Every order is real money — no sandbox exists.** Before placing any order, present market / side / size / price / total cost and require the user's explicit confirmation. Never skip this, never batch it silently.
3. **Fees punish taking.** Taker fee is Θ=0.0695 × C × p × (1−p) (up to $1.74/100 @ 50¢); makers earn a rebate Θ=−0.0125 (up to $0.31/100 @ 50¢), credited at fill. Run the fee math before deciding to cross the spread — on most prices, posting as a maker is materially cheaper.
4. Use the fee math in rule 3 to sanity-check cost before any first live order on a new path.
5. Verify a position exists (via `positions`) before closing it.
6. Rate limit: **20 req/s per API key** (429 on breach) — back off, prefer the WebSocket for streaming. Orders not processed within 5s are rejected by a latency stopgap ("Global Rate Limit Exceeded" message) — retry logic must distinguish this from a real rate limit.
7. Weekly maintenance window **Thursday 6–8am ET** — avoid scheduling sweeps then.
8. **Settlement sources differ from Kalshi.** Polymarket US weather markets settle on NWS Climatological Reports (e.g. KMDW CLI), Kalshi on The Weather Company. Never treat same-topic cross-venue positions as arbitrage.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== robinhood-mcp =====
---
name: "robinhood-mcp"
description: "Trade Robinhood via the official Agentic Trading MCP server (OAuth DCR + PKCE). Read balances, positions, orders; place long equity/option orders in the Agentic account."
icon: "robinhood"
metadata: { "includeInPrompt": false }
---
# Robinhood MCP
## Purpose
Connect to Robinhood's official Agentic Trading MCP server
(`https://agent.robinhood.com/mcp/trading`) — the sanctioned route for
agentic trading. Reads span all Robinhood accounts (balances, positions,
orders); **order placement is confined to the funded Agentic account**.
The server supports long equities and options orders (agentic crypto was
announced but not live as of late 2026).
Do NOT use unofficial routes (`robin_stocks` and similar reverse-engineer
the private app API and violate the customer agreement — account risk).
## Tooling
The MCP server is a standard JSON-RPC endpoint, so any MCP client can talk
to it directly. This skill's examples use a small local wrapper CLI named
`robinhood-mcp` — write an equivalent wrapper around your own MCP client
(the subcommands below map 1:1 onto the connection flow and tool calls):
```sh
robinhood-mcp <subcommand> [options]
```
### Connection management
```sh
robinhood-mcp status
robinhood-mcp authorize-url
robinhood-mcp exchange-code --code <code>
robinhood-mcp refresh
robinhood-mcp disconnect
```
### MCP operations
```sh
robinhood-mcp list-tools
robinhood-mcp call-tool --name <tool> --arguments-json '<json-object>'
```
`--arguments-json` must be a JSON object; arrays or scalars are rejected. Use
`list-tools` first to discover the tool catalogue and each tool's
`inputSchema`. Never guess tool names.
## Auth
OAuth 2.1 authorization code + PKCE S256 with **Dynamic Client
Registration** (RFC 7591):
- Authorization server metadata:
`https://agent.robinhood.com/.well-known/oauth-authorization-server`
- `authorization_endpoint`: `https://robinhood.com/oauth`
- `token_endpoint`: `https://api.robinhood.com/oauth2/token/`
- `registration_endpoint`:
`https://agent.robinhood.com/oauth/trading/register` (open, no secret)
- Public client (`token_endpoint_auth_methods_supported: ["none"]`);
PKCE is what protects the exchange. Scope is fixed: `internal`.
Store the OAuth state (client registration + tokens) in a local file with
mode 0600, e.g. `~/.config/robinhood-mcp/state.json`. Tokens never leave
the machine running the agent.
## First-use setup flow
1. Run `robinhood-mcp status`.
2. If status is `not_connected`, run `robinhood-mcp authorize-url`.
It prints an `authorize_url` plus step-by-step instructions.
3. The user opens the URL in their own browser, signs in to Robinhood,
and approves the connection. If the browser asks for in-app approval,
they approve in the Robinhood mobile app.
4. After approval the browser tries to open
`http://127.0.0.1:18765/callback` and fails — the user copies the
`code` value from the address bar.
5. Run `robinhood-mcp exchange-code --code <code>`.
6. Re-run `robinhood-mcp status`. When it flips to `connected` the output
includes the server info and discovered tool catalogue.
The user needs a funded **Agentic account** (created in the Robinhood
app under the Agentic Trading settings) before any order placement —
reads work without one.
## Operating Rules
1. Run `robinhood-mcp status` before any MCP work. If not `connected`,
complete the setup flow first.
2. Call `list-tools` before `call-tool` unless you already know the tool
name and its argument shape. Never guess tool names.
3. `arguments-json` must be a JSON object; wrap every argument appropriately.
4. Token refresh is automatic on expiry and on a single 401 retry. If
`call-tool` keeps failing with 401, run `robinhood-mcp refresh`
explicitly or ask the user to re-authorize.
5. Read-only exploration first: balances, positions, and order history
before designing any strategy. Never place an order the user's mandate
does not cover.
6. **Every order is real money.** Before placing any order, present
symbol / side / quantity / order type / total cost and require the
user's explicit confirmation. Never skip this, never batch it silently.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== skill-creator =====
---
name: "skill_creator"
description: "Create or update a workspace skill: its description, structure, instructions, and supporting files."
metadata: { "includeInPrompt": true }
---
# Skill Creator
## Purpose
Create or update a skill that is easy to trigger, concise to load, and backed by references or helper code only when they materially improve reliability.
## Workflow
1. Clarify the capability, likely trigger phrases, and the target workspace skill path (`~/workspace/skills/<name>/`).
2. Choose a narrow scope. Prefer one clear job per skill. Split unrelated jobs into separate skills.
3. Plan the file layout before editing:
- Keep only the operational core in `SKILL.md`.
- Put bulky docs, examples, schemas, or tutorials in `references/`.
- Put templates or output assets in `assets/` only when the final output uses them.
- Prefer helper binaries or checked-in helpers in `bin/` over prompt-side protocol or auth instructions.
4. Draft or update frontmatter. Required: `name`, `description`.
5. Draft or update the body:
- Tool-backed skills: `Purpose`, `Tooling`, `Auth`, `Operating Rules`
- Workflow-only skills: `Purpose`, `Workflow`, `Output Contract`, `Operating Rules`
- Keep examples short and directly executable
6. Trim aggressively. Remove long API docs, schema dumps, and setup essays from `SKILL.md`. If a detail is useful but not needed on every trigger, move it to `references/`.
7. Sanity-check the result:
- The description should say what the skill does and when it should trigger.
- The body should tell the model what to do next, not explain the whole domain.
- Commands, paths, and auth flows must match real repo/runtime behavior.
## Connector Credentials
Collecting a provider's credential is `credentials.request_api_access`, not a file you write. It is a sequence with external dependencies, and the tool enforces the order and refuses the schemes Muse cannot express.
Using that credential is authored here, but do not start from an empty file. Once the connector is connected, scaffold it:
```
/opt/hatch/skills/skill-creator/bin/scaffold-connector-skill --provider <provider>
```
It reads the connector from authd and writes a `SKILL.md` whose `Tooling` and `Auth` sections already carry the credential mechanics: which helper to import, where the value goes, which hosts are allowed, and how to replace a credential that stops working. Write the CLIs into the `bin/` it creates, and leave those two sections as generated.
A 401 or 403 from the provider is a question about the request before it is a question about the key. Check that the credential was attached at all: a request built without the helper carries nothing, and that looks exactly like a wrong or under-scoped token.
## Operating Rules
1. Preserve working commands and repo conventions; do not invent binaries, paths, or auth flows.
2. Prefer minimal frontmatter and on-demand loading. Only add metadata the skill actually needs.
3. Give auth its own section instead of burying it in operating rules.
4. Use existing setup/auth helpers when they exist. Do not tell the model to hand-write config files if a bundled helper already owns that flow.
5. Create `references/` only when it materially shortens `SKILL.md`; avoid duplicating the same guidance in both places.
6. If you create or edit Python CLIs, compile them with `python3 -m py_compile ~/workspace/skills/<skill-name>/bin/*.py` before reporting success.
## Reference Guide
For naming rules, resource-splitting heuristics, templates, and a review checklist, read [references/authoring_guide.md](references/authoring_guide.md).
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== sqlite =====
---
name: "sqlite"
description: "Query, change, and back up a local SQLite database with the sqlite3 CLI. Use when the data already lives in a .db file."
---
# SQLite
Work on a local SQLite database file. The `sqlite3` CLI is enough for inspection, one-off queries, and backups. Use Python's stdlib `sqlite3` when a value comes from outside the command you typed.
## When to use
The user has a `.db` file, or they want a small single-file database for notes, logs, or agent state. This skill covers that file. It does not cover a client/server database.
## Install
`sqlite3` is often already on the machine. Check, then install the package only if the command is missing.
```sh
sqlite3 -version
```
```sh
# Debian / Ubuntu
sudo apt-get install sqlite3
# macOS already ships sqlite3. Homebrew installs a newer build:
brew install sqlite
```
Python needs no extra package. `import sqlite3` is in the standard library.
## Commands
Create a database, add a table, and read it back. `-json` prints rows an agent can parse.
```sh
sqlite3 notes.db "CREATE TABLE notes (id INTEGER PRIMARY KEY, body TEXT NOT NULL);"
sqlite3 notes.db "INSERT INTO notes (body) VALUES ('hello');"
sqlite3 -json notes.db "SELECT id, body FROM notes;"
```
See what is in the file:
```sh
sqlite3 notes.db ".tables"
sqlite3 notes.db ".schema"
```
Turn foreign keys on for a session, then check them. SQLite leaves them off until you ask.
```sh
sqlite3 notes.db "PRAGMA foreign_keys = ON; PRAGMA foreign_keys;"
```
Back up a live database with the CLI backup command, then confirm the copy. Copying the file with `cp` can catch a WAL database mid-write.
```sh
sqlite3 notes.db ".backup 'notes-backup.db'"
sqlite3 notes-backup.db "PRAGMA integrity_check;"
```
When a value is not a literal you typed, bind it from Python:
```python
import sqlite3
con = sqlite3.connect("notes.db")
con.execute("PRAGMA foreign_keys = ON")
row = con.execute("SELECT body FROM notes WHERE id = ?", (1,)).fetchone()
print(row[0])
```
Run an untrusted SQL script with the safe mode so it cannot shell out or load extensions:
```sh
sqlite3 --safe notes.db
```
## Gotchas
- `PRAGMA foreign_keys` defaults to `0`. Set it on every connection that should enforce foreign keys.
- A WAL database keeps `dbname-wal` and `dbname-shm` beside the main file. Use `.backup` so those pages are included.
- `INTEGER PRIMARY KEY` is the rowid. Inserting without an id assigns one.
- Build queries with `?` placeholders. Concatenating text into SQL is how a value becomes a statement.
- `integrity_check` prints `ok` when the copy is consistent.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== the-odds-api =====
---
name: "the_odds_api"
description: "Use The Odds Api when the user asks for The Odds Api or this provider's API."
---
# The Odds Api
## Purpose
Fetch sportsbook odds (default: Pinnacle) and remove the vig to get fair,
no-vig prices — useful for comparing a sportsbook's fair price against a
prediction-market price for the same game.
## Credit budget (500/month free Starter)
- `sports` and `events` are FREE - use them for discovery, never spend on these.
- `odds` costs (#markets) x (#regions). One market + one region = 1 credit.
- Keep pulls minimal: `h2h` only, `regions=us`, `bookmakers=pinnacle`.
- Cache odds responses locally (e.g. 15 min); replays within the window are free.
- Check the remaining quota in each response; stop if it runs low.
## Workflow
1. `curl "https://api.the-odds-api.com/v4/sports?apiKey=$KEY"` — list sport keys (free).
2. `curl "https://api.the-odds-api.com/v4/sports/baseball_mlb/odds?apiKey=$KEY®ions=us&markets=h2h&bookmakers=pinnacle"` — odds (1 credit).
3. De-vig: for two-outcome decimal odds `d1`, `d2`: implied `p1=1/d1`, `p2=1/d2`, overround `=p1+p2`; fair `p1=p1/overround`. Multiply by 100 for fair cents.
4. Compare the fair price against the prediction-market price for the same game.
## Tooling
No bundled CLI — call `https://api.the-odds-api.com/v4/...` directly with any
HTTP client, passing your API key as the `apiKey` query parameter (see examples
in Workflow).
## Auth
Get a free API key at the-odds-api.com (Starter plan: 500 credits/month) and
pass it as the `apiKey` query parameter. Read the key from the user's
environment or secrets store at runtime — never hardcode it, never ask the
user to paste a raw key in chat, and never write it to files, logs, or memory.
A 401 or 403 is a question about the request before it is a question about the
key: first check that the `apiKey` parameter was actually attached.
## Operating Rules
1. Use this skill when the user asks for The Odds Api or this provider's API.
2. Restrict authenticated requests to: api.the-odds-api.com.
3. Do not print, log, or persist raw credentials.
4. If auth is missing or rejected, follow the Auth section rather than asking for a key.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
# ===== webhooks =====
---
name: "webhooks"
description: "Accept webhook POSTs on localhost, answer quickly, and ignore duplicate retries. Use when another service needs to notify this machine."
---
# Webhooks
Listen on localhost for JSON POST requests, store each new event, and answer `204` before doing slow work. A second delivery of the same `id` is ignored.
## When to use
Some other program needs to notify this machine with an HTTP POST, and you can point it at `127.0.0.1`. The listener below is the standard-library handler for that. It writes events to `events.jsonl` in the current directory.
## Install
Python 3 is the only dependency. There is no package to install.
```sh
python3 -c "import http.server; print('ok')"
```
Save this as `webhook_receive.py`:
```python
#!/usr/bin/env python3
"""Receive webhook POSTs on localhost and append new events to events.jsonl."""
import json
from http.server import BaseHTTPRequestHandler, ThreadingHTTPServer
from pathlib import Path
HOST = "127.0.0.1"
PORT = 8787
OUT = Path("events.jsonl")
MAX_BODY = 1_000_000
def known_ids():
if not OUT.exists():
return set()
ids = set()
for line in OUT.read_text(encoding="utf-8").splitlines():
if not line.strip():
continue
try:
event = json.loads(line)
except json.JSONDecodeError:
continue
event_id = event.get("id")
if isinstance(event_id, str):
ids.add(event_id)
return ids
class Handler(BaseHTTPRequestHandler):
def do_POST(self):
if self.path.split("?", 1)[0] != "/hook":
self.send_error(404)
return
try:
n = int(self.headers.get("Content-Length", "0"))
except ValueError:
self.send_error(400)
return
if n <= 0 or n > MAX_BODY:
self.send_error(413 if n > MAX_BODY else 400)
return
raw = self.rfile.read(n)
try:
event = json.loads(raw.decode("utf-8"))
except (UnicodeDecodeError, json.JSONDecodeError):
self.send_error(400)
return
if not isinstance(event, dict):
self.send_error(400)
return
event_id = event.get("id")
if isinstance(event_id, str) and event_id in known_ids():
self.send_response(204)
self.end_headers()
return
with OUT.open("a", encoding="utf-8") as fh:
fh.write(json.dumps(event, separators=(",", ":")) + "\n")
self.send_response(204)
self.end_headers()
def log_message(self, fmt, *args):
return
if __name__ == "__main__":
ThreadingHTTPServer((HOST, PORT), Handler).serve_forever()
```
## Commands
Start the listener, then send an event. A repeat of the same `id` still returns `204` and does not add a second line.
```sh
python3 webhook_receive.py
```
```sh
curl -sS -D - -o /dev/null -X POST http://127.0.0.1:8787/hook \
-H 'Content-Type: application/json' \
-d '{"id":"evt_1","type":"ping"}'
```
Read what was stored:
```sh
cat events.jsonl
```
## Gotchas
- The server binds to `127.0.0.1` only. A sender on another machine cannot reach it until you change `HOST` on purpose.
- Answer with `204` as soon as the event is stored. A non-2xx status is a signal for the sender to retry.
- The same `id` is stored once. The second POST still returns `204`, which tells the sender to stop retrying.
- Bodies that are empty, not JSON, or not an object get `400`. Bodies over 1,000,000 bytes get `413`.
- The handler stores the JSON. It does not execute it.
---
Also on Honeypot — a free, open index of skills for AI agents: https://honeypot-e6c.pages.dev
[](https://honeypot-e6c.pages.dev)
In this repository20 other files it gives its agents.
- llms.txtllms.txt
- agent-checkoutSkill
- coinbaseSkill
- context7Skill
- cronSkill
- cursorSkill
- discordSkill
- honeypotSkill
- image-optimizeSkill
- kalshiSkill
- oids-python-sdkSkill
- oidsSkill
- pdf-textSkill
- playwright-mcpSkill
- polymarketSkill
- robinhood-mcpSkill
- skill_creatorSkill
- sqliteSkill
- the_odds_apiSkill
- webhooksSkill
Does it work?
Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.
No reviews yet
People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.
- It worked
- Partly
- It didn't
Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.
Your trail
Files you open will collect here, so you can find them again.
Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.
Now do this for your own.
Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.

