How it works
Eklavya helps you understand the code Claude writes and remember the decisions behind it. Learning and memory share one local database, but have separate switches: turning questions off does not stop memory capture.
The three moving parts
| Part | Responsibility |
|---|---|
| Hooks | React to session events: load context, capture work, prompt a quiz, or check a commit. |
| MCP server | A local Node process that exposes tools to Claude. It selects concepts, stores answers, updates review schedules, and searches memory. |
| Skills and agents | Instructions that guide Claude’s teaching: write questions, assess answers, explain mistakes, and create explainer pages after a miss. |
Claude calls the server through the Model Context Protocol (MCP). Hooks open the same SQLite database directly; they do not send their reads and writes through the MCP server. The dashboard and CLI also use this local store.
From code to a question
The session-start hook is bounded: Claude Code ends a hook after 10 seconds and shows nothing of it. Recalled memory, the memory health line and the banner’s learning counts and level are therefore computed in parallel child processes that the hook stops at about seven seconds after it started (a SQLite query cannot be interrupted from inside the process, and a thread stuck in one holds the exit, so a separate process is the only thing that can be stopped). Whatever finished is shown and sent; the rest is left out for that session. The standing instruction to log concepts never depends on them.
Claude supplies the teaching; the server tracks what is due and what you have demonstrated.
- Log the work
Claude names the concepts used and links them to the code being changed. Each concept has a short name, a description and tags. When a concept Eklavya has not seen resembles ones you already have, nothing is created yet: Eklavya lists the closest matches and Claude reuses one or confirms the concept is new. Claude gives each new concept its tier and prerequisite links in the same call.
- Choose a question
A hook prompts a checkpoint. The planner selects a concept and difficulty tier.
- Answer and explain
Claude asks, assesses your answer, and explains any gap.
- Record progress
The server validates the attempt, updates mastery and review dates, and refreshes the gate.
Questions wait until the session changes code: Claude edits a tracked or new, non-ignored file in a git repository with its edit tools, in this checkout or a sibling worktree, or through a shell command that starts with cd into one, or the git working tree the session started in differs from how it was at the start, or, with delegate_work on, Claude starts a building agent. A git pull or branch switch alone does not count, and neither do files under artifacts/ or reports/. Outside any git repository, an edit tool or a shell command that changes a file in a repository below the folder it started in, which the command names or runs from, counts. Only work logged since you last came back after more than an hour away is asked about, newest first. Reading and research sessions are not quizzed (quiz.only_on_changes). Once that happens, checkpoints ask one question while work continues, with a four-minute minimum gap. Mid-task and end-of-task questions share a four-attempt session budget. cadence: "end" moves automatic questions to the end; an enforced gate can require further attempts to pass. See quiz settings and grading for the exceptions and scoring rules.
A concept name is 1 to 3 words. Its description holds up to 400 characters and it carries up to five tags of up to 24 characters each. A new concept’s domain is its first tag. When a session meets a concept again, its tags grow and a description Claude wrote earlier can be refined. Descriptions from the built-in graph or a pack are not rewritten.
Delegated agents can log concepts, but questions return to the main conversation. This keeps a quiz out of a background transcript you cannot answer. With delegate_work on (the default), Claude is asked to use that split on purpose: a background agent builds a multi-file change in the task’s directory (your worktree, if there is one), and Claude asks you questions while it builds, then reviews, checks and commits. Eklavya says this next to each task-sized prompt, and reminds Claude once if it changes a second file in the main conversation itself, with an edit tool or a shell command. Once Claude has started a building agent, the reminder stays quiet. Whichever way the work runs, any end-of-task questions (one under as-you-go, the remaining budget under end) come after Claude’s answer, and Claude then restates the answer in a few lines under “Back to your task:”, so the answer about your task is the last thing on screen. The first-session walkthrough shows what you see as a developer.
Questions explain the names they use so you can answer without reading the code first. Each question has four options and an Other answer for your own words. Options and their notes should have similar lengths and give no hints. A lopsided question is sent back once for a rewrite before you see it. A question that lacks needed context is set aside without grading you. Grading covers the 0–5 scale and the multiple-choice cap of 4. Levels and tiers explains how questions progress from recall to design decisions, and how a project earns a harder level.
Where the question appears
The planner chooses how a question is shown. The experimental side panel (presentation: "panel") is on by default when a supported Claude Code panel is showing. If it is off or unavailable, the planner uses Claude’s question card ("tool"). In the card flow Claude asks, waits, records your answer and gives the verdict. In the panel flow Claude writes the question and four graded options, stores it with present_question and goes back to work; the panel shows it, sends your answer to the server and records it once. Hooks, the planner and the skills all read the same presentation field. See Your first session.
After a missed question
The page teaches the answer; the dashboard lets you pick it, and the server decides what that pick is worth.
- Record the miss
record_attempt stores your answer, the right option and the note under each option, and returns the attempt id.
- Write the explainer
A background agent writes a page on the concept, linked to that attempt id.
- Open it in the dashboard
With the background dashboard running, the page opens as a dashboard tab, with a Correct your answer bar when the right option was recorded.
- Correct it
Each pick is checked on the server. Only the right one is recorded as an answer, a grade-3 pass.
This needs explain_on_wrong on (the default), the background dashboard, and a question recorded with its right option; otherwise the page opens as a file or has no button. A correction updates the concept’s score and counts the miss as right in your accuracy and toward your level. It does not count toward a commit gate, and the concept still comes back for review, because picking the answer right after reading it is recognition rather than recall. Grading has the details.
From work to useful memory
Recording work is evidence of what happened. Only an answered question is evidence of understanding.
- Capture
Hooks collect prompts and tool activity, subject to your capture settings and privacy filters.
- Summarize
The observer model turns events into observations. A local summariser runs if no observer is set.
- Index
Observations and summaries enter the local keyword and vector search indexes.
- Recall
Relevant history becomes context for Claude at the next session or prompt.
Raw events, observations, and answers live in ~/.eklavya/knowledge.db by default. Recall is limited to the current project unless you enable cross-project retrieval. See memory for capture controls, search, collections, code indexing, and optional integrations, or your data for storage and backup.
Recalled text becomes part of the Claude conversation. New installs also send captured evidence to claude-sonnet-5 for memory summaries and prompt feedback, through your Claude Code login. Notifications and sync are optional and use the services or folders you configure. Installation and update checks contact the package registry. The daily usage ping sends anonymous counts to Google Analytics unless you turn it off.
Prompt feedback
A review happens after a session, in the background, one item at a time. Nothing waits on it.
- Record
Memory already keeps your prompts, redacted. Feedback needs memory on.
- Wait
A session counts once it has been quiet for 30 minutes and began within 14 days.
- Review
At the next session start, a background process asks your observer model which prompt cost the most rework, or left the most to guess, and how to improve it.
- Acknowledge
You read it and press Acknowledge, or delete it. Only then can the next one be made.
With feedback.enabled on, the next session start launches eklavya feedback generate --background as a detached process, at most every 30 minutes, when memory is on, an observer model is set and no item is waiting. A hook never waits for it, and never runs it inline, because a hook may not wait on a model. It picks the oldest session of the current project that nothing has reviewed, skips prompts under 25 characters and Eklavya’s own slash commands, looks at up to five sessions in one run, and sends the model up to eight of that session’s prompts, each cut to 1,500 characters. Your later prompts are the evidence: a follow-up that corrects or adds something (“no, it’s in auth.ts”, “don’t touch the schema”) shows what an earlier prompt left out and cost you a turn. The model chooses the prompt whose follow-ups show the most rework, or, when nothing was corrected, the one that left the agent the most to guess. It names up to three gaps (outcome, context, scope or check), says for each of the four areas whether the prompt made it clear, left it out or did not need it for this task (an area it names as a gap is always left out), and rewrites the prompt so the follow-ups would not have been needed, using details you gave later. A gap may quote the later prompt that supplied it; a quote that does not appear in a later prompt, or runs to 15 words or more, is dropped before you see it.
What leaves your machine is the text of those prompts, already redacted when memory captured them, sent to the model named in providers.observer through claude -p on your own Claude subscription, as session evidence is for memory. With no observer set, no prompt text leaves for this feature and nothing is generated. New installs use claude-sonnet-5 for both memory summaries and prompt feedback without a settings walkthrough. Existing installs keep their choices. Older configs keep the previous defaults for these settings: no observer model and feedback off, unless explicitly set. A login, quota, busy-service or missing-claude problem leaves the session unreviewed to try again later; a malformed answer marks the session as failed once. There are no scores, no MCP tool a coding session could call to write feedback, and no path from feedback to mastery.
The result waits on the dashboard’s Feedback page, in the greeting as Feedback waiting and on a badge. Setting quiet hides only the greeting line.
The runtime, end to end
The interactive architecture view provides a broader component map. The smaller flows above explain the two everyday paths.
Still picture
Open interactive viewRuntime requirements
Eklavya requires Node.js 22 or newer. Its SQLite driver, better-sqlite3, includes native code, so installation also needs a compatible binary or the platform’s build tools. Start with the installation guide; use troubleshooting if the driver fails to load.
Git is optional for ordinary learning and memory. Without a repository, difficulty uses a shared fallback scope and there is no commit to gate. The optional terminal Git gate additionally needs a POSIX shell, jq, and the sqlite3 command-line tool; the Claude Code hooks do not.