Turn Claude Code into a persistent agent β memory, personality, voice, messaging, and more.
Quick Setup Β·
Why Β·
Features Β·
Skills Β·
Going further Β·
Troubleshooting Β·
Issues
Persistent agents for Claude Code as a plugin, not a harness. Memory, personality, messaging across WhatsApp, Telegram, and Discord, plus a service mode for 24/7 runs. Imports from OpenClaw.
Persistent agents for Claude Code as a plugin, not a harness. Memory, personality, messaging across WhatsApp, Telegram, and Discord, plus a service mode for 24/7 runs. Imports from OpenClaw.
Turn Claude Code into a persistent agent β memory, personality, voice, messaging, and more.
Quick Setup Β·
Why Β·
Features Β·
Skills Β·
Going further Β·
Troubleshooting Β·
Issues
ClawCode is a plugin for Claude Code. Install it and Claude Code remembers you between sessions: your name, the agent's own name and personality, the notes you and the agent wrote together last week. It adds memory with bilingual recall (Spanish β English), messaging through WhatsApp, Telegram, Discord, iMessage and Slack, a browser chat, nightly memory consolidation, and a background service for 24/7 runs. Everything lives inside Claude Code's plugin system.
The agent remembers your dog's name, warns about allergies before suggesting food, and answers in 1 to 2 lines instead of paragraphs.
Claude Code is stateless by default. Open a new session and the agent starts from zero: no memory of what you were working on yesterday, no name, no feel for who it is. Good agents should not do that. That gap is what ClawCode fills.
There are roughly two ways to build persistence on top of Claude. One is a harness: a separate runtime that wraps Claude's API with its own session, memory, and tool layer. OpenClaw is one example. Harnesses run on Claude's API directly; as of April 2026 they can no longer draw from a Claude subscription, so users need to pay for API usage separately.
ClawCode takes the other route. It extends Claude Code from inside as a plugin, so there's no separate runtime and no separate billing. A ClawCode user is just a Claude Code user with an extra layer on top. ClawCode inherits what Claude Code already does well (its harness, tool system, skills, hooks, MCP plumbing) and adds only what a persistent agent needs.
Coming from OpenClaw? /agent:import brings your agent's personality, memory, skills, and crons across.
say. STT via local Whisper or OpenAI API./status, /help, /whoami, /new, /compact work from CLI, WhatsApp, Telegram, Discord β same commands, formatting adapts per platform.owner/repo@branch#subdir. OS + dependency validation.--fix auto-repairs safe issues.1. Create a folder for your agent.
Each agent lives in its own folder. Create one and open Claude Code there:
mkdir ~/my-agent && cd ~/my-agent
claude2. Install the plugin.
Inside Claude Code, add Anthropic's official community marketplace:
/plugin marketplace add anthropics/claude-plugins-community
Then install the plugin:
/plugin install clawcode@claude-community
When prompted for scope, select "Install for you, in this repo only (local scope)" β this keeps the agent isolated to this folder.
Then reload plugins so the skills become available:
/reload-plugins
Bleeding-edge alternative. The community marketplace syncs nightly from Anthropic's review pipeline, so brand-new fixes can take up to ~24h to land. If you want the absolute latest commit, install from this repo's marketplace instead β same plugin, different identifier. Run them one at a time:
/plugin marketplace add crisandrews/ClawCode/plugin install agent@clawcode
3. Create your agent:
/agent:create
This starts the bootstrap ritual β a casual conversation where the agent discovers its name, personality, and emoji. You can also import an existing agent instead:
/agent:import
4. Reload to apply the personality:
/mcp
The agent now wakes up with its identity on every session.
ClawCode injects personality and behavior at four points in the session lifecycle:
| Hook | When | What happens |
|---|---|---|
| SessionStart | Session opens | Reads SOUL.md + IDENTITY.md + USER.md and injects them as context. Checks if heartbeat + dreaming crons exist β creates them if missing. |
| PreCompact | Context getting full | Reminds agent to save important facts to memory/YYYY-MM-DD.md before compression erases them. |
| Stop | Session closing | Reminds agent to write a session summary (what was discussed, decisions, open items). |
| SessionEnd | Session closed | Logs a session.end event for the dreaming system. |
This means:
The agent also detects your language from each message and responds in kind. Switch from Spanish to English mid-conversation β the agent switches too. Status cards, error messages, and commands all adapt.
Full details: docs/hooks.md
The agent writes to memory/YYYY-MM-DD.md during sessions and searches it automatically at the start of every turn β no need to say "search memory." Bilingual (Spanish β English, 40+ synonym pairs), date-aware ("hoy" resolves to today's date), and safety-critical (warns about allergies before suggesting food). Trivial messages (greetings, "ok", slash commands) skip the search β no wasted context.
Two backends: builtin (SQLite + FTS5, works out of the box) and QMD (local embeddings for semantic search β install with bun install -g qmd).
Full details: docs/memory.md Β· docs/memory-context.md Β· docs/qmd.md
Nightly cron (3 AM) runs 3-phase memory consolidation:
DREAMS.mdmemory/MEMORY.mdRun manually: dream(action='run') or preview with dream(action='dry-run').
Full details: docs/dreaming.md
TTS via sag, ElevenLabs, OpenAI, or macOS say. STT via local Whisper or OpenAI Whisper API. The agent auto-selects the best available backend. Enable with agent_config(action='set', key='voice.enabled', value='true').
Full details: docs/voice.md
Browser-based chat UI with real-time SSE delivery. Enable the HTTP bridge, open http://localhost:18790. Dark/light mode, conversation logging in JSONL + Markdown (same format as WhatsApp plugin).
agent_config(action='set', key='http.enabled', value='true')
/mcp
Full details: docs/webchat.md Β· docs/http-bridge.md
Reach your agent from WhatsApp, Telegram, Discord, iMessage, or Slack. Each messaging plugin is an independent MCP server β no conflicts with ClawCode.
/agent:messaging
Slash commands work from any channel β /status, /help, /whoami, /new, /compact all respond whether the user is in the CLI terminal or chatting via WhatsApp. Formatting adapts automatically (*bold* for WhatsApp, **bold** for Telegram, standard markdown for CLI).
Full details: docs/channels.md
Have an existing OpenClaw agent? /agent:import brings it into Claude Code with a step-by-step wizard (clickable options, one question at a time):
Files are copied clean β no annotations, no comments. Adaptation details go to IMPORT_BACKLOG.md so the user can revisit skipped items later. The import event is logged to memory so the agent remembers what was imported.
External systems can send events to the agent via POST /v1/webhook (requires HTTP bridge enabled). The agent queues them and processes on the next turn.
Use cases:
curl -X POST http://localhost:18790/v1/webhook \
-H "Content-Type: application/json" \
-H "Authorization: Bearer your-token" \
-d '{"event": "deploy", "status": "success", "repo": "my-app"}'Security: when the bridge is exposed to the network (host: "0.0.0.0"), a token is required β the bridge refuses to start without one.
Queue holds up to 1000 events. Drain with GET /v1/webhooks or the chat_inbox_read MCP tool.
Full details: docs/http-bridge.md
/agent:doctor runs 11 health checks: config validity, identity files, memory directory, SQLite integrity, QMD availability, bootstrap state, HTTP bridge, messaging plugins, dreaming, cron registry, jq availability. Returns a β
/--fix to auto-repair safe issues (create missing memory/, reindex SQLite, remove stale BOOTSTRAP.md).
Full details: docs/doctor.md
Reminders (heartbeat, dreaming, imports, and ad-hoc "remind me in 2h") survive session closes. ClawCode maintains a registry at memory/crons.json and reconciles it against the live harness on every SessionStart: anything missing gets recreated, anything live-but-unknown gets adopted. PostToolUse captures ad-hoc CronCreate/CronDelete automatically β you don't need a special command for "remind me".
Manage reminders through /agent:crons (aliases /agent:reminders, list reminders, recordatorios):
/agent:crons list # β
β οΈβΈ status table
/agent:crons add "0 9 * * *" "email" # add a reminder
/agent:crons delete 3 # remove with AskUserQuestion confirm
/agent:crons pause heartbeat-default # pause without deleting
/agent:crons reconcile # force sync
/agent:crons import # bring OpenClaw crons into the registry
Full details: docs/crons.md
| Skill | Description |
|---|---|
/agent:create |
Create a new agent with bootstrap ritual |
/agent:import [id] |
Import an existing agent (personality + memory + skills + crons) |
/agent:doctor [--fix] |
Diagnose agent health. --fix applies safe auto-repairs |
/agent:settings |
View/modify agent config (guided) |
/agent:skill install|list|remove |
Install community skills from GitHub |
/agent:channels |
Messaging channel status and launch command |
/agent:service install|status|uninstall|logs |
Always-on background service |
/agent:voice status|setup |
TTS / STT backends |
/agent:messaging |
Set up WhatsApp, Telegram, Discord, iMessage, Slack |
/agent:crons / /agent:reminders |
Manage reminders: list, add, delete, pause, reconcile, import |
/agent:heartbeat |
Memory consolidation and periodic checks |
/agent:update |
Check for new Claude Code / ClawCode releases and print safe update commands |
/agent:status |
Agent status dashboard |
/agent:usage |
Resource usage |
/agent:new |
Save session and prepare for /clear |
/agent:compact |
Save context before compression |
/whoami |
Sender info and agent identity |
/help |
List all available commands (dynamic) |
Install skills from GitHub:
/agent:skill install alice/pomodoro
/agent:skill install alice/skills@main#weather
/agent:skill list
/agent:skill remove pomodoro
Full details: docs/skill-manager.md
Run the agent as a background service (launchd on macOS, systemd on Linux):
/agent:service install
/agent:service status
/agent:service logs
The service defaults are tuned for 24/7 daemon use: PTY wrap so lifecycle hooks survive graceful shutdown, crash-loop guard, persistent logs under ~/.clawcode/logs/, a resume-on-restart wrapper so the agent rehydrates its last conversation after a restart, and a self-heal sidecar that recovers from stuck deferred-tool loops automatically. Full details in docs/service.md.
Optional companion: docs/watchdog.md β opt-in external health probe + auto-restart for always-on services.
Run /agent:update to check whether Claude Code or ClawCode has a newer release available. The skill compares installed versions against npm and the upstream git tags, prints the safe update commands for each, and never applies them itself. The heartbeat cron does the same check once per UTC day with per-version dedupe, so a new release pings you once and then stays quiet.
All settings in agent-config.json. Edit directly or use agent_config:
agent_config(action='get')
agent_config(action='set', key='memory.backend', value='qmd')
Non-critical settings apply live. Critical settings need /mcp β the agent tells you which.
Full details: docs/config-reload.md
Update to the latest version. Use the command set that matches how you installed. Run each line one at a time β Claude Code's slash commands don't batch.
If you installed from the community marketplace (clawcode@claude-community):
/plugin marketplace update anthropics/claude-plugins-community
/plugin update clawcode@claude-community
/reload-plugins
If you installed from this repo's marketplace (agent@clawcode):
/plugin marketplace update crisandrews/ClawCode
/plugin update agent@clawcode
/reload-plugins
If /plugin update says "already at latest version" but you know there's a new one, use the manual method: type /plugin, find your installed plugin in the list, press Enter, and select Update.
Your personality, memory, skills, and config are preserved β only the plugin code updates. No data loss.
Uninstall:
/plugin uninstall clawcode@claude-community # if installed from community marketplace
/plugin uninstall agent@clawcode # if installed from this repo's marketplace
Your agent files (SOUL.md, IDENTITY.md, memory/, skills/) stay in the folder β they're yours. Only the plugin code is removed.
Clear cache (if reinstall fails or behaves unexpectedly). The cache path depends on which marketplace you installed from. Close Claude, then in terminal:
rm -rf ~/.claude/plugins/cache/claude-community/clawcode # community marketplace install
rm -rf ~/.claude/plugins/cache/clawcode # own marketplace installReopen Claude and install again.
Each agent is its own folder with its own personality, memory, and config:
~/agent-work/ β Agent #1
~/agent-personal/ β Agent #2
Install the plugin in each folder with local scope. Switch: cd ~/other-agent && claude.
Every agent has these files in its root. They're injected as context at session start via the SessionStart hook.
| File | What it defines |
|---|---|
SOUL.md |
Core truths, boundaries, philosophy β the agent's deepest identity |
IDENTITY.md |
Name, emoji, creature type, vibe, birth date |
USER.md |
Your info: name, timezone, language, preferences |
AGENTS.md |
Operational rules, safety boundaries, local skill triggers |
TOOLS.md |
Platform-specific formatting (WhatsApp uses *bold*, Telegram uses **bold**) |
HEARTBEAT.md |
What to check every 30 min (review daily logs, consolidate memory) |
BOOTSTRAP.md |
First-run ritual (deleted after onboarding) |
The agent never says "I'm Claude" β it uses its name from IDENTITY.md. Even when asked directly "are you Claude?", it answers: "I'm [name] β built on Claude, but with my own memory, personality, and name."
~/my-agent/
βββ SOUL.md, IDENTITY.md, USER.md # Agent personality
βββ AGENTS.md, TOOLS.md, HEARTBEAT.md # Behavioral rules
βββ agent-config.json # Settings
βββ memory/
β βββ MEMORY.md # Long-term curated memory
β βββ YYYY-MM-DD.md # Daily logs (append-only)
β βββ .memory.sqlite # Search index (auto-generated)
β βββ .dreams/ # Dream tracking data
βββ .webchat/logs/conversations/ # WebChat logs (JSONL + MD)
βββ skills/ # Installed + imported skills
βββ IMPORT_BACKLOG.md # Skipped import items (if any)
Conversation logs are stored in two formats per channel:
Run /agent:doctor first β it checks everything in one shot. Add --fix to auto-repair safe issues.
:clawcode:clawcode on community installs) β Dependencies didn't install. Check Node.js v18+ (node --version). Then try manually depending on where you installed from: close Claude, run cd ~/.claude/plugins/cache/clawcode/agent/*/ && npm install (own marketplace) or cd ~/.claude/plugins/cache/claude-community/clawcode/*/ && npm install (community), then reopen Claude./mcp to reload. The SessionStart hook injects identity from SOUL.md + IDENTITY.md.agent_config(action='set', key='memory.backend', value='qmd')./mcp. The agent tells you which./agent:channels status for installed/authenticated/active status.durable: true is currently session-only in Claude Code. Crons are recreated automatically at each session start via the SessionStart hook (default heartbeat + dreaming). For 24/7, use /agent:service install./plugin update clawcode@agent stays silent for minutes β Not hung. Claude Code is downloading and installing the new version in the background; no progress indicator is shown during the fetch. Wait; a status line should appear when it's ready (can take a few minutes on the first update). Once it finishes, /plugins-reload is a good follow-up to make sure the running session picks up the new cache before the next turn./agent:service install.memory.extraPaths in config.Per-feature documentation in docs/.
Build within Claude Code's limits. Use its plugin system, its hooks, its MCP servers. Don't patch Claude Code's internals; don't disable its features from the outside. If a feature needs restraint (the in-process auto-updater during daemon mode, for example), reach for the environment variable Claude Code itself documents, not a workaround. Respect the terms of service. The platform is where the agent lives, not something to work around.
Most of v1.4.0 and v1.4.1 came from @JD2005L, running ClawCode as a 24/7 systemd service and sending back a dozen PRs of fixes, hardening, and features from the front lines: the WORKSPACE resolution fix, the service crash-loop PTY wrap, the resume-on-restart wrapper, the hardening defaults, the /agent:update skill, cross-user import discovery, the reconcile fast-path, and the self-heal sidecar. Thank you.
ClawCode is an independent, open-source project. Claude is a trademark of Anthropic, PBC. ClawCode is not affiliated with or endorsed by Anthropic.
| Version | Changes | Urgency | Date |
|---|---|---|---|
| v1.4.13 | ### Changes - Hooks/reconcile: emit a 4-line session banner at the top of every SessionStart β `=== CLAWCODE v<version> Β· MIT License ===`, docs/config link to the repo, an `/agent:doctor` tip, and a neutral issues/feedback invite. Version is read at runtime from `plugin.json` (jq with a `sed` fallback for jq-missing environments), so it never drifts from the manifest. Additive only: identity injection, the cron reconcile envelope, the `BOOTSTRAP.md` early-exit, and the jq-missing degraded path | High | 4/20/2026 |
| v1.4.12 | ### Fixes - Docs/readme: add a Troubleshooting bullet for the "my agent went silent for minutes after `/plugin update clawcode@agent`" case β it's the download running in the background with no progress indicator, not a hang. Tip: `/plugins-reload` afterwards to make the running session pick up the new cache cleanly before the next turn. Surfaced live after v1.4.11 shipped. - Skills/about: reorder the Format-per-surface section so the tail-line language rule is the first thing an agent reads, | High | 4/20/2026 |
| v1.4.11 | ### Fixes - Skills/crons: `writeback.sh upsert` refuses (exit 5) when an active entry with the same `cron`+`prompt` already exists under a different key. Kills the "hook captured the CronCreate as `harness-<id>`, agent also ran a manual `upsert` with a custom key" duplicate pattern that silently produced double-firing reminders β observed earlier today on a live WhatsApp agent. `openclaw-import` is exempt; tombstoned entries are ignored. - Hooks/cron-pretool: new `PreToolUse` hook that gates ` | High | 4/20/2026 |
| v1.4.9 | ### Fixes - Skills/release: removed `skills/release/` from the plugin distribution. It was added at plugin scope in v1.4.7-v1.4.8 by mistake β every end user of an agent (Cloudy, Wally, etc.) saw a "release" skill in their `/plugin` viewer that had nothing to do with their agent's workspace. The release flow is a maintainer-only tool and now lives at user-scope on the maintainer's own machine, not in the published plugin. Plugin manifest, end-user agent config, and runtime behavior are unchange | High | 4/19/2026 |
| v1.4.8 | ### Changes - Skills/release: adopt the release-notes format used by `openclaw/openclaw` (~360k stars) as the canonical style for ClawCode CHANGELOG entries and `gh release` bodies. Two groups only (`### Changes` / `### Fixes`), bullets prefixed with `Area/subarea:` scope, one-line narrative + outcome, optional `(#PR) Thanks @user.` suffix, link back to CHANGELOG at the end. Mirrors what readers already see on OpenClaw's releases page so the style is familiar across both projects. Concrete work | High | 4/19/2026 |
| v1.4.7 | ### Added - **`/about` and `/version` slash commands** for the agent. Surfaces a 3-line card with the plugin name, current version, and the repo URL β so users who installed via marketplace can find docs / file issues / star the project right from inside their agent on any channel (CLI, WhatsApp, Telegram, Discord, iMessage). Version is read dynamically from `plugin.json` so it never goes stale. - **`skills/release/` β the release flow as an actual skill** (not just a memory). Codifies the 4 ma | High | 4/19/2026 |
| v1.4.6 | ### Added - Plugin metadata fields (`homepage`, `repository`, `license`, `author.url`) so the `/plugin` viewer in Claude Code surfaces a link back to the repo. Without this, users who installed via marketplace had no way to find docs, file issues, or star the project from inside Claude Code. Pure metadata, no runtime behavior change. Full changelog: [CHANGELOG.md](https://github.com/crisandrews/ClawCode/blob/main/CHANGELOG.md#146--2026-04-19). | High | 4/19/2026 |
| v1.4.5 | ### Fixes - **Reminders now actually survive `/exit` + relaunch.** Three concatenated bugs in v2.1.114 silently broke the cron registry's persistence promise. The PostToolUse capture hook missed the new object-shape `tool_response`, the SessionStart reconcile fast-path skipped recreation when stale `harnessTaskId`s were present (which they always are after `/exit`, since upstream `durable: true` is still broken β confirmed live, the harness response now explicitly returns `"durable": false`), a | High | 4/19/2026 |
| v1.4.4 | ### Fixes - Plugin/manifest: drop redundant `hooks: ./hooks/hooks.json` from `plugin.json` β Claude Code β₯ 2.1.114 auto-loads the standard path and rejects the explicit declaration as a duplicate, which previously disabled every ClawCode hook on startup (SessionStart reconcile, PostToolUse cron capture, PreCompact/Stop memory prompts, SessionEnd dreams event). Line was redundant since v1.0.0, only failed once the duplicate-load guard landed. Full changelog: [CHANGELOG.md](https://github.com/cr | High | 4/19/2026 |
| v1.4.3 | ClawCode v1.4.3 closes the "silent stale code" failure mode and polishes the `/agent:create` onboarding so the ritual actually drives itself instead of leaving the user staring at an idle prompt. Thanks [@JD2005L](https://github.com/JD2005L) for the service-side stamp writer β another production find from his 24/7 deployment. ## Fixes **`/agent:create` now continues the bootstrap ritual inline.** The skill used to tell you to run `/mcp` and then stop, expecting the agent to "detect `BOOTSTRAP | High | 4/18/2026 |
| v1.4.2 | ClawCode is now available on Anthropic's official [`claude-plugins-community`](https://github.com/anthropics/claude-plugins-community) marketplace. The README now leads new users there; the existing `crisandrews/ClawCode` path stays as the bleeding-edge alternative for users who want same-day fixes (community syncs nightly, so it can lag by ~24h). No code changes in this release. Existing installs work unchanged. ## Install β new default ``` /plugin marketplace add anthropics/claude-plugins-co | High | 4/17/2026 |
| v1.4.1 | ClawCode v1.4.1 ships two hotfixes from @JD2005L's live service deployment on 2026-04-17. The resume-wrapper introduced in 1.4.0 can land back inside a stuck session and spam the log for hours without crashing; a new three-layer self-heal system catches that class of fault automatically. The cron hooks also gain a PATH prefix so `jq` installed user-local (pip --user, Homebrew under launchd, Linuxbrew) is visible to the hook regardless of how minimal the inherited PATH is. Full detail in [CHANGEL | High | 4/17/2026 |
| v1.4.0 | ClawCode v1.4.0 is a daemon-safety release built almost entirely by @JD2005L from running ClawCode 24/7 as a systemd service. Service install mode is materially safer: PTY wrap on both platforms, crash-loop guard, persistent logs, and a resume-on-restart wrapper so a service restart no longer drops the conversation. A long-standing WORKSPACE bug in `server.ts` that silently pointed memory tools at the plugin dir is also fixed. Full detail in [CHANGELOG.md](CHANGELOG.md). ## Changes - Resume-on | High | 4/17/2026 |
| v1.3.0 | ClawCode v1.3.0 is an operational reliability release for always-on services. The memory index now picks up mid-session file changes, service installs guard against the upstream bypass-dialog hang, and a new opt-in watchdog recipe catches plugin-subprocess death that systemd silently misses. ## Changes - Watchdog (optional): new `recipes/watchdog/` with 5 tiered probes β service-manager status, HTTP `/health`, `/watchdog/mcp-ping`, scoped `pgrep -P $MainPID` against expected plugins, and `/wat | High | 4/15/2026 |
| v1.2.2 | π Thanks to @JD2005L for reporting [#1](https://github.com/crisandrews/ClawCode/issues/1). Your report surfaced a silent bug that was affecting every user of this plugin. ## Fixed Reminders now survive session closes. Previously, `CronCreate(durable: true)` was effectively a no-op: crons died when the Claude Code session ended, and the marker-based workaround self-cancelled on the second session. This release introduces a registry at `memory/crons.json` that reconciles against the live harnes | Medium | 4/13/2026 |
| v1.2.1 | ### Security - Token is now **required** when HTTP bridge binds to non-localhost. Bridge refuses to start without one. - WebChat HTML requires auth when token is configured. ### Added - **Cloudflare Email Worker tutorial** β catch-all that forwards every email to your agent in real-time ([docs](docs/webhooks.md)) - **Gmail push tutorial** β Pub/Sub notifications to your agent when new emails arrive ([docs](docs/webhooks.md)) - **CHANGELOG.md** β retroactive changelog from 1.0.0 - **Self-managin | Medium | 4/13/2026 |
| v1.2.0 | ## What's new ### Bug fixes - **Fixed silent install failure** β `npm install` errors are no longer silenced. Users now see clear error messages instead of "Failed to reconnect" with no explanation. - **Faster startup** β dependencies only install if not already present (skips `npm install` on subsequent sessions). ### New features (since v1.0.0) - **Active memory** β bilingual recall (ES β EN, 40+ synonym pairs) at the start of every turn. Date-aware ("hoy" β today's date). - **Voice** β TTS | Medium | 4/13/2026 |
| v1.1.0 | ## What's new in 1.1.0 - Active memory with bilingual recall (ESβEN) - AskUserQuestion wizard for import/create flows - Clean imports (no file annotations) - Voice TTS/STT (sag, ElevenLabs, OpenAI, say, Whisper) - WebChat with JSONL+MD conversation logging - HTTP bridge with status/skills/webhook/chat endpoints - Live config (non-critical settings apply without /mcp) - Channel detector + launch command builder - Command discovery (dynamic /help) - /doctor diagnostics with --fix - Skill manager | Medium | 4/13/2026 |