done
Skill5 starsChanged 43 days agoMITView on GitHub
End-of-session wrap-up — saves a session note to the hub, updates CONTEXT.md, and commits hub changes. Use this skill whenever the user types `/done`, `/wrap`, says "wrap up the session" / "save the session", or signals the conversation is ending and they want it documented. Also use when the user is closing a coding/research session and wants the work captured before they walk away — even if they don't say "/done" explicitly. Do NOT auto-trigger; wait for an explicit closing signal from the user.
- Commits and pushes
37 other projects use a version of this.
Adopted by
Most recently taken up by
- spongetimblin/claude-skill-librarytheir own version, first seen Nov 8, 2026
- vtmocanu/skillstheir own version, first seen Nov 7, 2026
- Melvynx/ai-maxxing-skillstheir own version, first seen Nov 1, 2026
- duthaho/skillhubtheir own version, first seen Oct 31, 2026
- bholmesdev/skillstheir own version, first seen Oct 18, 2026
- cyrilichti/agent-workflowstheir own version, first seen Oct 17, 2026
Used with
Projects with it also use simplify, work and 2 more.
Other files people use alongside this one.
Files found in the same public projects as a version of this one, more often than they turn up anywhere else. Each project counts once, large collections count for less, and this file's own repository is left out.
Hugging FaceSkillsimplify
Refactor code after tests pass. The "Refactor" phase of Red-Green-Refactor.
Also in 5 projects that use this
vbrevikSkillwork
Use when the user says 'plan', 'todo', 'copy plan', 'append plan', 'resume plan', 'priorities', or 'what's next'.
Also in 3 projects that use this
OpenAISkilltranscribe
Transcribe audio files to text with optional diarization and known-speaker hints. Use when a user asks to transcribe speech from audio/video, extract text from recordings, or label speakers in interviews or meetings.
Also in 3 projects that use this
MicrosoftSkillhandoff
Compact the current conversation into a handoff document for another agent to pick up.
Also in 9 projects that use this
Other versions37 projects use a version of this.
Word for word · 0
None found.
Edited · 0
None found.
Wrote their own version · 37
- bholmesdev/hubble.md★ 1.5ksame name
- bholmesdev/skills★ 179same name
- Melvynx/ai-maxxing-skills★ 32same name
- endlessblink/master-plan★ 26same name
- fredoliveira/agents★ 24same name
- oldwinter/skills★ 11same name
- duthaho/skillhub★ 9same name
- Trejon-888/ix-claude-code-starter-kit★ 9same name
- HaipingShi/coderail★ 8same name
- ohm41321/luciazero★ 6same name
27 more not listed
How matches are found. Word for word: the exact same text. Edited: shares passages with this file (“99% same” means 99% of its five-word phrases also appear here; 10% or more counts). Their own version: similar meaning, or, weakest, the same name. We can’t tell which project had it first. Projects are counted among the 200 most-starred candidates, and mentions are links to the repository we found, up to 50 per site, so both counts are a floor.
In this repository12 other files it gives its agents.
- AGENTS.mdAGENTS.md
- councilSkill
- defuddleSkill
- eli5Skill
- grill-meSkill
- learnSkill
- media-genSkill
- memory-consolidationSkill
- qmdSkill
- research-notebookSkill
- setup-for-meSkill
- wiki-articleSkill
The file
Show its rules and text
We split this skill into the rules it gives an agent
23 rules. 0 are common, 6 are distinctive, and 17 are very specific to this project.
0
Common
Most of the 33 edited versions we read keep these.
6
Distinctive
This author's own choices. Worth a look.
17
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Distinctive: line 14
No narration between tool calls: Don't write "Running command...", "Edit succeeded, continuing...", "Now committing..." — those are wasted …
- Very specific: line 16
Skip steps when they don't apply: If the resolver printed no dirty: lines → no commit step.
- Distinctive: line 49
When unsure, lean light. A thin honest note beats an inflated one.
- Very specific: line 55
Idempotency: check the today_session: lines from the resolver.
- Very specific: line 89
If today_daily_note exists, you may add a one-line Daily note: link near the top.
- Very specific: line 91
Use the commit:<hash> <msg> lines from the resolver to populate "Work done" — those are real commits since the last session note.
- Distinctive: line 109
State sections: update separately and only when something genuinely changed.
- Very specific: line 118
Never append a second dated line for a project to CONTEXT.md.
- Very specific: line 123
Only if a *real* lesson surfaced — user corrected you, non-obvious tooling discovery, failure mode worth remembering.
- Very specific: line 129
If patterns.md doesn't exist yet, don't create it from /done — that's a job for a memory-consolidation pass, not this skill.
- Very specific: line 131
If no match, append under ## YYYY-MM-DD heading:
- Distinctive: line 137
If nothing genuinely new, skip step 5 entirely.
- Very specific: line 141
The contract: after /done, the hub's wiki reflects this session's work.
- Distinctive: line 145
Step 5.5a — detect: Run the freshness detector (pass nothing.
- Very specific: line 174
Look at what changed. The session note you just wrote (step 3) + the WIKI_FILES hint + the work you actually did this session tell you …
- Very specific: line 179
If an existing article already covers this component → Read it and update in place (refresh How it works, Code references, bump …
- Very specific: line 180
If nothing covers it → create using the wiki-article skill's template.
- Very specific: line 181
Update the index: Add or refresh the [[topic/article|Title]] line in <hub>/wiki/<project>/index.md so the new/changed article is …
- Very specific: line 200
Add --dry-run first if you want to see the file list without committing.
- Distinctive: line 220
Initializes the hub as a git repo on first use: if it wasn't one already, instead of silently doing nothing — a hub with no version history …
- Very specific: line 221
Checks git identity before committing: If user.name/user.email were never set (local or global), it reports error:hub git identity not set …
- Very specific: line 247
If something failed, say so explicitly: Missed <X> because <reason>.
- Very specific: line 259
Write conversation-log.md (typically owned by a memory-consolidation pass, if the user has one configured).
“Common” is measured: kept by at least 6 in 10 of the 33 edited versions of this file we could read. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
/done — Session Wrap-Up
Save a durable record of this session into the hub (see the plugin's hub concept — resolved from JARVIS_HUB env, then ~/.jarvis-hub-path, then ~/jarvis-hub). Scale effort to session weight: light/conversational → minimal note; substantial work (commits, decisions, multi-step) → structured note. Don't fabricate. Don't pad.
Token discipline (read this first)
This skill runs at the end of every session, so cost compounds. Four rules to keep it cheap:
- No narration between tool calls. Don't write "Running command...", "Edit succeeded, continuing...", "Now committing..." — those are wasted tokens. Run tools silently. Only the final confirmation is shown to the user.
- One bash call for context. The resolver script bundles every piece of prep info you need. Don't make additional
git log,ls, orcatcalls unless the resolver output is genuinely missing something. - Skip steps when they don't apply. If the resolver printed no
dirty:lines → no commit step. If session was light → no patterns scan. Iftoday_daily_note=(none)→ no link to it. - Never full-Read
CONTEXT.mdorpatterns.md. Both can grow large over a long-lived hub. Step 4 updatesCONTEXT.mdvia a script (no read); step 5 dedups patterns viagrep(no read). If you ever must touch them directly, useoffset/limit— never load the whole file.
Workflow
1. Resolve context
bash "${CLAUDE_PLUGIN_ROOT}/skills/done/scripts/resolve-context.sh"The output is a flat key=value block. Key fields you'll use:
hub,sessions_dir,project— where the session note goes and what the work belongs tohub_is_git—nomeans the hub isn't a git repo at all; skip the commit step entirely (see edge cases)hub_dirty— any uncommitted changes anywhere in the hubsessions_dirty,wiki_dirty,memory_dirty,other_hub_dirty— per-area dirt flagsdirty:hub:<path> <count>lines — every dirty top-level path in the hub. This is the authoritative list for what to stage; don't guess from the flags alone.hub_branch/_remote/_upstream/_ahead— push state. See step 6.wiki_recent_count— wiki files modified in the last 24h (informational only)current_branch— branch of the repo you were working in (not the hub) — note it in the session note if relevanttoday_daily_note— path to today's daily note, or(none)(most hubs won't have this — that's fine, skip the line)last_session_note,last_session_date— for continuity contexttoday_session:<path>lines — existing session notes for today (idempotency)commit:<hash> <msg>lines — commits in the hub since last session date
2. Decide session weight
- Light — purely conversational, no code changes, < 5 substantive turns, no decisions worth keeping. → 3-line note. Skip patterns.
- Substantial — code/files changed, real decisions, multi-step work. → Structured note + patterns scan.
Weight decides how much you write, never whether you commit. Step 6 is driven by the resolver's dirty: lines alone — a light session that still left patterns.md or CONTEXT.md dirty gets committed, because the alternative is drift that compounds silently.
When unsure, lean light. A thin honest note beats an inflated one.
3. Write the session note
Path: <sessions_dir>/YYYY-MM-DD-<slug>.md. Slug = 2-5 word kebab-case describing topic.
Idempotency: check the today_session: lines from the resolver. If one matches your slug → read that file, append ## Part 2 — HH:MM with new content. Different slug, same date → new file (fine). Never overwrite.
Substantial-session structure:
---
type: session
date: YYYY-MM-DD
project: <project>
status: <completed | in-progress | blocked>
tags: [session, ...]
---
# Session: YYYY-MM-DD — <Title>
**Goal:** <one sentence>
**One-line takeaway:** <single most important thing for future-you>
**Branch:** <current_branch> (only include if not main/master)
## Work done
- <commit-hash> <message> — <context if non-obvious>
## Decisions
- **<decision>** — <reasoning>
## Open threads
- <thread> — <what's blocked or pending>
## Next steps
- <concrete action>For light sessions, drop the structured sections — frontmatter + Goal + 2-3 bullets is enough.
If today_daily_note exists, you may add a one-line **Daily note:** [link](daily-notes/YYYY-MM-DD.md) near the top. Skip if (none).
Use the commit:<hash> <msg> lines from the resolver to populate "Work done" — those are real commits since the last session note.
4. Update CONTEXT.md
Do NOT Read CONTEXT.md — reading the whole file every run is the cost this step exists to avoid on a long-lived hub. Pipe a one-line entry to the updater instead; it prepends it, keeps the newest 12, and auto-archives the overflow — the model never loads the file:
python3 "${CLAUDE_PLUGIN_ROOT}/skills/done/scripts/update-context.py" <<'ENTRY'
- Date: YYYY-MM-DD (topic) — one-line summary of what happened. Open: <blocker if any>. Note: `sessions/YYYY-MM-DD-<slug>.md`
ENTRYYou already have the content — you just wrote the session note. One line, newest-first. The script owns the ## Recent Sessions region between the SESSIONS:START/END markers and creates CONTEXT.md from a minimal scaffold if it doesn't exist yet — the ## Active Projects / ## Open Threads / ## Recent Decisions sections above that region are untouched by this script unless you call it in project mode (below).
Re-running /done in the same day is safe: the script matches on the sessions/…md path in your entry and replaces the existing line instead of stacking a duplicate (it reports replaced=1). So keep the note path in the entry — it's what makes the update idempotent.
Exit code 2 means you piped an empty entry, which means step 4 didn't actually happen — fix the entry and rerun.
State sections update separately and only when something genuinely changed.
Active Projects is an index: ONE status line per project, never more. The history of a project lives in
<hub>/projects/<name>.md. When a project moved this session, use the same script in project mode (it replaces the single status line, adds the dated detail to the project file, creates the file if absent, and is safe to re-run):python3 "${CLAUDE_PLUGIN_ROOT}/skills/done/scripts/update-context.py" \ --project "<name>" --status "<one line, 360 chars max>" --history "<dated detail>"Never append a second dated line for a project to
CONTEXT.md. A hub that still has many lines per project can be migrated once withskills/memory-consolidation/scripts/split-context.py.- Open Threads: edit in place with a targeted
offset/limitRead around that section, never a full-file Read. A thread that is resolved or stale is moved verbatim to<hub>/archive/open-threads-archived-YYYY-MM-DD.md, not deleted.
5. Patterns (substantial sessions only)
Only if a real lesson surfaced — user corrected you, non-obvious tooling discovery, failure mode worth remembering. Before appending, dedup: grep patterns.md for similar phrasing — if the same lesson is already there, skip.
grep -i "<key-phrase>" "<hub>/patterns.md" 2>/dev/nullIf patterns.md doesn't exist yet, don't create it from /done — that's a job for a memory-consolidation pass, not this skill. Skip step 5 silently in that case.
If no match, append under ## YYYY-MM-DD heading:
- **Pattern**: <one-line>. **Why it matters**: <one-line>. **Trigger**: <when this applies>.If nothing genuinely new, skip step 5 entirely. Manufactured patterns silently bias future decisions — worse than missing ones.
5.5. Wiki auto-update
The contract: after /done, the hub's wiki reflects this session's work. /done doesn't hand the work back to the user; it detects what the wiki owes and writes it automatically, then reports what changed.
Runs after the session note is written, BEFORE the commit in step 6.
Step 5.5a — detect. Run the freshness detector (pass nothing; it auto-finds this session's transcript):
bash "${CLAUDE_PLUGIN_ROOT}/skills/done/scripts/wiki-check.sh"Parse the WIKI_* block from stdout:
WIKI_VERDICT—update_owed|up_to_date|skippedWIKI_REASON— one-line explanation of the verdict (quote it if you report "skipped")WIKI_PROJECT— the project (hub subdirectory) the work touchedWIKI_FILES— comma-separated basenames of the non-wiki files edited this session (targeting hint)WIKI_EDITS/WIKI_DISCOVERY— counts (real file edits / discovery actions)WIKI_TARGET— suggested article path skeleton
The detector locates this session's transcript itself: $PWD with /, _ and spaces flattened to - under ~/.claude/projects/, newest .jsonl. It fails open — any problem finding or parsing the transcript yields skipped, never a blocked /done.
One blind spot to cover yourself: it only classifies paths inside the hub. A session that spent its time editing this plugin's own skills/hooks/settings returns up_to_date because nothing hub-shaped was touched — if that's the kind of work this session actually did and it's worth remembering, write an article regardless of the verdict.
Trigger model: any changed files. If the session edited/created real files in a hub-tracked project (or did ≥3 discovery actions on one) and did NOT already write a wiki article, WIKI_VERDICT=update_owed.
up_to_date→ nothing owed. Skip to step 6.skipped→ escape flag was set or transcript missing. Note "wiki-check skipped" in the confirmation and skip to step 6.update_owed→ continue to 5.5b. Do not skip. Do not ask the user first — if the user prefers to review before writing, that's a one-time setting, not a per-session question.
Step 5.5b — write the wiki (automatic).
Articles live at <hub>/wiki/<project>/<topic>/<article>.md, indexed by <hub>/wiki/<project>/index.md. See the wiki-article skill for the template and the anti-fabrication guard.
- Look at what changed. The session note you just wrote (step 3) + the
WIKI_FILEShint + the work you actually did this session tell you which component/concept needs a wiki article. - Decide update vs create. List the project's existing articles:
ls "<hub>/wiki/<project>"/**/*.md 2>/dev/null- If an existing article already covers this component → Read it and update in place (refresh
How it works,Code references, bumplast-updated, add new failure modes). Don't create a duplicate. - If nothing covers it → create using the
wiki-articleskill's template.
- If an existing article already covers this component → Read it and update in place (refresh
- Update the index. Add or refresh the
[[topic/article|Title]]line in<hub>/wiki/<project>/index.mdso the new/changed article is discoverable. - Multiple distinct components touched → write/update one article each (don't cram unrelated work into one).
Anti-fabrication guard (hard rule). The wiki must never contain invented content. If the work was too shallow to write ≥200 honest words (1–2 file reads, a one-line tweak, no real structural understanding gained), do NOT manufacture an article. Instead append a 5-line "what's missing for a wiki article" stub to <hub>/wiki/<project>/index.md naming the component and where the next session should start. A thin honest stub beats a padded fake article. Note this choice in the confirmation.
Manual opt-out still exists: passing /done --skip-wiki-check sets DONE_SKIP_WIKI_CHECK=1 in front of the detector call (or touch /tmp/done-skip-wiki) so it returns skipped.
The articles you just wrote are uncommitted; step 6 re-reads git state at commit time and picks them up (the resolver's wiki_dirty from step 1 predates them — don't read it as "nothing to commit"). Record which articles you wrote/updated; you'll list them in the confirmation and in the session note's "Work done".
6. Commit the hub (only what's dirty)
The point of this step is that nothing you just wrote stays unversioned. Always run it when there's anything to commit — hub_is_git=no from step 1 is no longer a reason to skip: commit-hub.sh initializes the hub as a git repo on its own the first time it has something real to stage (see the edge cases entry). It only reports nothing:hub when there is genuinely no dirt.
One call does the whole step — staging, the push decision:
bash "${CLAUDE_PLUGIN_ROOT}/skills/done/scripts/commit-hub.sh" --slug <the-slug-you-used>Add --dry-run first if you want to see the file list without committing.
It re-reads git state at commit time rather than trusting the step-1 snapshot — which matters because everything you wrote in steps 3–5.5 came into existence after the resolver ran. Staging by hand from the stale dirty: lines is exactly how freshly-written wiki articles used to get left behind.
Parse its output for the confirmation:
| Line | Meaning |
initialized:hub <path> | this was the hub's first commit ever — it just became a git repo |
cleaned:hub <files> | one-time placeholder removal fired this run (see below) — name the files in the confirmation |
committed:hub <hash> <n> files | landed |
nothing:hub | clean, nothing owed |
pushed:hub <branch> -> <remote> | synced |
nopush:hub <reason> | deliberately not pushed — report the reason verbatim |
error:hub <msg> | say so plainly in the confirmation; don't retry, don't force |
What it guarantees, so you don't have to re-verify:
- Allowlist only —
sessions wiki patterns.md conversation-log.md CONTEXT.md daily-notes ideas research learning. Any file that looks hand-curated (MEMORY.md, anyuser_*/project_*/feedback_*/reference_*memory file) can never be staged by this script — those are the user's own edit-in-progress, same reasoning as never touchingCLAUDE.mdin a code repo. - One narrow, deliberate exception to the line above: the very first time a run has real content to commit, it also retires
memory-template's seededexample-*.mdplaceholders (example-feedback-rule.md,example-project-note.md,example-user-fact.md) and their index lines inMEMORY.md— but only files that still contain the literal placeholder marker text, so a file you kept and genuinely repurposed under that name is never touched. Rationale: those three files exist only to show the memory format; shipping forever, they'd get injected into every session's context alongside your real memory. "The hub's first real commit" is the natural signal that you're actually using it now. In practice this fires once, ever, per hub. - Initializes the hub as a git repo on first use if it wasn't one already, instead of silently doing nothing — a hub with no version history was the old failure mode (see edge cases).
- Checks git identity before committing. If
user.name/user.emailwere never set (local or global), it reportserror:hub git identity not set — run: git config --global user.name "Your Name" && git config --global user.email "you@example.com" ...— surface that verbatim; there is nothing to retry until the user runs it. - Refuses to commit mid-rebase/merge — reports
error:instead of burying an unfinished operation. - Never auto-pushes — the hub holds personal memory by definition, so pushing requires an explicit
JARVIS_HUB_PUSH=1opt-in even when a remote and upstream exist. See the script's own comment for the reasoning.
conversation-log.md, if present, is typically owned by a scheduled memory-consolidation pass, not /done. Two writers on a rolling-window file produce duplicate entries and a corrupt boundary. /done commits whatever consolidation left there; it doesn't author it.
git push from a code repo is a separate, higher-stakes operation than this — this exception covers the hub only, and only with the explicit opt-in above.
7. Confirm
Short. Skip lines that don't apply.
Saved.
Session: sessions/YYYY-MM-DD-<slug>.md
Wiki: <article(s) written/updated> / up to date / stub added / skipped
Patterns: +N / nothing added
Context: updated
Hub: <N files> committed / clean
Commit: <hash> / no changes
Push: <branch> -> <remote> / no remote / skipped — <reason>The Wiki line is required. State exactly what happened: which articles you wrote or updated (by path), or "up to date" if nothing was owed, or "stub added" if the anti-fabrication guard fired, or "skipped" if the detector was skipped.
If something failed, say so explicitly: Missed <X> because <reason>.
Edge cases (load only when hit)
For unusual cases — detached HEAD, no git repo, write errors, hub-not-found, conflicting today files — read references/edge-cases.md. Don't preload it.
What this does NOT do
- Push a hub with no upstream, or push without the explicit
JARVIS_HUB_PUSH=1opt-in (see step 6). - Modify or stage
MEMORY.mdor any hand-curated memory file. - Write
conversation-log.md(typically owned by a memory-consolidation pass, if the user has one configured). - Send anything to a chat bridge, Telegram, or any other notification channel — this skill reports into the session only.
- Close tasks in daily notes (separate concern).
- Auto-trigger — only on explicit closing signal.
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.

