Agent skill
discord-clawd
Query Peter's local Discord archive in ~/.discrawl/discrawl.db when asked about Discord history, channel activity, top posters, message counts, summaries, or anything in synced Discord data. Use this skill for local search, SQL stats, channel/member lookups, and freshness checks before answering recent or latest Discord questions.
Install this agent skill to your Project
npx add-skill https://github.com/steipete/agent-scripts/tree/main/skills/discord-clawd
SKILL.md
Discord Clawd
Use this for Discord questions first. Local archive first; live Discord only when freshness matters and the archive is stale.
Trigger
Use when the user asks things like:
- "what happened in #maintainers"
- "who posted the most in discord"
- "search discord for ..."
- "how many messages/users/channels"
- "summarize this week in #channel"
- "is Discord fully synced"
Data Sources
Prefer in this order:
~/.discrawl/discrawl.db/tmp/discrawl --config ~/.discrawl/config.toml ...- Live refresh from
~/Projects/discrawlonly if needed
Do not browse the web for Discord archive questions unless the user explicitly wants external context too.
Freshness Check
For latest, recent, today, this week, or sync questions, check freshness first.
Useful queries:
sqlite3 ~/.discrawl/discrawl.db \
"select coalesce(max(updated_at),'') from sync_state where scope like 'channel:%';"
sqlite3 ~/.discrawl/discrawl.db "
select count(*)
from channels c
where coalesce(c.kind,'') in (
'text','news','announcement',
'thread_public','thread_private','thread_news','thread_announcement'
)
and not exists (
select 1 from sync_state s
where s.scope = 'channel:' || c.id || ':history_complete'
)
and not exists (
select 1 from sync_state s
where s.scope = 'channel:' || c.id || ':unavailable'
);"
Interpretation:
0remaining = fully synced for real message-bearing channels- forum parents are metadata containers; their post history lives in thread channels
Query Workflow
- Resolve scope: channel, date range, author, keyword.
- Check freshness if the user asked for recent/current data.
- Use SQL for counts/rankings/exact filters.
- Use
search/FTS for discovery, then SQL for precise slices. - Prefer the
messagesCLI for exact channel+date slices before dropping to raw SQL. - Report with absolute dates, counts, and channel names.
Common Queries
Resolve channel name:
sqlite3 ~/.discrawl/discrawl.db \
"select id, name, kind from channels where name like '%maintainers%' order by name;"
Top channels:
sqlite3 ~/.discrawl/discrawl.db "
select c.name, c.kind, count(m.id) as messages
from channels c
join messages m on m.channel_id = c.id
group by c.id
order by messages desc
limit 20;"
Top authors with names:
sqlite3 ~/.discrawl/discrawl.db "
select
coalesce(mem.display_name, mem.username, m.author_id) as author,
m.author_id,
count(*) as messages
from messages m
left join members mem
on mem.user_id = m.author_id
and mem.guild_id = m.guild_id
where coalesce(m.author_id,'') != ''
group by m.author_id, coalesce(mem.display_name, mem.username, m.author_id)
order by messages desc
limit 20;"
Messages in one channel for the last X days:
/tmp/discrawl --config ~/.discrawl/config.toml \
messages --channel maintainers --days 7 --all
Messages in one channel since a date:
/tmp/discrawl --config ~/.discrawl/config.toml \
messages --channel '#maintainers' --since 2026-03-01T00:00:00Z --all
Keyword search:
/tmp/discrawl --config ~/.discrawl/config.toml search "query terms"
Read-only SQL via CLI:
/tmp/discrawl --json --config ~/.discrawl/config.toml sql \
"select count(*) from messages;"
Summaries
For channel summaries:
- pull the exact slice first
- include counts: messages, authors, date span
- identify recurring topics, decisions, blockers
- do not claim certainty beyond the retrieved slice
For release-window summaries, anchor on exact timestamps, not vague relative dates.
Name Resolution
Prefer:
members.display_namemembers.usernamemessages.raw_json -> $.author.username- raw author id
If a user asks "who is this id", resolve locally before answering.
Live Refresh
Only do this if the user wants fresher data than the archive has.
Repo:
cd ~/Projects/discrawl
Token source:
ssh peters-mac-studio-1 \
"zsh -lc 'source ~/.profile >/dev/null 2>&1; printf %s \"\$DISCORD_BOT_ID_FLAWD\"'"
Targeted refresh is better than full sync for ad hoc questions:
DISCORD_BOT_TOKEN="..." /tmp/discrawl \
--config ~/.discrawl/config.toml \
sync --full --channels <channel-id> --concurrency 1
Guardrails
- never expose bot tokens
- prefer local DB over network
- use absolute dates in answers
- if freshness is uncertain, say so
- if the archive is stale, either sync first or label the answer as archive-based
Recommended Agent Skills
Expand your agent's capabilities with these related and highly-rated skills.
brave-search
Web search and content extraction via Brave Search API. Use for searching documentation, facts, or any web content. Lightweight, no browser required.
xurl
Use the official xurl CLI for the X API. Covers install, safe auth setup, app selection, common shortcuts, and raw endpoint access.
nano-banana-pro
Generate/edit images with Nano Banana Pro (Gemini 3 Pro Image). Use for image create/modify requests incl. edits. Supports text-to-image + image-to-image; 1K/2K/4K; use --input-image.
domain-dns-ops
Domain/DNS ops across Cloudflare, DNSimple, Namecheap for Peter. Use for onboarding zones to Cloudflare, flipping nameservers, setting redirects (Page Rules/Rulesets/Workers), updating redirect-worker mappings, and verifying DNS/HTTP. Source of truth: ~/Projects/manager.
swiftui-liquid-glass
Implement, review, or improve SwiftUI features using the iOS 26+ Liquid Glass API. Use when asked to adopt Liquid Glass in new SwiftUI UI, refactor an existing feature to Liquid Glass, or review Liquid Glass usage for correctness, performance, and design alignment.
swiftui-view-refactor
Refactor and review SwiftUI view files for consistent structure, dependency injection, and Observation usage. Use when asked to clean up a SwiftUI view’s layout/ordering, handle view models safely (non-optional when possible), or standardize how dependencies and @Observable state are initialized and passed.
Didn't find tool you were looking for?