Review recent conversations to find improvements for CLAUDE.md files.
Scanned 5/27/2026
Install via CLI
openskills install qGolem/orc---
description: Review recent conversations to find improvements for CLAUDE.md files.
argument-hint: (no arguments)
allowed-tools:
- Bash(ls:*)
- Bash(jq:*)
- Bash(mkdir:*)
- Bash(wc:*)
- Bash(date:*)
- Read
- Glob
- Agent
- AskUserQuestion
model: inherit
context: inherit
hooks: {}
user-invocable: true
---
# Review CLAUDE.md from conversation history
Analyze recent conversations to improve both global (~/.claude/CLAUDE.md) and local (project) CLAUDE.md files.
<progress>
- [ ] Step 1: Find conversation history
- [ ] Step 2: Extract recent conversations
- [ ] Step 3: Spin up Sonnet subagents
- [ ] Step 4: Score and filter findings
- [ ] Step 5: Walk user through findings one by one
</progress>
<purpose>
Transcript auditor, not prose reviewer. You programmatically extract user messages, tool calls, and results from JSONL conversation logs, then spin up subagents to analyze behavior against CLAUDE.md rules.
</purpose>
<constraints>
**Your role:**
- Extract conversation data from JSONL files via jq
- Launch parallel subagents to analyze conversations against CLAUDE.md
- Score findings ruthlessly — CLAUDE.md is loaded into every context
- Present findings one at a time via AskUserQuestion for user review
**Not your role:**
- Editing CLAUDE.md directly (present findings, user decides)
- Reviewing the current session (skip most recent file)
</constraints>
<antipatterns>
**Avoid:**
- Processing the current session (always skip most recent JSONL)
- Swallowing jq errors to /dev/null
- Treating user messages as always string type (they can be arrays)
- Dropping tool_use blocks from assistant messages
- Presenting a wall of findings — use AskUserQuestion to walk through one at a time
</antipatterns>
## Process
### Step 1: Find Conversation History
The project's conversation history is in `~/.claude/projects/`. The folder name is the project path with slashes replaced by dashes.
```bash
# Find the project folder (replace / with -)
PROJECT_PATH=$(pwd | sed 's|/|-|g' | sed 's|^-||')
CONVO_DIR=~/.claude/projects/-${PROJECT_PATH}
ls -lt "$CONVO_DIR"/*.jsonl | head -20
```
### Step 2: Extract Recent Conversations
Extract the 15-20 most recent conversations (excluding the current session) to a temp directory.
**IMPORTANT:** The jq filter contains `!=` which zsh will escape/mangle when passed inline. Write the filter to a file first, then reference it with `jq -r -f`.
**Step 2a:** Write the jq filter to `$SCRATCH/extract.jq`:
```jq
if .type == "user" then
.message.content |
if type == "string" then
"USER: " + .
elif type == "array" then
[ .[] |
if .type == "text" then .text
elif .type == "tool_result" then
(.content |
if type == "string" then .[0:100]
elif type == "array" then
[.[] | select(.type == "text") | .text[0:100]] | join(" ")
else "" end
) | if . != "" then "RESULT: " + . else empty end
else empty end
] | map(select(. != "")) | join("\n") |
if . != "" then "USER:\n" + . else empty end
else empty end
elif .type == "assistant" then
[ .message.content // [] | .[] |
if .type == "text" then .text
elif .type == "tool_use" then
"TOOL: " + .name + "(" + (.input | tostring | .[0:100]) + ")"
else empty end
] | map(select(. != "")) | join("\n") |
if . != "" then "ASSISTANT:\n" + . else empty end
else empty end
```
**Step 2b:** Run the extraction loop using the filter file:
```bash
SCRATCH=/tmp/claudemd-review-$(date +%s)
mkdir -p "$SCRATCH"
# Write the jq filter file first (Step 2a above)
# tail -n +2 skips the most recent file (current session)
for f in $(ls -t "$CONVO_DIR"/*.jsonl 2>/dev/null | tail -n +2 | head -20); do
convo_id=$(basename "$f" .jsonl)
jq -r -f "$SCRATCH/extract.jq" "$f" > "$SCRATCH/${convo_id}.txt" 2>>"$SCRATCH/debug.log"
done
ls -lhS "$SCRATCH"
```
### Step 3: Spin Up Sonnet Subagents
Launch parallel Sonnet subagents to analyze conversations. Each agent should read:
- Global CLAUDE.md: `~/.claude/CLAUDE.md`
- Local CLAUDE.md: `./CLAUDE.md` (if exists)
- Batch of conversation files
Give each agent this prompt template:
```
Read:
1. Global CLAUDE.md: ~/.claude/CLAUDE.md
2. Local CLAUDE.md: [project]/CLAUDE.md
3. Conversations: [list of files]
Analyze the conversations against BOTH CLAUDE.md files. For each finding, output:
**Finding:** [one-line description]
**Type:** violated | add-local | add-global | outdated
**Evidence:** [specific conversation ID + what happened]
**Proposed change:** [exact wording to add, edit, or remove]
**Universality score (1-5):**
5 = Will prevent bugs/waste in virtually every future session
4 = Applies to most sessions in this project type
3 = Applies sometimes, depends on task
2 = Niche — only relevant for specific workflows
1 = One-off incident, not a pattern
**Frequency:** [how many conversations exhibited this]
Be specific. Output structured findings only.
```
Batch conversations by size (smaller batches = more agents = better parallelism):
- Large (>100KB): 1 per agent
- Medium (10-100KB): 2 per agent
- Small (<10KB): 3-4 per agent
This typically yields 6-8 agents, which is fine for parallel execution.
### Step 4: Collect and Filter Findings
All agents were launched with `run_in_background=true`. **Do not block on TaskOutput** — wait for the automatic completion notifications to arrive for each agent. Only proceed to aggregation after all agents have reported back via notifications.
Aggregate all subagent findings. Apply these filters before presenting to user:
**CLAUDE.md is loaded into every context for all conversations. Every line has a token cost.**
Discard findings that score below threshold:
- **Universality < 3**: Too niche. CLAUDE.md isn't the place for edge-case workarounds.
- **Frequency = 1 conversation AND universality < 4**: One-off incidents don't justify permanent context cost.
- **Already covered by existing rule**: If a rule exists and was just violated, the fix is rewording — not adding a new rule. Merge into the existing rule's proposed edit.
- **Derivable from code/git**: If the information can be found by reading the codebase or running `git log`, it doesn't belong in CLAUDE.md.
- **Session-specific debugging**: Hook stdout contracts, specific error messages, tool quirks — these are docs, not rules.
Score remaining findings and sort by: universality desc, frequency desc.
For each surviving finding, prepare a preview showing:
1. The exact diff (what changes in which file)
2. The universality score and reasoning
3. The evidence summary
### Step 5: Walk User Through Findings
Present findings **one at a time** using AskUserQuestion. Do not dump a summary table.
For each finding:
```
AskUserQuestion:
header: "Finding [N/total] — [type]"
question: |
**[one-line description]**
Score: [universality]/5 — [frequency] conversations
Evidence: [brief evidence summary]
Proposed change to [global|local] CLAUDE.md:
```diff
[exact diff preview]
```
options:
- label: "Accept"
description: "Apply this change"
- label: "Edit"
description: "I want to modify this before applying"
- label: "Skip"
description: "Don't apply this one"
- label: "Stop"
description: "Done reviewing, skip remaining"
```
- **Accept**: Apply the edit immediately, then present next finding
- **Edit**: Ask user for their preferred wording, apply that instead, then next
- **Skip**: Move to next finding without changes
- **Stop**: End the review
After all findings reviewed (or user stops), show a summary of what was applied vs skipped.
## File Ownership
| File | Access | Purpose |
|------|--------|---------|
| `~/.claude/projects/-$PROJECT/*.jsonl` | Read only | Source conversation logs |
| `~/.claude/CLAUDE.md` | Read only (edit only after Accept) | Global rules to audit against |
| `./CLAUDE.md` | Read only (edit only after Accept) | Project rules to audit against |
| `$SCRATCH/*.txt` | Write | Extracted conversation text |
| `$SCRATCH/debug.log` | Write | jq error log |
## Skip Conditions
Skip if:
- No JSONL files found in project directory
- Fewer than 2 files (only current session exists)
## Completion Criteria
- [ ] 15-20 conversations extracted (or all available, whichever is fewer)
- [ ] Current session excluded from analysis
- [ ] jq errors logged to debug.log (not swallowed)
- [ ] Subagent findings scored and filtered (universality >= 3, frequency > 1 or universality >= 4)
- [ ] Each surviving finding presented individually via AskUserQuestion
- [ ] User accepted/skipped each finding explicitly
- [ ] Summary of applied vs skipped changes shown at end
No comments yet. Be the first to comment!