Your personal AI assistant, as a Claude Code plugin. One markdown folder, one plugin, a brain that learns who you are session after session.
Kevin is a portable, file-based personal AI assistant that runs inside Claude Code. Everything that makes Kevin Kevin, personality, memory, knowledge, projects, tasks, lives in your own directory as plain markdown. Any AI can read it. You can browse it in Obsidian or Finder. If you ever want to leave Claude Code, you take the folder and go.
This isn't a chat wrapper. It's an operating system for personal AI:
- A 28-tool MCP server for tasks, knowledge compilation, reports, search, page-speed, Playwright, and Google Search Console.
- A 20-skill library covering onboarding, project lifecycle, daily/weekly/monthly cadences, trip planning, and read-only SEO auditing.
- A knowledge pipeline that turns every conversation into structured, queryable memory.
- A skill-pack system for opt-in capabilities (SEO, Browser) and an install-on-demand bridge to community skill libraries via skills.sh.
- Bundled behaviour is
disable-model-invocation: trueβ Kevin only acts when you ask, never spontaneously. The exceptions are two read-only orientation skills,dashboard(refresh the mission-control page) andwhere-am-i(session radar), which Kevin can run on its own when you ask to see the big picture or where you left off; neither mutates knowledge or task state.
Kevin is named after the loyal minion. Helpful, enthusiastic, a little nerdy.
π¦ Prerequisites β what to install first
Kevin runs on a small, bun-first toolchain (no Node.js). Install these once:
| Tool | Why you need it | Get it |
|---|---|---|
| Claude Code | The host Kevin plugs into | docs.claude.com |
| Bun β₯ 1.1 | Runtime for the MCP server, hooks, and the kevin CLI |
bun.sh |
| Git | Cloning, the plugin marketplace, and Kevin's git-activity awareness | git-scm.com |
| Python 3 (optional, recommended) | Kevin is TypeScript-first, but some tooling and integrations still reach for Python | python.org |
| Obsidian (optional) | Browse the knowledge graph; opens dashboard links rendered, not raw | obsidian.md |
bun and git are hard requirements β /agent-kevin:init checks for them up front and stops with an install pointer if either is missing. Chromium (for the Playwright tools) is not a manual step β bun install downloads it into the plugin via a postinstall hook.
On Windows? Kevin runs on native Windows through Git Bash β the shell Claude Code already uses for its Bash tool, which supplies the POSIX environment Kevin's hooks, MCP server, and per-skill bash permission patterns expect. Install the bun + git toolchain (above) for Windows, then run Claude Code + /agent-kevin:init as usual. WSL2 is also fully supported if you prefer a full Linux userland: install WSL2 (wsl --install in an admin PowerShell, then reboot), put the toolchain inside the distro, and launch Claude Code from there. Either works β native is lighter; WSL2 is closer to a Linux production target. Native Windows has a few rough edges to know about (MSYS path-mangling on colon-paths, no OS sandbox, and a couple of pack-gated skills that assume tools Git Bash lacks like jq); see Platform support.
First, cd to wherever you want Kevin's brain to live and launch Claude Code:
mkdir -p ~/Documents/Agents/Kevin && cd ~/Documents/Agents/Kevin
claudeInside the session, register the marketplace and install the plugin:
/plugin marketplace add github:AgentLayer1/agentlayer-claude-marketplace
/plugin install agent-kevin@agentlayer
/exit
Then enter claude again and run /agent-kevin:init to scaffold your home (see Onboarding below).
The plugin ships its own embedded marketplace (.claude-plugin/marketplace.json), so a local clone of agent-kevin is itself a marketplace you can register.
# Clone the plugin
git clone https://github.com/AgentLayer1/agent-kevin ~/Developer/agent-kevin
# One-time MCP-server deps install (~150MB, pulls chromium for Playwright)
cd ~/Developer/agent-kevin/mcp-server && bun install
# cd to wherever you want Kevin's brain to live and launch Claude Code
mkdir -p ~/Documents/Agents/Kevin && cd ~/Documents/Agents/Kevin
claudeInside the session, register the local marketplace and install:
/plugin marketplace add ~/Developer/agent-kevin
/plugin install agent-kevin@agentdev-kevin
/exit
Then claude again and /agent-kevin:init as above.
Already have a
CLAUDE.mdin the directory? Kevin writes its operating manual toCLAUDE.local.mdinstead and leaves yours alone. Both files load at session start.
Plugin updates are not automatic for third-party marketplaces β Kevin ships an explicit version in plugin.json, so you pull new releases on your own. Inside a session:
/plugin marketplace update agentlayer # refresh the catalog
/plugin update agent-kevin@agentlayer # pull the new version
/reload-plugins # activate without restarting
(Local dev install? Swap agentlayer for agentdev-kevin.)
Prefer hands-off? Turn on auto-update via /plugin β Marketplaces tab β select the marketplace β Enable auto-update. Each launch then refreshes the catalog and pulls any new version automatically.
β οΈ Auto-update is a global toggle per marketplace, not per plugin β enabling it updates every plugin installed from that marketplace at startup, not just Kevin. Leave it off if you want to control exactly when each plugin changes.
/plugin update refreshes the plugin code only β it never touches your home's
scaffolded files (CLAUDE.md, SOUL.md, settings, rules) or runs bun install. After
pulling a new version, run /agent-kevin:upgrade to reconcile your home:
/agent-kevin:upgrade
See How upgrades & releases work for the full process.
graph LR
A[Sessions] -->|capture| B[Knowledge]
B -->|informs| C[Projects]
C -->|generate| D[Results]
D -->|feed back into| A
The flywheel. Every session makes Kevin smarter. Every project generates knowledge. Every piece of knowledge makes the next session better.
- π§ Memory that compounds. The
SessionEndandPreCompacthooks copy your conversation toknowledge/raw/sessions/. Theknowledge-compileskill distils those raw logs into structured wiki articles (user profile facets, cross-cutting concepts, active memory). On your next launch, the compiled knowledge loads as @-imports before you've typed a word. This loop is the entire evolution story. - π Project lifecycles, not just chats. Spin up projects with
/agent-kevin:create-project, track tasks with status / priority / dependencies, archive cleanly when they're done. Markdown files. Obsidian-friendly. Git-friendly. - π Daily, weekly, monthly cadences. Morning briefings, evening wraps, weekly goals, monthly reviews. Built-in skills, run on demand.
- π SEO that audits itself. Plug GSC + PageSpeed + SerpAPI, run
/agent-kevin:google-search-audit, get a ranked-by-impact diagnostic report. - π Web at your fingertips. Bundled Playwright + chromium for screenshots, styled PDFs (markdown + mermaid rendered), URL β clean Markdown (handles SPAs), scripted page recordings. Optional Perplexity for live web research.
- π Multiple homes, multiple personas. One personal Kevin, one work Kevin, one SEO Kevin. Same plugin, different brains.
- β Subscription-billed, not API-billed (see Claude Code Billing).
There's a lot going on inside an agent β and even more going on in your life around it. The Agent OS dashboard shows both: your life through Kevin's eyes. Every /agent-kevin:sync regenerates <HOME>/dashboard.html β a dark mission-control page you open like any file (no server, no service). A left sidebar carries Kevin's wordmark, the page nav, your avatar, and the system-health badge; the pages are operator-first:
- Today β a time-aware greeting and stat strip, with sub-tabs: the plan (focus, next 7 days, waiting-on), your weekly/monthly/yearly goals, a "today so far" activity trail (sessions, tasks touched, commands run, output produced), and a News tab of headlines harvested from recent briefings.
- Tasks β the agenda grouped by due horizon (overdue β today β this week β this month β later) and a needs-attention view (blocked with reasons, going stale).
- Projects β color-coded project cards with description, done/total progress, and last-updated; click one to expand its tasks grouped by status.
- Sessions β your real working sessions (command runs filtered out) from the last 30 days, grouped by day with longer summaries, subtle turn counts, and the working directory only when it isn't the agent home.
- Brain β active memory threads and recent decisions, the Memory tab (daily memory with summaries, learnings, pending), concept articles, the compile pipeline, and the last lint run.
- Reports β everything Kevin has produced, grouped by day, skill chips color-coded, every title clickable.
- Capabilities β a cheatsheet of starter recipes, every skill as a tile (with an
autobadge when the model may self-invoke it), every MCP tool, the fullkevinCLI command reference, and hook wiring. The "what can I ask Kevin?" page. - Profile β the operator page: your avatar, timezone, and the compiled profile rendered section by section (web links open in new tabs).
- Persona β Kevin's page: avatar, vibe, bio, core role, and soul traits rendered from IDENTITY.md and SOUL.md.
- System β sub-tabs for context assembly, settings (per-scope layers with their allow/deny/env contributions), and a scrollable log tail.
Pages and sub-tabs deep-link by hash (dashboard.html#work/projects), text filters narrow tasks/sessions/skills/tools/reports live, every project carries a stable color across its badges, and the pulsing health badge jumps you to whatever needs attention. Markdown links (tasks, reports, concepts, memory) open through a configurable opener app so they land rendered and editable rather than downloading as raw text β obsidian://open?path={path}&paneType=tab by default (the paneType=tab opens notes in a new Obsidian tab so the dashboard stays put); set the MARKDOWN_URL env var in .claude/settings.local.json to point elsewhere, e.g.:
{ "env": { "MARKDOWN_URL": "markedit://open?path={path}" } }How to refresh it: every /agent-kevin:sync does it automatically; /agent-kevin:dashboard rebuilds and opens it; kevin dashboard does the same from a terminal; the dashboard MCP tool is the programmatic hook. Every refresh also rebuilds projects/TASKS.md (and vice versa) β the two derived views always regenerate together. It's a snapshot, not a live app β the generated timestamp is in the footer. The file is fully self-contained and makes zero external requests: no CDN, no webfonts, no analytics. It renders identically offline, nothing on it leaves your machine, and regenerating it never mutates state.
β οΈ Privacy note:dashboard.htmlsits at your HOME root and reflects your tasks, knowledge stats, and (redacted) settings. If you ever publish that repo β e.g. enable GitHub Pages on it β this page publishes too. Keep agent homes private.
> /agent-kevin:init
β Kevin's character (SOUL): accept default, or refine?
β Kevin's role (IDENTITY): general / coding / research / planning / custom?
β Your name and timezone?
β Paste any URLs about you (blog, LinkedIn, GitHub, etc.) so Kevin seeds your profile
β Paste a path or URL for your avatar (optional, gets linked to knowledge/user/profile.md)
β Should knowledge/ and projects/ live somewhere else? (e.g. ~/Documents/Agents/Kevin-Knowledge)
β Communication style and any hard preferences?
β Configure skill packs (SEO, Browser, third-party libraries)?
β Confirm + scaffold
Total time: β 5 minutes. Each question's answer becomes the default for later steps. The wizard writes:
CLAUDE.md(operating manual + identity @-imports), orCLAUDE.local.mdif a CLAUDE.md already existsSOUL.md,IDENTITY.md,USER.md(Kevin's character / role / your headline)knowledge/andprojects/directory trees, optionally at custom locations.claude/settings.json(marketplace registration + pre-granted permissions for the always-on core MCP tools:ping,compile_*,task_*,knowledge_lint,links_rewrite,memory_prune,report_write. SEO + Browser pack tools land here only when you activate the matching pack viaconfigure-skills).claude/settings.local.json(gitignored; init writes an empty{}β Kevin has no universal-infra env keys. Pack-gated keys likePERPLEXITY_API_KEY,SERPAPI_KEY,OPENPAGERANK_API_KEY,GSC_SITE_URLare planted byconfigure-skillswhen you activate the matching pack; you fill the values in your editor, never via chat)
If you chose custom KEVIN_KNOWLEDGE or KEVIN_PROJECTS paths outside the home directory, the wizard appends the required permissions.allow entries and (where supported) sandbox.filesystem.allowWrite entries to <HOME>/.claude/settings.json so Claude Code can read/write there without prompting you on every operation.
The plugin registration in .claude/settings.json only takes effect on a fresh session. After init:
/exit
cd ~/Documents/Agents/Kevin && claudeWatch for a marketplace trust prompt on first relaunch. Accept it. If you miss it, recover with /plugin marketplace add ... + /plugin install agent-kevin@agentlayer.
$ cd ~/Documents/Agents/Kevin && claude
π§ Knowledge: ~/Documents/Agents/Kevin/knowledge
π Projects: ~/Documents/Agents/Kevin/projects
π Context Β· 4.2KB
β session tail 1.6KB (YYYY-MM-DD.md)
β today reports 0.2KB (1 briefing)
β git activity 0.3KB (15 commits in the last week)
> /context
Context loaded from <HOME>/CLAUDE.md and its @-imports:
CLAUDE.md operating manual + @-imports
ββ @SOUL.md Kevin's character
ββ @IDENTITY.md Kevin's role
ββ @USER.md your headline + links to deeper user facets
ββ @knowledge/index.md master catalog
ββ @knowledge/memory/index.md active threads Β· decisions Β· learnings
ββ @projects/TASKS.md cross-project task dashboard
Read on demand (not auto-loaded β Kevin pulls them when relevant):
Β· knowledge/user/{profile,skills,preferences,career,interests}.md
Β· knowledge/concepts/<slug>.md
Β· projects/<slug>/README.md + tasks
Dynamic (per-session, injected by SessionStart hook):
Β· today's date (YYYY-MM-DD, <your-timezone>)
Β· last session tail (yesterday's conversation)
Β· today's reports (briefings, plans, audits written earlier today)
Β· recent git activity in knowledge/
Plugin: agent-kevin@agentlayer Β· 28 MCP tools loaded
> /agent-kevin:morning-briefing
[Kevin reads your active threads, in-flight tasks, anything overdue, and surfaces what
deserves your attention today, using yesterday's session tail as continuity context]
> Create a project called "new-blog". I want to relaunch under a different domain.
[Kevin runs /agent-kevin:create-project, scaffolds projects/new-blog/, registers the
prefix, asks you for the one-line vision, opens for your first task]
> Audit the site I have in Search Console.
[Kevin runs /agent-kevin:google-search-audit, pulls 28 days of GSC, PSI on the top 5
pages, applies 4 rules, ranks findings by impact, writes the report to
projects/<slug>/audits/YYYY-MM-DD.md, threads matching findings into open tasks]
> /exit
[SessionEnd hook captures the conversation to knowledge/raw/sessions/YYYY-MM-DD.md,
redacting any API key values from settings.local.json before persisting.
Next time you run /agent-kevin:knowledge-compile, this session feeds into Kevin's
long-term memory.]
The header banner (π§ Knowledge / π Projects / π Context) is what the SessionStart hook injects on every launch β quick proof your brain is wired up. The /context slash command (built into Claude Code) shows the full @-imports cascade: identity stack, knowledge index, memory index, task dashboard, plus the dynamic per-session additions. User facets and concept articles aren't auto-loaded β Kevin reads them on demand via the links in USER.md and knowledge/index.md. That keeps the static lane lean while keeping the deeper material one read away.
Kevin's long-term memory follows Andrej Karpathy's LLM Wiki pattern. Raw conversations are source code, an LLM is the compiler, the compiled wiki is your queryable second brain.
graph LR
HOOK[SessionEnd hook] --> SES[raw/sessions/]
PRE[PreCompact hook] --> SES
SES --> C[knowledge-compile]
FB[raw/user/feedback.md] --> C
INBOX[raw/inbox/] --> C
C --> USER[user/]
C --> CON[concepts/]
C --> MEM[memory/]
USER -.-> NEXT[next session]
CON -.-> NEXT
MEM -.-> NEXT
The capture is automatic. Every time you exit a session, or Claude Code auto-compacts mid-session, a hook calls bin/kevin session-capture which reads your transcript and appends it to today's session log under knowledge/raw/sessions/YYYY-MM-DD.md. The hook redacts API key values before writing (exact-match against .claude/settings.local.json env values, plus prefix heuristics for sk-β¦, pplx-β¦, AIzaβ¦, sk-ant-β¦, gh[pous]_β¦). The CLI is harness-agnostic β adding Codex (or any future host) is a one-file format adapter inside mcp-server/src/knowledge/session-capture.ts, not a new hook script.
Capture anything else manually. A thought, a meeting note, a clipped article, a file, a URL, a correction rule β anything you want compiled into the wiki goes in via the capture verb. Same destination, same compile pipeline; you just initiate it instead of a hook.
In a conversation (the common case). Drop a URL, paste a snippet, or hand Kevin a file path β he'll route to the capture MCP tool automatically. The tool is exposed as mcp__plugin_agent-kevin_kevin__capture, and natural-language prompts work fine:
you > capture this for the inbox: https://thenewstack.io/hidden-agentic-technical-debt/
kevin > [calls capture(url=β¦)] β wrote inbox β knowledge/raw/inbox/2026-05-29-1430-hidden-agentic-technical-debt.md
you > save as feedback: when refactoring, don't touch adjacent code I didn't ask about
kevin > [calls capture(text=β¦, kind=feedback)] β appended to knowledge/raw/user/feedback.md
you > here's my standup notes β capture with title "Standup 2026-05-28": <paste>
kevin > [calls capture(text=β¦, title=β¦)] β wrote inbox
you > pull in ~/notes/board-meeting.md
kevin > [calls capture(file=β¦)] β wrote inbox
URL fetches run through Mozilla Readability + Turndown, which extracts the article body (drops nav/footer/sidebar/modal noise) and converts it to clean Markdown β no HTML soup in the inbox.
From the CLI β same surface, useful for clipboards, scripts, and one-shots from a terminal:
# Inline thought β raw/inbox/<ts>-<slug>.md
kevin capture "remember to follow up with tracy on constitution lodgement"
# Local file β raw/inbox/ with an explicit title (overrides the auto-slug)
kevin capture --file=~/notes/board-meeting.md --title="Board meeting 2026-05-28"
# URL β fetch, extract article body, convert to Markdown, store with provenance
kevin capture --url=https://docs.anthropic.com/en/docs/claude-code/overview
# Stdin pipe β useful for clipboard / scripted captures
pbpaste | kevin capture --stdin --title="Clipped article"
# Correction / rule / preference β raw/user/feedback.md (compiled into memory/index.md β Learnings)
kevin capture --kind=feedback "don't propose git push for local-only repos"
# Optional metadata β label is stored in frontmatter (inbox) or in the feedback header
kevin capture --file=~/spec.md --label="design-spec"| Flag | Behaviour |
|---|---|
(positional) or --text=... |
Inline text. Default input source. |
--file=PATH |
Read a local file (β€ 512 KB) and capture its contents. |
--url=URL |
Fetch over HTTP(S) (β€ 5 MB raw). HTML responses run through Mozilla Readability (extracts the article body, drops nav / footer / sidebar / modals) β Turndown (HTML β Markdown). On extraction failure, falls back to a regex strip of <script>/<style>/<head>/<nav>/<header>/<footer>/<aside>/<form>/<svg>/<iframe>/comments. Sanitized body must fit β€ 512 KB. Provenance recorded as source: url:<url> in frontmatter. |
--stdin |
Read from stdin. Auto-enabled when stdin is a pipe. |
--kind=inbox (default) |
Write to knowledge/raw/inbox/<YYYY-MM-DD-HHMM>-<slug>.md. Compiled into concepts / user facets next compile. |
--kind=feedback |
Append to knowledge/raw/user/feedback.md. Operator-meta β corrections, preferences, rules. Compiled into memory/index.md β ## Learnings. |
--title=X |
Sets the filename slug + frontmatter title (inbox only). Without it, the slug comes from the first heading / first line. |
--label=X |
Stored in frontmatter (inbox) or in the feedback entry header. Free-form tag. |
Local-only, secret-redacted (same heuristics as session capture), atomic write, content-hash deduped (re-capturing identical input short-circuits to the existing file). The same surface is exposed as mcp__plugin_agent-kevin_kevin__capture for use inside Claude Code sessions β same options, same defaults.
The compile is on-demand. When you run /agent-kevin:knowledge-compile, Kevin picks up any session logs whose hash has changed since last compile, plus any inputs you've captured into knowledge/raw/inbox/ (via kevin capture, the MCP capture tool, or a direct file drop), plus any new feedback in knowledge/raw/user/feedback.md. The MCP server returns a synthesis prompt; you, in your TUI session, synthesize; the MCP server confirms the write. Idempotent, hash-tracked, interruptible.
| Output | Lifecycle | What lives there |
|---|---|---|
knowledge/user/ |
Permanent, evolves with you | profile, skills, preferences, career, interests, the durable facets refined every compile |
knowledge/concepts/ |
Permanent, cross-cutting | patterns and strategies spanning multiple projects. Specs distill into concepts here |
knowledge/memory/ |
Hot context (index.md loads every session) |
active threads, recent decisions, learnings from feedback. Daily entries auto-prune after 14 days |
Why this stays cheap. The compile MCP tool returns a synthesis prompt, Claude Code (you, in your TUI turn) runs the synthesis using your subscription, the result is written back via another MCP call. No internal LLM-as-a-service, no API billing.
/agent-kevin:sync runs the whole maintenance chain β compile β lint β prune β links β flywheel β scan β dashboards β when you want every derived view brought current at once. Heavier than quick-pulse, lighter than running each skill manually.
flowchart TD
SES[/raw/sessions/<br/>YYYY-MM-DD.md/] -.pending.-> C1
INB[/raw/inbox/<br/>captured items/] -.pending.-> C1
FB[/raw/user/<br/>feedback.md/] -.pending.-> C1
START([/agent-kevin:sync]) --> C1[1\. Compile pending raw inputs]
C1 --> C2[2\. Lint + auto-fix]
C2 --> C3[3\. Prune transient memory]
C3 --> C4[4\. Rewrite stale wikilinks]
C4 --> C5[5\. Flywheel: advance Β· **archive** Β· **persist**]
C5 --> C6[6\. Scan for overdue/stale]
C6 --> C7[7\. Refresh dashboards + read dust-settled state]
C7 --> OUT([π Status block])
C1 -.synthesis in your TUI turn.-> WIKI[(knowledge/<br/>user Β· concepts Β· memory)]
C2 -.errors + warnings.-> LINT[/.kevin/lint.md/]
C5 -.advance Β· update Β· close.-> TASKMUT[(task frontmatter<br/>+ threads)]
C5 -.unconditional sweep.-> ARCHIVE[(projects/<slug>/<br/>tasks/archive/)]
C5 -.unconditional snapshot.-> FLYREP[/reports/briefings/<br/>flywheel/<slug>.md/]
C7 -.one call, both views.-> TASKS[/projects/TASKS.md<br/>+ dashboard.html/]
The dependency order is the point: compile feeds the wiki state that lint operates on; lint's auto-fix touches the same articles the dashboard's task-link rewriter needs to be clean. Flywheel runs after the wiki is clean (so it reads a current memory index) and before scan + dashboard refresh (so both views reflect post-flywheel task state). Running steps out of order makes you re-reconcile.
Two sub-steps of flywheel run every sync, unconditionally: the archive sweep (moves done/cancelled task files into tasks/archive/ so the active dir stays scannable) and the snapshot persist (report_write to reports/briefings/flywheel/ so the next morning brief can pick up the cross-session trail). Advance Β· update Β· close Β· concepts Β· decisions fire only when there's real work to do.
The status block reads from the dust-settled artifacts (projects/TASKS.md, .kevin/lint.md, knowledge/memory/index.md) β not from per-tool return values β so the summary reflects what's actually on disk after every mutation has landed. See skills/sync/SKILL.md for the protocol.
Four MCP tools (the browser_* family) backed by a bundled chromium (installed once via bun install's playwright postinstall, ~150MB). All four output to <HOME>/reports/captures/<timestamp>-<name>.<ext>. The Browser pack must be active (/agent-kevin:configure-skills β tick Browser pack) for the permissions to be pre-granted; without it the first call confirms.
| Tool | Output | Use it for |
|---|---|---|
browser_screenshot |
PNG | Visual snapshot of any URL or local HTML / MD file; optional fullPage for the whole scrolling page |
browser_pdf |
PDF (A4) | Render markdown (with mermaid diagrams) or HTML to print-styled PDF |
browser_markdown |
Markdown | Convert any URL β including SPAs / Next.js / React sites β to clean LLM-friendly Markdown. Loads in chromium so client-rendered sections hydrate; pipes through Mozilla Readability + Turndown |
browser_record |
WebM video | Drive a page through scripted steps (navigate / scroll / wait) and capture the run |
All four take the same input β a URL, a file:// URL, or an absolute/relative path. screenshot and pdf will also render local Markdown files (loading them through marked + a styled CSS so mermaid renders). markdown does the reverse β fetches a hydrated page and converts back to Markdown.
In a conversation (the common case) β just ask:
you > screenshot https://acme.com and call it acme-landing
kevin > [calls browser_screenshot(input=β¦, name=acme-landing)] β reports/captures/<ts>-acme-landing.png
you > render ~/Documents/business-plan.md to PDF
kevin > [calls browser_pdf(input=β¦)] β reports/captures/<ts>-pdf.pdf (mermaid diagrams come through)
you > convert https://basem.emara.io to markdown β make sure the JS-rendered sections come through
kevin > [calls browser_markdown(input=β¦, waitUntil=networkidle)] β reports/captures/<ts>-markdown.md
you > record a 15-second tour of agentlayer.one β scroll halfway, wait 2s, scroll to the bottom
kevin > [calls browser_record(input=β¦, steps=[{kind:scroll,pixels:600},{kind:wait,ms:2000},{kind:scroll,pixels:9999}])] β reports/captures/<ts>-record.webm
graph LR
CAP["Reactions + corrections<br/>in chat"]
FB["knowledge/raw/user/<br/>feedback.md"]
SYN["compile: feedback<br/>synthesis"]
LN["knowledge/memory/<br/>index.md ## Learnings"]
NEXT["next session"]
REV["self-review skill"]
EDIT["edits to SOUL,<br/>CLAUDE.md, skills"]
PLANS["plans to<br/>reports/plans/"]
CAP --> FB
FB --> SYN
SYN --> LN
LN -.->|loaded every session| NEXT
FB --> REV
REV --> EDIT
REV --> PLANS
Every time you correct Kevin mid-conversation ("don't do that", "actually, that's wrong"), the SessionEnd hook captures the correction into knowledge/raw/user/feedback.md, append-only, durable. The next knowledge-compile run synthesises all feedback into a ## Learnings block in knowledge/memory/index.md, which loads as static memory at the start of every future session. Kevin sees his own past misses while he works and self-corrects in real time.
When you have ten minutes, run /agent-kevin:self-review. It's not a quick pass over the synth β Kevin casts a wide signal net across eight sources: the ## Learnings synth, the full feedback.md, the last 7 days of session logs and task threads, git history (to find prior-fix commits), concept articles, in-flight plans, and installed skills. Grep is for both correction and confirmation phrases β wins matter too, they validate non-obvious choices.
Each theme gets classified as missing, buried, present-but-violated, or present-and-working β the whole point is catching rules that landed but didn't stick. Themes rank by severity Γ instance count Γ cycle count; anything with fewer than two independent signals or present-and-working gets dropped. If nothing clears the bar, Kevin says so and stops.
Proposals come in three tracks:
- Track A β prompt/skill edits. Applied synchronously in-session, you pick which to accept. Surface choice is deliberate: identity β SOUL, procedural β CLAUDE.md, skill-specific β that skill's body.
- Track B β code-change plans. Written to
<HOME>/reports/plans/via thereport_writeMCP tool, never auto-applied. You implement them in a separate session. - Track C β skill install or create. Only when the signal is a recurring multi-step procedure. Requires explicit in-session approval.
Kevin also sweeps <HOME>/reports/plans/ for aging proposals (>14 days, no follow-through) and proposes re-surface / downgrade / close on each one. A quality gate runs before any proposal lands β every target file actually read (not paraphrased), specific evidence (timestamps, quotes, file:line), coverage audit done, and for any pre-existing rule: violations counted after it was introduced.
Three stages, loosely coupled. Capture is automatic. Compile is on-demand. Review is manual. No ceremony.
Track your projects, plan your weeks, capture decisions, remember context across sessions. Spin up cd ~/Documents/Agents/Kevin && claude whenever you want, ask Kevin what you were working on last Tuesday, get a coherent answer because the session tail loaded itself.
Configure GSC + PageSpeed + SerpAPI keys once. Run /agent-kevin:google-search-audit weekly (or wire it to cron). Get a markdown report ranked by impact, findings threaded into existing tasks. Pair with optional third-party SEO libraries for content drafting + EEAT scoring.
Different homes for different roles. Each home is its own brain with its own configured skill packs.
~/Documents/Agents/personal-kevin/ # personal projects, journals, life ops
~/Work/agents/work-kevin/ # client projects, professional persona
~/Documents/Agents/seo-kevin/ # SEO-focused, only the SEO pack configuredThe plugin code lives once on disk. Each home is independent. Switch by cd-ing into the home you want and launching claude. The right brain loads automatically.
You already have a project with its own CLAUDE.md. You want Kevin's memory + task system layered on top, without overwriting your existing instructions.
cd ~/Developer/my-existing-project
claude
/agent-kevin:initInit detects the pre-existing CLAUDE.md and writes Kevin's operating manual to CLAUDE.local.md instead. Both files load at session start (Claude Code natively merges them). Your project context and Kevin's identity coexist.
Drop Kevin into a team repo, commit the <HOME>/{CLAUDE.md, SOUL.md, IDENTITY.md, .claude/settings.json, knowledge/} files, gitignore settings.local.json. Every teammate gets the same agent identity. Each accepts the trust prompt once on first launch.
The brain is portable markdown on your disk. Claude Code is the runtime. The plugin is the glue. Obsidian is how a human reads the brain. Terminal-driven scripts read and write the brain directly via bin/kevin when you don't want a session.
graph LR
YOU["You"]
CC["Claude Code"]
PLUGIN["agent-kevin plugin<br/>MCP server Β· skills Β· hooks"]
BRAIN["Brain<br/>your markdown home"]
OBS["Obsidian"]
TERM["Terminal"]
EXT["External services<br/>GSC Β· PageSpeed Β· SerpAPI<br/>OpenPageRank Β· Perplexity Β· Playwright"]
YOU <-->|chat| CC
CC <-->|plugin loaded| PLUGIN
PLUGIN -->|reads + writes| BRAIN
PLUGIN -.->|hooks capture sessions| BRAIN
PLUGIN -->|dispatch with your keys| EXT
TERM -->|bin/kevin CLI| BRAIN
BRAIN -->|browse| OBS
| Layer | What | Where |
|---|---|---|
| You | The decision maker | wherever you are |
| Claude Code | The AI runtime that reads the brain and acts on it | your terminal |
| Plugin | Skill bodies, MCP server, hooks | agent-kevin/ (one repo, multiple homes) |
| Brain | Personality, knowledge, projects, everything that makes Kevin yours | <HOME>/ (portable markdown) |
| Obsidian | Human-facing browser for the brain β clickable wiki-links, daily notes, graph view | <HOME>/ opened as an Obsidian vault |
| Terminal | Bypass route for scripted task ops and headless compile runs | shell bin/kevin invocations |
| External services | Optional tools the MCP server dispatches to with your API keys | GSC, PageSpeed, SerpAPI, OpenPageRank, Perplexity, in-process Chromium |
| Skill | What it does |
|---|---|
init |
First-run onboarding |
configure-skills |
Configure skill packs, install third-party libraries |
knowledge-compile |
Synthesise raw sessions/feedback/inbox items into the wiki |
create-project / archive-project |
Project lifecycle |
flywheel |
Cross-project work session |
sync |
End-to-end maintenance: compile β lint+fix β memory-prune β dashboard refresh β briefing in one pass |
morning-briefing / evening-briefing |
Daily orient + wrap |
weekly-goals / monthly-goals / yearly-goals |
Goal-setting cadences β weeks, monthly themes, and the year planned quarter by quarter |
quick-pulse |
60-second status check |
self-review |
Process feedback into skill refinements |
itinerary |
Wizard-style trip planner β interviews you, researches flights/routes/prices, renders an interactive, print-ready HTML itinerary into a trips project |
plan-spec |
Deep-dive spec writer β Socratic interview β standalone, plan-compatible spec saved to the plans directory (/plan-spec) |
simple-simplify |
Review a script/app/area/change and simplify it: elegance, dead-code removal, no over-engineering (/simple-simplify) |
humanizer |
Strip the tells of AI-generated prose β inflated symbolism, rule-of-three, em-dash overuse, AI vocabulary β to make writing read as human |
Custom-skill authoring isn't a Kevin skill, because Claude Code already ships a native
skill-creatorplugin that does exactly that. Use it for your own skills.
serpapi Β· open-page-rank Β· google-search-console Β· google-page-speed Β· wordpress-rest Β· google-search-audit
Four need API keys (SerpAPI, OpenPageRank, Google OAuth + GSC_SITE_URL for the last two). wordpress-rest uses curl with a host-scoped permission grant derived from GSC_SITE_URL. google-search-audit is a composite read-only audit using everything above. Account signup steps and costs: External accounts & costs.
- Perplexity, live web search with citations (
mcp__plugin_agent-kevin_kevin__web_search). Built into thekevinMCP server β direct call to the Perplexity Search API, no extra subprocess. Activate the tool via/agent-kevin:configure-skills(grants the permission + ensures aPERPLEXITY_API_KEYplaceholder insettings.local.json), then fill the key value in your editor βconfigure-skillsnever asks for it in chat, since pasted secrets touch the transcript and the Anthropic API. Way better answers than vanilla web-search and dirt-cheap on pay-as-you-go: $5 of credit lasts most personal users several days to several weeks depending on query volume. Get a key at perplexity.ai/settings/api. - Browser tools, four web tools backed by a bundled Playwright + chromium (drops in via the one-time
bun install). See Browser web tools below for the full set, or here's the short of it:browser_screenshotβ PNG of any URL or local HTML/MD filebrowser_pdfβ styled PDF (markdown + mermaid rendered)browser_markdownβ JS-rendered page β clean Markdown via Readabilitybrowser_recordβ scripted page interactions β WebM video
Installed on demand via skills.sh. Pure-prompt content/marketing skill libraries are not bundled. They install via Vercel Labs' skills CLI into <HOME>/.claude/skills/ as symlinks into the skills.sh cache, so upstream updates propagate without re-running install. Currently offered:
aaron-he-zhu/seo-geo-claude-skills(Apache-2.0): 20-skill SEO + GEO library includingcontent-quality-auditor(80-item CORE-EEAT audit),seo-content-writer,content-refresher,domain-authority-auditor.coreyhaines31/marketingskills: 23 marketing playbooks (CRO, SEO, copy, analytics, experiments, pricing, launches, ads, social).
Install: /agent-kevin:configure-skills β tick "Third-party libraries".
| Group | Tools |
|---|---|
| Tasks (7) | task_query, task_get, task_create, task_update, task_close, task_thread, task_scan |
| Knowledge (7) | capture, memory_prune, links_rewrite, knowledge_lint, compile_status, compile_next, compile_write |
| Reports (1) | report_write |
| Dashboard (1) | dashboard |
| GitHub (9) | github_pr_list, github_pr_view, github_pr_diff, github_pr_checks, github_run_list, github_run_view, github_run_log, github_issue_list, github_issue_view |
| Dispatch (15) | serpapi_search, open_page_rank, google_auth, gsc_query, gsc_inspect, gsc_sites, page_speed_psi, page_speed_audit, browser_screenshot, browser_pdf, browser_markdown, browser_record, browser_flows, web_search, ping |
Always-on core (ping, compile_*, task_*, knowledge_lint, memory_prune, links_rewrite, report_write, dashboard) is pre-granted via permissions.allow at init. Pack-gated tools (SEO: serpapi_search, open_page_rank, gsc_*, page_speed_*, google_auth; Browser: web_search, browser_*; Database: database_*; GitHub: github_pr_*, github_run_*, github_issue_*) only land in permissions.allow when you activate the matching pack via /agent-kevin:configure-skills. This keeps settings.json an accurate audit trail β it advertises only the packs you actually opted into.
- SessionStart: pre-init shows the setup banner. Post-init injects today's date, last session tail, today's reports (any briefings or plans written earlier today), and recent git activity (β€10KB total).
- SessionEnd + PreCompact: capture transcript turns to
knowledge/raw/sessions/YYYY-MM-DD.mdwith API key redaction. This is what makes the flywheel work. Without these hooks, Kevin would have no source material to compile into long-term memory.
agent-kevin/
βββ .claude-plugin/
β βββ plugin.json # plugin manifest
βββ assets/ # Kevin's avatar, AgentLayer logo
βββ bin/
β βββ kevin # standalone CLI for shell-driven task ops
βββ hooks/
β βββ hooks.json # SessionStart + SessionEnd + PreCompact
βββ mcp-server/ # the kevin MCP server (Bun)
β βββ src/
β βββ package.json
βββ scripts/ # one-off migration scripts (session-capture/start now live in bin/kevin)
βββ skills/ # 21 skills (15 core + 6 SEO) auto-load with plugin
βββ templates/ # init copies these into <HOME>
β βββ CLAUDE.md # β <HOME>/CLAUDE.md (or CLAUDE.local.md on collision)
β βββ IDENTITY.md # Kevin's role (includes Kevin's avatar)
β βββ SOUL.md # Kevin's character
β βββ USER.md # YOUR headline + links to knowledge/user/
βββ .mcp.json # declares the `kevin` MCP server
βββ LICENSE # Apache 2.0
βββ NOTICE # Apache 2.0 attribution
<HOME>/
βββ .claude/
β βββ assets/ # Kevin's avatar (kept out of the home root)
β βββ skills/ # third-party skill libraries installed via skills.sh (lazy)
β βββ settings.json # enabledPlugins + pre-granted permissions
β βββ settings.local.json # API keys, gitignored
βββ .kevin/ # plugin runtime state (hidden)
β βββ config/ # OAuth tokens
β βββ logs/
β βββ knowledge.json # compile state
βββ knowledge/ # (or KEVIN_KNOWLEDGE elsewhere)
β βββ concepts/ # cross-cutting articles
β βββ memory/ # hot context (threads, decisions, learnings)
β βββ raw/ # unprocessed inputs to compile
β β βββ archive/ # compiled inbox items land here after compile
β β βββ sessions/ # auto-captured conversations (the source of evolution)
β β βββ inbox/ # drop any input here (or use `kevin capture`) for distillation
β β βββ user/
β β βββ feedback.md # corrections log (append-only)
β βββ user/ # evolving long-form knowledge about you (incl. profile.md with your avatar)
β βββ index.md # master catalog
βββ projects/ # (or KEVIN_PROJECTS elsewhere)
β βββ <slug>/
β β βββ tasks/
β β β βββ <id>-<slug>.md
β β βββ README.md
β βββ TASKS.md
βββ reports/ # transient skill outputs (briefings, plans)
β βββ index.md # auto-maintained "newest first" log (today's entries injected into SessionStart)
β βββ briefings/ # morning/evening briefings, weekly/monthly goals, self-review summaries
β βββ captures/ # browser-tool artifacts (screenshots, pdfs, recordings) β gitignored, regenerable
β βββ plans/ # self-review code-change proposals (Track B) + native plan-mode saves (plansDirectory)
βββ .mcp.json # only present if the user adds their own MCP servers β Kevin's bundled `kevin` server lives in the plugin's own .mcp.json
βββ CLAUDE.md # operating manual + @-imports for identity stack
β # (or CLAUDE.local.md if CLAUDE.md pre-existed)
βββ IDENTITY.md # Kevin's role + evolving self-description
βββ SOUL.md # Kevin's character
βββ USER.md # YOUR headline + links to knowledge/user/
Open <HOME>/ in Obsidian to browse with working wiki-links. .claude/ and .kevin/ are hidden by default.
For terminal-driven task ops, cron jobs, scripted compile prep:
export PATH="$HOME/Developer/agentlayer-claude-marketplace/agent-kevin/bin:$PATH"
kevin help # full command referencekevin help prints groups, commands, flags, env vars, and examples. The major groups:
| Group | What it does |
|---|---|
kevin task <subcmd> |
Query, get, create, update, close, thread, scan tasks |
kevin dashboard |
Rebuild both dashboards: projects/TASKS.md + the Agent OS page at <HOME>/dashboard.html |
kevin knowledge lint [--fix] |
Structural wiki health check (broken links, orphans, missing backlinks, sparse, invalid frontmatter); --fix auto-rewrites links + inserts backlinks |
kevin compile <subcmd> |
status (queue), next (peek), write <id> (mark complete). Synthesis itself runs in Claude Code via /agent-kevin:knowledge-compile |
kevin prune |
Delete memory/YYYY-MM-DD*.md older than the retention window (14 days) |
kevin links |
Rewrite bare task IDs + shorthand into [[wikilinks]] across the wiki |
kevin ping |
Print resolved paths + timezone (sanity check) |
Common examples:
kevin task query --status=active
kevin task create --project=blog-dev --title="Draft launch post" --description="..." --priority=P1
kevin task dashboard # rebuild projects/TASKS.md from frontmatter
kevin knowledge lint --fix # check wiki + auto-fix broken links + backlinks
kevin compile status # what's pending compileNote: bin/kevin invokes the MCP server logic locally without going through Claude Code. The compile pipeline returns prompts (not synthesized output), so full evolution still needs a TUI session β see /agent-kevin:knowledge-compile for the orchestration loop, or /agent-kevin:sync to run compile β lint β dashboard β briefing in one pass.
| Env var | Purpose | Default |
|---|---|---|
KEVIN_HOME |
Path to your agent home. Required when launching claude from anywhere other than the agent home itself (subdirs, other repos, the user-level capture hook). |
current working directory at launch |
KEVIN_TIMEZONE |
IANA timezone for date formatting | system timezone |
KEVIN_KNOWLEDGE |
Override knowledge dir | $KEVIN_HOME/knowledge |
KEVIN_PROJECTS |
Override projects dir | $KEVIN_HOME/projects |
KEVIN_REPORTS |
Override reports dir | $KEVIN_HOME/reports |
KEVIN_CODE_PATH |
Absolute path to your primary codebase. Lets Kevin ground code-related tasks against it and surface its git activity in session context. Optional β asked in chat at init (not a secret), or set later. | none |
KEVIN_GIT_REPOS |
Comma-separated extra git repo paths (~-expanded) surfaced in the SessionStart context block alongside the knowledge repo. Init derives it from KEVIN_CODE_PATH; append more later. |
derived from KEVIN_CODE_PATH |
KEVIN_LOG_LEVEL |
Log level: debug Β· info Β· warn Β· error. Falls back to LOG_LEVEL. |
info |
KEVIN_LOG_FILE |
Override log file path. Set to off to disable file output. |
$KEVIN_HOME/.kevin/logs/app.log |
On KEVIN_HOME. When you launch claude from inside your agent home, the cwd-fallback works and you don't need to set anything. When cwd is somewhere else β a subdir of home, a sibling repo, or the user-level session-capture hook firing from a random project β the MCP server resolves paths relative to cwd instead, and writes land in the wrong place (or the isInitialized() guard fires and the hook silently no-ops). If you ever launch Claude Code from outside the home, set KEVIN_HOME in your shell rc or in ~/.claude/settings.json env.
KEVIN_KNOWLEDGE and KEVIN_PROJECTS let you put those directories anywhere (e.g. a cloud-synced folder β iCloud Drive on macOS, OneDrive on WSL2 β an external drive, or a separate git repo). The init wizard offers this during scaffold and, if the chosen path is outside the agent home, automatically appends permissions.allow (and sandbox.filesystem.allowWrite where supported) entries to <HOME>/.claude/settings.json so Claude Code can read/write there without prompting. If you set these env vars after init, edit settings.json yourself.
API keys (SERPAPI_KEY, OPENPAGERANK_API_KEY, GSC_SITE_URL, PERPLEXITY_API_KEY) live in <HOME>/.claude/settings.local.json env block, gitignored. The rule: init owns universal-infra env keys; configure-skills owns pack-gated env keys. Kevin's only universal-infra keys are the optional KEVIN_CODE_PATH / KEVIN_GIT_REPOS pair β init writes them only if you give a codebase path at Step 4b (otherwise /init writes an empty {}). Every API key above is a pack-gated key that configure-skills plants as an empty placeholder when you activate the matching pack. You fill the secret values in your editor β neither flow asks for them in chat, since secrets must not enter the session transcript or the Anthropic API. (The codebase path isn't a secret, so init does ask for it in plain chat.)
The database_list, database_schema, and database_query MCP tools run read-only Postgres queries against any databases you wire up: no external account, just a connection string. Connections are discovered by env-var convention. Every KEVIN_DB_<NAME> entry in <HOME>/.kevin/secrets/.env (since v0.3.0 connection strings, like all credentials, live in the deny-gated secrets store β not settings.local.json) becomes a connection named <name> (lowercased). Add or remove connections by editing that file, with no code change:
# <HOME>/.kevin/secrets/.env
KEVIN_DB_APP=postgres://user:pass@localhost:5432/app_dev
KEVIN_DB_ANALYTICS=postgres://user:pass@host:5432/analyticsThat yields connections app and analytics. The easiest way to set this up is the Database pack: run /agent-kevin:configure-skills (or tick it during /agent-kevin:init Step 8), which grants the database_* tool permissions and ensures .kevin/secrets/.env exists for the KEVIN_DB_<NAME> lines you add. You then fill the connection string in your editor, never in chat (it carries a password, and the secrets file is deny-gated so Kevin can't read it). Re-run the pack any time to add more connections. You can also just add the env lines by hand: the tools discover any KEVIN_DB_<NAME> key regardless of how it got there. database_list only ever reports host/port/database, never the credentials.
Every query runs inside a BEGIN READ ONLY transaction with a statement timeout and is then rolled back, so Postgres itself rejects any write: the read tools are read-only by construction. For tighter control (row or column limits), point the connection string at a SELECT-only database role.
The pack also grants one write tool, database_fork: it clones a database into a private copy via CREATE DATABASE <fork> TEMPLATE <source> (pure SQL β no pg_dump/pg_restore, no dump file, cross-platform), so you can run risky or destructive schema changes against a scratch copy instead of a shared/live DB. It refuses remote hosts (local servers only), defaults to the first connection and its database, names the fork after the current git branch, and can repoint an env file at the fork; drop: true tears it back down. This is what the setup-worktree skill uses to give a worktree its own database on demand.
Nine read-only GitHub tools let Kevin review pull requests and issues and diagnose failing CI without leaving the session: github_pr_list, github_pr_view, github_pr_diff, github_pr_checks, github_run_list, github_run_view, github_run_log, github_issue_list, and github_issue_view. github_run_log defaults to the failed steps only (gh run view --log-failed) β the right altitude for "why is this build red" without dumping a megabyte of green log. Diffs and logs are truncated to a character budget you can override per call.
They wrap the gh CLI (brew install gh), shelled out from inside the MCP server. That matters: under the Claude Code sandbox gh dies during TLS setup (its macOS build verifies certs through the keychain, which the seatbelt blocks), but the MCP server runs outside that sandbox, so the same gh works. There are no write subcommands β commenting, creating PRs, merging, and re-running workflows stay a deliberate human-in-terminal activity.
Auth is a fine-grained, read-only personal access token in <HOME>/.kevin/secrets/.env as GITHUB_TOKEN (gh honors it and skips the keychain). The easiest setup is the GitHub pack: /agent-kevin:configure-skills β tick GitHub (or tick it at /agent-kevin:init Step 8). It grants the nine tool permissions, ensures .kevin/secrets/.env exists, and walks you through minting the PAT β resource owner set to the repos' owner, repository permissions all read-only (Pull requests Β· Issues Β· Metadata Β· Checks Β· Actions). You paste the value into your editor, never into chat. The read-only token is a second wall behind the read-only tool surface.
One gotcha worth calling out: grant Actions: Read (which GitHub describes as "Workflows, workflow runs and artifacts") β that's what lets Kevin see CI run status and logs. Do not grant the separate Workflows permission: despite the name it's write access to the .github/workflows/*.yml files, which Kevin never touches. You don't need Contents either β PR diffs come through the Pull requests permission.
When a call omits repo, Kevin resolves owner/repo from the origin remote of your KEVIN_CODE_PATH, then the first KEVIN_GIT_REPOS entry β the same codebase pair init configures. An explicit repo="owner/repo" always wins, so you can point any call at another repo the token can see.
Two halves of one machine: maintainers release (describe what changed and what a
home needs), consumers upgrade (apply it). The contract between them is
CHANGELOG.md.
graph LR
A["/agent-kevin:release<br/>(maintainer)"] -->|CHANGELOG + tag| B["/plugin update<br/>(pull code)"]
B -->|/agent-kevin:upgrade| C["your home<br/>reconciled"]
Why two steps at all? A plugin update replaces files in the plugin directory.
Your home (CLAUDE.md, SOUL.md, .claude/settings.json, knowledge/, β¦) was
copied out of templates/ once, at /init, and has been yours to edit ever since. A
code update can't safely overwrite it. So the home is reconciled separately, on your
terms.
How "you're behind" is detected β locally, no network. Your home records which
template version it's on in .kevin/version.json (git-tracked, so it survives a clone).
Compared against the installed plugin.json version, that yields three states, surfaced
on the SessionStart banner and the dashboard's sidebar badge:
| State | Meaning | Signal |
|---|---|---|
current |
baseline == installed | (nothing) |
pending |
baseline < installed β migrations await | amber badge "upgrade available Β· N" |
onboard |
no version.json yet (home predates tracking) |
"enable update tracking" |
- Scope. Reads the
### Upgradeblocks for every release between your baseline and the installed version (pending), or all of them on a first run (onboard). Handles being many versions behind in one pass. - Coalesce. Merges the actions (latest wins) β the target is the current template state, not a replay of every intermediate edit.
- Back up. Snapshots every file it will touch into
.kevin/updates/<from>-to-<to>/before writing a byte. - Apply. Auto-applies functionality-critical changes; asks before anything you
may have personalized:
depsβ runsbun installin the MCP serversettingsβ merges missingpermissions.allowentries (never removes yours)fileβ copies new rule/concept files (only if absent)template/<file>β section-aware merge ofCLAUDE.md/SOUL.md/ etc.: adds new sections, updates changed ones, and preserves any sections you added (your personal blocks are never touched or deleted)
- Stamp. Writes the new baseline to
.kevin/version.json. - Sync. Finishes with
/agent-kevin:syncso the dashboard, briefing, and knowledge reflect the new state (or tells you to reload first if MCP code/deps changed).
Safety guarantees: always backs up first Β· never overwrites a file wholesale Β· never deletes a section it doesn't recognize Β· only auto-applies what the release marked mandatory/additive Β· idempotent (re-running when current is a no-op).
- Diffs everything since the last
v*tag and groups it into Added / Changed / Fixed. - Detects what consumers need by inspecting the diff (dependency changes, touched
templates/, new skills/tools needing permissions) and writes them as a machine- actionable### Upgradeblock. - Bumps
.claude-plugin/plugin.json(SemVer), prepends theCHANGELOG.mdentry, and stages a commit +vX.Y.Ztag for your approval β it never commits or pushes on its own.
Each release carries an ### Upgrade section; every actionable line is a backticked tag
plus a note. This is the exact text /agent-kevin:upgrade parses:
- `<kind>: <severity>` β <note>
| kind | severity | what the upgrade does |
|---|---|---|
deps |
required |
runs bun install |
settings |
mandatory |
adds the named permission/hook/env entries |
file |
additive |
copies a new file if absent |
template/<f> |
mandatory |
section-merges, applied automatically |
template/<f> |
optional |
section-merges, asks first with a diff |
manual |
β | a step only you can do; surfaced, never silent |
A code-only release writes a single line: None β code-only, no bun install or HOME changes.
Kevin's core needs zero external accounts: tasks, knowledge compile, dashboard, session capture, and all four Playwright web tools (bundled chromium) run entirely on your machine against your Claude Code subscription. External accounts only enter the picture when you activate the SEO, Browser, or GitHub packs via /agent-kevin:configure-skills. Everything below is optional; skip this section if you don't need web search, SEO tooling, or PR/CI access.
| Account | What it unlocks | Pack | Credential | Cost |
|---|---|---|---|---|
| Perplexity | web_search: live web research with citations |
Browser | PERPLEXITY_API_KEY |
Pay-as-you-go, $5 per 1,000 requests. A $5 credit lasts most personal users days to weeks. |
| GitHub | github_pr_* / github_issue_* / github_run_*: read-only PR + issue review + CI diagnosis (needs the gh CLI) |
GitHub | GITHUB_TOKEN (fine-grained, read-only PAT) |
Free |
| Google Cloud | gsc_* (Search Console data) + page_speed_* (Lighthouse audits) |
SEO | OAuth client JSON at <HOME>/.kevin/config/google-oauth-client.json |
Free. PSI quota is 25k requests/day per project. |
| Google Search Console | The site data behind gsc_query, gsc_inspect, and the audit skill |
SEO | Your site verified under the same Google account | Free |
| SerpAPI | serpapi_search: live Google SERP positions for rank tracking |
SEO | SERPAPI_KEY |
Free tier: 250 searches/month. Paid from $25/month (1,000 searches). |
| OpenPageRank | open_page_rank: domain-authority proxy (0β10) for competitor tracking |
SEO | OPENPAGERANK_API_KEY |
Free (1,000 requests/day; DomCop pledges to keep it free) |
No account needed for the rest of the SEO pack: wordpress-rest reads the public /wp-json/wp/v2/ API of whatever site GSC_SITE_URL points at, and google-search-audit is a composite over the tools above. The knowledge pipeline never bills an API key either (see Claude Code Billing).
Bottom line: a typical personal setup runs at $0/month on free tiers. Heavy Perplexity use or serious rank tracking adds roughly $5 to $30/month.
For every keyed service the flow is the same: /agent-kevin:configure-skills activates the pack and plants an empty placeholder in settings.local.json; you paste the key value in your editor, never in chat.
Perplexity (web search): create an account at perplexity.ai, go to Settings β API, load a small credit block ($5 is plenty to start), and generate a key. Note the API bills separately from a Perplexity Pro chat subscription (Pro only includes $5/month of API credit).
Google Search Console + PageSpeed (one free Google Cloud project covers both):
- console.cloud.google.com β create a project (any name).
- APIs & Services β Library β enable Search Console API and PageSpeed Insights API.
- APIs & Services β Credentials β Create credentials β OAuth client ID β application type Desktop app. (First time, Google forces you through the consent-screen setup: choose External, add your own email as a test user.)
- Download the client JSON and save it as
<HOME>/.kevin/config/google-oauth-client.json. - Verify your site in Search Console under the same Google account, and set
GSC_SITE_URLinsettings.local.json(e.g.https://example.com/orsc-domain:example.com). - Run the
google_authMCP tool once (orbun run dispatch google-search-console authfrom the plugin dir). A browser consent flow mints tokens that are cached and shared across allgoogle-*tools; you won't be asked again.
SerpAPI (rank tracking): sign up at serpapi.com, copy the key from the dashboard. The free 250 searches/month comfortably covers a weekly audit of a small site; upgrade only if you track many keywords across devices and locales.
OpenPageRank (domain authority): sign up at domcop.com/openpagerank, generate the free key.
By default Kevin only captures sessions when you launch claude from inside your agent home (the plugin's hooks fire on enabled-plugin sessions). If you want every Claude Code session on your machine β coding work in random repos, one-off Q&A, anything β to land in your knowledge base, add user-level hooks to ~/.claude/settings.json:
{
"env": {
"KEVIN_HOME": "/absolute/path/to/your/agent/home"
},
"hooks": {
"SessionEnd": [
{
"matcher": "",
"hooks": [
{
"type": "command",
"command": "bun /absolute/path/to/agent-kevin/bin/kevin session-capture --mode=session-end --hook-protocol=claude",
"timeout": 30
}
]
}
],
"PreCompact": [
{
"matcher": "",
"hooks": [
{
"type": "command",
"command": "bun /absolute/path/to/agent-kevin/bin/kevin session-capture --mode=pre-compact --hook-protocol=claude",
"timeout": 30
}
]
}
]
}
}Why this is useful. Kevin's knowledge compounds from raw session inputs. The richer the input stream, the richer the wiki. A coding session in another repo that mentions a new library, a debugging conversation that surfaces a workflow rule, a one-off chat that captures a decision β all of those would normally be lost. With capture-everywhere wired in, they all land in <HOME>/knowledge/raw/sessions/YYYY-MM-DD.md and feed the next /agent-kevin:knowledge-compile run.
How it stays safe. The CLI's isInitialized() guard checks for <KEVIN_HOME>/SOUL.md before writing β if your KEVIN_HOME env var is misconfigured or points at a non-Kevin directory, the verb logs a skip and exits. It won't pollute random dirs.
Excluding specific directories. Pass one or more --exclude PATH flags (repeatable) to suppress capture when claude is launched from those paths or any of their children. Paths are tilde-expanded and resolved to absolutes; matching uses /-boundary prefixes (so ~/Developer/foo excludes ~/Developer/foo/bar but not ~/Developer/foobar). Useful for sibling agents (another SOUL.md-rooted home), Ring-1 repos that shouldn't bleed into this knowledge base, or noisy throwaway dirs:
"command": "bun /absolute/path/to/agent-kevin/bin/kevin session-capture --mode=session-end --hook-protocol=claude --exclude ~/Developer/foo --exclude ~/scratch"Repeat the flag in both the SessionEnd and PreCompact hook entries. The plugin's own SessionEnd hook (when you launch from the agent home itself) already takes precedence via the pluginEnabledInCwd() check, so excludes only need to cover other agent homes and dirs you actively want to skip.
Three things to choose:
- Both hooks, recommended β
SessionEndcaptures complete conversations;PreCompactcaptures long sessions before Claude's auto-compaction discards detail. Together they cover ~all conversational content. SessionEndonly β lighter. You'll lose detail from sessions that hit auto-compact before you exit cleanly.- Don't set this up β only sessions launched from your agent home get captured. Simplest, but you'll miss cross-repo signal.
Trade-offs:
- The hardcoded plugin path means moving/uninstalling the plugin breaks the hooks. Acceptable for personal use; not portable across machines.
- Every Claude session pays a small startup cost to run the hook (β100ms). Negligible.
- This does not enable the plugin globally β no MCP tools or identity stack loads in non-Kevin sessions. The hooks are isolated.
- If you also want Kevin's full context (skills, MCP tools) available everywhere, enable the plugin globally instead in your
~/.claude/settings.jsonenabledPluginsblock. This is heavier and usually not what you want.
After editing ~/.claude/settings.json, launch claude from any directory, have a one-turn conversation, /exit, then check <KEVIN_HOME>/knowledge/raw/sessions/<today>.md β a new block should be appended.
- All data stays local. Your agent home is markdown on your disk. No cloud sync unless you choose to commit it to git.
- API keys live in
.claude/settings.local.jsonand data in.kevin/, gitignored by default. The plugin's.gitignoreincludes them. - Transcripts are redacted before persisting. The session-capture hook scrubs all values present in
settings.local.jsonand runs prefix heuristics for common key formats. - Anthropic training opt-out + telemetry disable is recommended on your Claude Code install. See docs.claude.com.
- The folder is the product. If anything goes wrong, the markdown + git history is the complete backup.
Built and tested on macOS. The plugin also runs on Linux (one caveat: chromium auto-install via playwright is sometimes flaky in headless sandboxes β on a fresh distro run playwright install-deps chromium once) and on Windows, both native and via WSL2.
- Native Windows works through Git Bash β the shell Claude Code uses for its Bash tool β which supplies the POSIX environment the hooks, MCP server, and per-skill
bashpatterns (e.g.Bash(git log *)) assume. Requirements:bunandgitonPATH. Rough edges to know about: MSYS path-mangling can bite commands that pass colon-paths or unix-style absolute paths (MSYS_NO_PATHCONV=1is the escape hatch); the OS sandbox is unavailable (Windows has no equivalent, so the sandbox block is omitted); and a few pack-gated skills assume tools Git Bash doesn't ship (e.g.serpapipipes throughjq). The core loop β tasks, compile, memory, briefings, worktrees, dashboard β runs natively. - WSL2 is the closest-to-Linux-production option: run everything from inside the distro, where Kevin shares the same POSIX path as Linux.
If you run Kevin on Linux, native Windows, or WSL2 and hit a platform-specific snag, please open a PR with install notes or a fix.
/agent-kevin:knowledge-compile is the showcase of how this plugin handles billing. Other personal-AI setups call the LLM internally, which bills against a metered API key. This plugin doesn't. The MCP server returns a synthesis prompt; you, in your interactive Claude Code session, do the synthesis; the MCP server confirms the write. The thinking happens inside your TUI turn, so it draws from your Claude Code subscription pool (Max / Pro / Teams), not a per-token API bucket.
Verify it yourself:
- Open Anthropic Console β Usage. Note current API cost.
- Run
/agent-kevin:knowledge-compileinside Claude Code. - Refresh Usage. API cost should not change. Subscription usage should increment.
If it does change, open an issue β that assumption was wrong.
Kevin started life as a much more ambitious thing: a standalone Bun daemon running a Telegram bot for the whole family, a cron-style heartbeat scheduler that woke Kevin up at 7am to send morning briefings, evening wraps that arrived while you were cooking dinner, the homeschool planner that produced actual printable HTMLs for the kids before the school week, autonomous knowledge compiles every six hours. The brain was the same markdown folder you see here. The body was a long-running process talking to the Claude Agent SDK on your behalf, calling out from your phone, the office, the car.
Then Anthropic closed off the Claude Agent SDK from subscription billing. Headless SDK calls became pay-per-token-API only. The whole point of Kevin was that he ran on your Max/Pro subscription bucket, not a metered API; the cost ceiling was a flat monthly bill, not "what did Kevin do while you were sleeping." Without subscription-backed SDK, the daemon model couldn't survive.
So Kevin had to die a little bit inside, and Kevin had to be reborn as a Claude Code plugin. The brain is intact. The skills got ported. The MCP server runs locally, returning prompts that you, in your TUI session, synthesize using your subscription. That's why everything in this plugin is structured to make Claude Code do the LLM work, not the plugin itself. No API charges, ever.
What that means in practice:
- β
You drive every session. Kevin is reactive, not proactive. You type
claude, Kevin loads, you ask. - β No proactive messaging. No "morning briefing at 7am" delivered to your phone. You run
/agent-kevin:morning-briefingwhen you sit down. - β No Telegram bridge. No texting Kevin from the airport.
- β No cron daemon. External schedulers (launchd, cron, GitHub Actions) can invoke Kevin via
claude --print, but they pay-per-token-API. Inside-CC manual runs stay subscription-billed. - β Everything else. Memory compounding, the wiki pipeline, projects, tasks, audits, briefings on demand. All here.
If Anthropic ever reopens the Agent SDK to subscription billing, we'll happily revive the daemon. Until then, this plugin is the maximum amount of Kevin that fits inside the rules.
Q: Do I need to be a developer to use this?
A: You need to clone a git repo, run bun install, and launch Claude Code. After that, the entire experience is conversational. /agent-kevin:init walks you through everything.
Q: I finished /init and relaunched, but no SessionStart banner appears.
A: The marketplace trust prompt was missed. Recover inside Claude Code with /plugin marketplace add github:AgentLayer1/agentlayer-claude-marketplace followed by /plugin install agent-kevin@agentlayer, then /exit and relaunch.
Q: I already had a CLAUDE.md in this directory before installing Kevin. Did it get overwritten?
A: No. Init detects pre-existing CLAUDE.md and writes Kevin's operating manual to CLAUDE.local.md instead. Both files load at session start.
Q: How do I update the plugin?
A: /plugin marketplace update agentlayer from inside Claude Code. Or if you cloned locally, git pull the marketplace repo. Your <HOME>/ data is untouched.
Q: How do I uninstall?
A: /plugin uninstall agent-kevin@agentlayer. Your <HOME>/ data stays. To purge everything: rm -rf <HOME>/.
Q: Will Kevin ever message me first?
A: No. See Claude Code Billing. Inside Claude Code, you initiate every session. External schedulers can pipe prompts into claude --print but those go through pay-per-token API.
Q: Subscription billing, does it really avoid API costs?
A: For the LLM synthesis steps yes. The MCP server is pure I/O, returning prompts; your interactive Claude Code session does the thinking using your subscription quota. To verify: note Anthropic Console β Usage before running /agent-kevin:knowledge-compile, refresh after. API cost should not change; subscription usage should increment.
macOS-only. Kevin runs anywhere Claude Code does, but the tooling below is what I (the author) actually use day to day on a Mac. Linux/Windows users: most have equivalents, but the specifics here assume macOS.
Running agents well is less about the model and more about the rig around it: a fast terminal, sane keybindings, isolated worktrees, and a place to read the markdown brain. Here's the setup that makes driving Kevin (and a swarm of other agents) genuinely pleasant.
Ghostty is a GPU-accelerated, native-Mac terminal. It's fast (120fps, zero input lag even with agents streaming walls of output), it's native AppKit (no Electron tax), and the config is a single readable file. After bouncing through iTerm2 and the rest, this is the one that stuck. The 25MB scrollback alone is worth it when an agent dumps a long trace and you need to scroll back through all of it.
π My Ghostty config β ~/.config/ghostty/config (a starting point, not gospel)
# Typography
font-family = JetBrainsMonoNerdFont
font-size = 14
font-thicken = true
adjust-cell-height = 2
# Theme and Colors β Catppuccin with automatic light/dark switching
theme = light:Catppuccin Latte,dark:Catppuccin Mocha
# Window and Appearance
background-opacity = 0.9
background-blur-radius = 20
macos-titlebar-style = transparent
window-padding-x = 10
window-padding-y = 8
window-save-state = never
quit-after-last-window-closed = true
window-theme = auto
# Cursor
cursor-opacity = 0.8
# Mouse
mouse-hide-while-typing = true
# Security
clipboard-paste-protection = true
clipboard-paste-bracketed-safe = true
# Shell Integration
shell-integration = detect
# Keybindings β tabs
keybind = cmd+t=new_tab
keybind = cmd+shift+left=previous_tab
keybind = cmd+shift+right=next_tab
keybind = cmd+w=close_surface
# Splits
keybind = cmd+d=new_split:right
keybind = cmd+shift+d=new_split:down
keybind = cmd+alt+left=goto_split:left
keybind = cmd+alt+right=goto_split:right
keybind = cmd+alt+up=goto_split:top
keybind = cmd+alt+down=goto_split:bottom
# Font size
keybind = cmd+plus=increase_font_size:1
keybind = cmd+minus=decrease_font_size:1
keybind = cmd+zero=reset_font_size
# Splits management
keybind = cmd+shift+e=equalize_splits
keybind = cmd+shift+f=toggle_split_zoom
# Reload config (Cmd+Shift+,)
keybind = cmd+shift+comma=reload_config
# Performance β generous scrollback (25MB)
scrollback-limit = 25000000
# Command finished notifications
notify-on-command-finish = unfocused
notify-on-command-finish-action = no-bell,notify
notify-on-command-finish-after = 30s
# Working directory inheritance
window-inherit-working-directory = false
tab-inherit-working-directory = true
split-inherit-working-directory = trueThese are readline (emacs-style) bindings that work in the Claude Code prompt and your shell. Internalize them and you stop reaching for arrow keys:
| Keys | Does |
|---|---|
Cmd + β / Cmd + β |
Jump to start / end of line |
Ctrl + A / Ctrl + E |
Start / end of line (readline equivalent) |
Ctrl + W |
Delete the word before the cursor |
Ctrl + K |
Kill from cursor to end of line |
Ctrl + U |
Clear the whole line |
Option + β / Option + β |
Move one word at a time |
Ctrl + W and Ctrl + K are the two that pay for themselves daily β chopping a half-typed prompt back a word at a time beats holding backspace.
cmux is a native-Mac terminal built on Ghostty (it renders via libghostty and reads your existing Ghostty config, so the look and keybindings above carry straight over). It's purpose-built for the parallel-agent era: instead of one terminal with one Claude session, you get workspaces in a vertical sidebar, each showing its git branch, PR status, working directory, and the latest agent notification.
Why it's great for driving Kevin and friends:
- One workspace per agent task. Kick off Kevin in one, a coding agent in another, a long research run in a third. Split panes within a workspace for the editor + logs + agent.
- Notifications that tell you who's waiting. When an agent finishes or needs input, its pane gets a ring and the sidebar tab lights up, so you know which of your six running agents wants attention without staring.
- Organize like a file system. Group related workspaces into folders, color-code by project (Kevin home = one color, each repo = another), and the sidebar becomes a live map of everything in flight.
- Session restore. It saves and restores workspace layouts, directories, and scrollback, so closing the lid doesn't lose your swarm.
cmux is open source (AGPL-3.0, by Manaflow AI). It pairs naturally with worktrees (next tip) β one workspace per worktree, one agent per workspace.
Add this to your user-level ~/.claude/settings.json env block:
{ "env": { "CLAUDE_CODE_NO_FLICKER": "1" } }It's an alias for Claude Code's fullscreen renderer, and it fixes more than the name suggests:
- Click-to-position in the prompt. This is the big one. Fullscreen mode enables mouse tracking, so you can click anywhere in your prompt text to move the cursor instead of arrow-keying across a long instruction. Without it, clicks fall through to the terminal and the prompt cursor never moves.
- No flicker. It draws on the alternate screen buffer (like vim/htop) and virtualizes rendering, so the input box stays pinned to the bottom and streaming output doesn't make the screen jump.
- Flat memory in long sessions. Only visible messages render, so a marathon session doesn't bloat.
A git worktree checks out a second (third, fourth) working copy of the same repo into a separate folder, each on its own branch, all sharing one .git. This is the unlock for running multiple agents on the same codebase without them stepping on each other's files:
# From inside the repo β spin up an isolated copy on a new branch
git worktree add ../myrepo-feature-x -b feature-x
git worktree add ../myrepo-bugfix -b bugfix-y
git worktree list # see them all
git worktree remove ../myrepo-feature-x # clean up when mergedPoint one cmux workspace (and one agent) at each worktree. Agent A refactors on feature-x while Agent B fixes a bug on bugfix-y, no merge conflicts mid-flight, no "wait, why did my file just change" surprises. When a branch lands, remove the worktree and the folder's gone. (Claude Code's own background agents use the same trick under the hood.)
Two conventions make this painless (and Kevin follows both):
- Worktrees are siblings of the main repo, never nested inside it. The main checkout lives at, say,
~/Developer/Acme/tech/acme, so a worktree lands one level up alongside it:~/Developer/Acme/tech/acme-my-feature. From the main checkout, the../keeps it at the same level:git worktree add ../acme-my-feature -b feat/my-feature. A nested worktree would sit under a tracked path and pollute the parent's working tree. - A fresh worktree needs its gitignored local files before it can run. A new checkout has no
.env*, no.claude/settings.local.json, no installed deps or built packages. You need to copy the machine-local config over from the main checkout, install, and build before the branch is workable.
You can just ask Kevin to do all of this. The bundled setup-worktree skill (/agent-kevin:setup-worktree, like every Kevin skill it only acts when you ask) first pins down which repo you mean (it asks when the HOME sits above several repos), creates the worktree as a sibling on a new branch, then bootstraps it: it copies the gitignored local files (.env*, .claude/settings.local.json, .cursor, .cmux) from the main checkout, detects the package manager (bun / pnpm / yarn / npm), installs, and runs the repo's build script. Say "make a worktree for the billing refactor" and you get a ready-to-code checkout. Under the hood the skill calls the bundled setup_worktree MCP tool, which runs outside the Bash sandbox so git worktree add can make the writes the seatbelt blocks (the main repo's .git/config and checked-out config like .vscode/settings.json / .mcp.json). The same logic is on the CLI for a real terminal: kevin worktree <repoPath> --branch=....
π‘ Managing worktrees from the CLI gets tedious. Tower has an excellent worktree GUI to create, switch, and prune them visually. See tip #10.
If your terminal (cmux) is now the primary place agents do work, Cursor is overkill. Cursor's whole pitch is an AI layer baked into the editor, but when Claude Code and other agents live in the terminal driving the actual changes, you're paying for a second AI surface you don't use. Drop back to plain VS Code for reading diffs, quick manual edits, and extensions. The editor becomes a viewer/tweaker; the terminal is the cockpit.
Kevin's entire memory is markdown with [[wikilinks]], and so is almost everything an agent touches: tasks, project READMEs, plans, reports, knowledge articles. Working with agents is working in markdown all day. Open <HOME>/ as an Obsidian vault and that whole tree comes alive β it's a far nicer reader/editor for the projects, tasks, and notes than a code editor:
- A real markdown workspace. Browse and edit
projects/,knowledge/, reports, and daily memory with proper rendering, outline, search, and tags. This is where you live when you're reading what Kevin (and your other agents) wrote. - Graph view turns the knowledge base into a visual map β concepts, projects, memory, and user facets as linked nodes. You can see what's densely connected and what's orphaned.
- Working wikilinks + backlinks for navigating between concepts, tasks, and daily memory the way Kevin wrote them.
- HTML-viewer plugins (e.g. an "HTML Reader" community plugin) let you open the generated Agent OS dashboard (
<HOME>/dashboard.html) rendered, right inside Obsidian, next to the notes it summarizes. Combined with theMARKDOWN_URLsetting (obsidian://open?path={path}), dashboard links open notes rendered in a new tab.
MarkEdit is a free, open-source, native-Mac markdown editor (think "TextEdit for Markdown"). It's fast, distraction-free, and deeply Mac-integrated: Quick Open, system Quick Look, and a live preview so you see rendered output beside the source. The markedit-preview extension adds the live HTML preview pane.
The payoff is a clean Markdown β HTML β PDF export pipeline for anything you want to look polished (a business plan, a one-pager, a report Kevin generated). I run mine through a custom panda-doc stylesheet β a CSS theme that styles the exported HTML (typography, spacing, headings, code blocks) so the resulting PDF looks designed, not dumped. Drop your own stylesheet in, export to HTML, then print/render to PDF (Kevin's browser_pdf tool can also do the HTML β PDF step with your CSS applied).
The mental model that keeps multi-agent setups sane: the agent's home is a knowledge+projects directory; your code repos live separately.
~/Documents/Agents/Kevin/ # Kevin's HOME β knowledge/, projects/, SOUL.md, etc.
# the brain. No source code here.
~/Developer/Acme/ # A forked company agent's HOME (fictitious "Acme")
βββ knowledge/ # same Kevin template, scoped to the company
βββ projects/
βββ SOUL.md / IDENTITY.md / USER.md
βββ tech/ # ALL the company's code lives under here
βββ repo-one/
βββ repo-two/
βββ worktrees/ # parallel worktrees for agents (tip #5)
The key idea: a company gets its own fork of Kevin whose HOME is the company directory (knowledge + projects scoped to that business), and a tech/ subfolder holds every repo and worktree. So the agent's brain sits one level above the code it reasons about, the company's knowledge and its source live in one tree, and you can cd ~/Developer/Acme && claude to wake the company agent or cd ~/Developer/Acme/tech/repo-one to point a coding agent at a specific repo.
VS Code's built-in git is fine for staging a quick commit, but for reviewing history, diffs, and branch topology it's cramped. Tower gives you a proper visual overview: a clear commit graph, side-by-side diffs that are actually readable, interactive rebase/stage-by-hunk, fast branch navigation, and (per tip #5) a first-class worktree manager. When you're reviewing what three agents did across three worktrees before merging, a real git client earns its keep.
- CC must open in
<HOME>for static identity to load. Outside, you only get the dynamic lane. - Sandbox can block
.claude/skills/writes during/agent-kevin:configure-skills. Pre-create the dir from a normal terminal if it hits the wall. - Playwright + macOS sandbox. Browser launch can fail inside CC's sandboxed subprocesses (XPC walls). Workaround: install playwright manually in a normal terminal so chromium caches.
- No live GUI. The Agent OS dashboard at
<HOME>/dashboard.htmlis a static snapshot regenerated on sync (orkevin dashboard), not a served app β between syncs it can drift from task frontmatter. - Single-user. Multi-user / team-isolation isn't built in. Workaround: separate homes per user.
- No proactive Kevin. See Claude Code Billing. External schedulers can run Kevin via
claude --print, but those calls bill against API quota, not your subscription.
Pull requests welcome. Particularly interested in:
- New skill packs that ship as opt-in via
configure-skills - New MCP dispatch tools that fit the read-mostly + key-gated model
- Linux / Windows platform notes
- Documentation improvements, more use-case examples
- Translations / regional compliance hints
Open an issue first for architectural changes. Kevin's contract with <HOME>/ markdown is intentional and worth preserving.
Licensed under the Apache License, Version 2.0.
agent-kevin is Β© AgentLayer Β· agentlayer.one. See NOTICE for the attribution stanza.
Third-party skill libraries installable via /agent-kevin:configure-skills are not bundled with this plugin. They install via skills.sh into <HOME>/.claude/skills/, each carrying its own LICENSE. Review each library's terms before relying commercially.
Built by AgentLayer Β· agentic infrastructure for AI-native operations
Kevin is named after the loyal minion. Helpful, enthusiastic, a little nerdy.
