MCP Servers
egc-memory
Persistent cross-session memory for AI coding tools. The one you'll use every session.
Overview
egc-memory is a local MCP server that stores project state in a SQLite database at ~/.egc/state/. The AI reads it at the start of each session and writes to it at the end.
State is stored per project branch as Markdown files encrypted at rest (AES-256-GCM). The memory server and session hooks decrypt them transparently; nothing ever leaves your machine.
Tools
get_project_state get_project_state() Returns server health metadata: storage engine (sqlite-wal) and write arbitration mode (MessageQueue). Use this to verify the egc-memory server is running and responsive before calling get_state or update_state.
Returns: JSON with { status, engine, arbitration }.
get_state get_state({ project_path?: string }) Reads the state file for the current project. State is scoped to the current git branch when the project is a git repository, falling back to the default branch state and then to the legacy flat state file. Call this at the start of every session to restore context.
Returns: Markdown string with project context, active decisions, preferences, and next steps.
update_state update_state({ project_path?: string, context?: string, decisions?: { what: string, why?: string }[], avoid?: { what: string, why?: string }[], preferences?: string[], next?: string[] }) Saves this session's decisions and preferences. Writes to the state file of the current git branch when the project is a git repository. Merges with existing state and does not erase previous memory. Only include fields that changed this session. Also propagates the updated context to all EGC-managed tool config files found in the project (Cursor, Copilot, Gemini CLI, Windsurf, Trae, Zed, Cline, Aider, .cursorrules, AGENTS.md, llms.txt) so every tool stays in sync.
Returns: Confirmation string with the updated state file path.
store_decision store_decision({ context: string, decision: string }) Persists a single decision to SQLite with write-lock arbitration. Provide a short context label and the decision text. Queryable via query_history and surfaced in get_state.
Returns: Confirmation string.
query_history query_history({ limit?: number, offset?: number }) Returns a paginated list of past decisions stored in SQLite. Each entry includes the decision text, context label, and timestamp. Use limit and offset for pagination.
Returns: Array of decision records with timestamps and context labels.
search_history search_history({ query: string, limit?: number, min_score?: number }) Full-text search over stored decisions using FTS5 with BM25 ranking. Returns results ordered by relevance rather than recency. min_score filters by normalized relevance (0 to 1).
Returns: Array of matching decisions ranked by relevance score.
working_memory_set working_memory_set({ project_path?: string, key: string, value: string, ttl_seconds?: number }) Stores a transient key-value entry scoped to the current project with an optional TTL. Entries expire automatically so working memory does not accumulate stale data across sessions. Default TTL is 86400s.
Returns: Confirmation with the stored key and TTL.
working_memory_get working_memory_get({ project_path?: string, key: string }) Retrieves a single transient entry by key for the current project. Returns null if the key does not exist or has expired.
Returns: The stored value string with expires_at, or null.
working_memory_list working_memory_list({ project_path?: string }) Lists all live transient entries for the current project, ordered by key. Expired entries are excluded.
Returns: Array of live entries with key, value, and expires_at.
lesson_save lesson_save({ content: string, context: string, tags?: string, initial_confidence?: number }) Persists a new lesson learned during this session. Lessons are stored with a confidence score that decays over time when not reinforced. Use this to record patterns, rules, or observations the AI should remember across sessions.
Returns: Stored lesson object with ID, content, context, and initial confidence.
lesson_recall lesson_recall({ query: string, min_confidence?: number, limit?: number }) Searches active lessons above a confidence threshold. Filters by keyword across content, context, and tags. Lessons below 0.2 confidence are archived and not returned by default. Updates last_recalled timestamp on matched lessons.
Returns: Array of lesson records ordered by confidence descending.
lesson_reinforce lesson_reinforce({ id: string }) Reinforces an existing lesson when the same pattern is observed again. Increases confidence by 0.15, capped at 1.0. Unarchives lessons that had decayed below the threshold. Call this when a previously stored lesson proves relevant or a mistake is repeated.
Returns: Updated lesson object with the new confidence score.
detect_patterns detect_patterns({ window_days?: number, min_occurrences?: number }) Analyzes runtime events recorded by hooks to surface repeated commands and recurring errors across sessions. Helps identify automation candidates and structural issues.
Returns: Object with patterns array and metadata about the analysis window.
compress_observations compress_observations({ project_path?: string, since?: string, limit?: number }) Compresses raw hook observations into structured typed summaries (tool_failure, tool_success, file_edit, etc.) using rule-based analysis. Reduces token usage when injecting context into new sessions.
Returns: Object with count of compressed items and a summary of what was processed.
session_announce session_announce({ project_path?: string, territory?: string }) Registers this session on the session bus so parallel sessions can see each other. Doubles as a heartbeat; dead sessions are swept automatically after 10 minutes.
Returns: Object with the session id and the list of live peers.
session_peers session_peers({ project_path?: string }) Lists the other live sessions working on the same project, with their announced territories. Check it before picking work in parallel setups.
Returns: Array of peer sessions with territory and last heartbeat.
claim_path claim_path({ path: string }) Takes a cooperative, fail-fast lock on a file or directory before editing shared ground. A refused claim means another live session holds it: coordinate or work elsewhere.
Returns: Object confirming the claim or naming the session that holds it.
release_path release_path({ path: string }) Releases a previously claimed path so other sessions can take it.
Returns: Confirmation of the release.
State file format
State files live at ~/.egc/state/<project-slug>/<branch>.md, one per project branch (flat <project-slug>.md files from older versions are still read). The slug is derived from the absolute path of the project directory, and files are encrypted at rest with the key at ~/.egc/encryption.key.
# Project State
project: /home/user/Projetos/my-app
updated: 2026-06-05T01:00:00.000Z
## Context
Next.js 15 app with PostgreSQL and row-level security.
Auth uses sessions via iron-session, not JWT.
## Active Decisions
- Drizzle ORM over Prisma: better TypeScript inference, lighter
- No client components unless strictly needed
## Avoid
- Prisma: tried it, generated types were too verbose
- JWT: dropped after audit flagged refresh token storage
## Preferences
- Terse responses, no summaries
- Functional components only
## Next
- Add RLS policies to the projects table
- Wire up the invite flow Session protocol
The cognitive bootstrap injected by the installer writes this protocol into every tool's global instruction file. For Claude Code, the installer also registers a SessionStart hook that calls get_state automatically when a session opens, and a Stop hook that calls update_state automatically when a session ends. For other tools, the AI is instructed to run the protocol via the global instruction file.
get_state({}) AI reads project state and picks up where the last session ended.
update_state({
context: "...",
decisions: [...],
next: [...]
}) AI saves decisions, what to avoid, preferences, and next steps.