# <a href="../README.md"><img src="https://raw.githubusercontent.com/skynetcmd/m3-memory/main/docs/icon.svg" height="60" style="vertical-align: baseline; margin-bottom: -15px;"></a> M3 Memory — Quick Start

Get persistent memory running with your MCP agent in under five minutes.

This is the generic quick start. For OS-specific walkthroughs see
[QUICKSTART_LINUX.md](./QUICKSTART_LINUX.md),
[QUICKSTART_MACOS.md](./QUICKSTART_MACOS.md), and
[QUICKSTART_WINDOWS.md](./QUICKSTART_WINDOWS.md).

---

## 1️⃣ Install M3 Memory

### Easiest path — one-line installer (Linux + macOS)

```bash
curl -fsSL https://raw.githubusercontent.com/skynetcmd/m3-memory/main/install.sh | bash
```

Detects your distro, installs prerequisites (`pipx`, `git`, `sqlite3`)
via your package manager, runs `pipx install m3-memory`, then drives the
**one-command wizard** (`m3 setup`) which installs the system payload,
the sovereign CPU embedder (bundled — no LM Studio / Ollama / GPU
required), per-agent MCP wiring, chatlog hooks, and runs a final
`m3 doctor`. Refuses to run as root; sudo only for OS package install.

### Claude Code users — install as a plugin

```
/plugin marketplace add skynetcmd/m3-memory
/plugin install m3@skynetcmd
```

15 `/m3:*` slash commands (`/m3:health`, `/m3:search`, `/m3:save`,
`/m3:status`, …), the `m3:curate-memory` and `m3:curate-chatlog` subagents,
and auto-wired Stop + PreCompact chatlog hooks. See
[claude_code_plugin.md](./claude_code_plugin.md) for the full reference.

### Windows

```powershell
winget install -e --id Python.Python.3.12 Git.Git SQLite.SQLite
pip install m3-memory
m3 setup
```

If `pip install --user` puts the `m3.exe` shim somewhere not on PATH,
see the [Windows install gotchas](./install_windows.md#common-gotchas).

### Manual / older Linux / pip route

```bash
pip install m3-memory
m3 setup
```

`m3 setup` is the recommended path — interactive wizard, sensible
defaults. Power users can still run individual steps with `m3 install-m3`,
`m3 embedder install`, `m3 chatlog init`, etc. — see `m3 --help`.
Upgrade path: `pip install -U m3-memory && m3 update`.

> **Tool catalog stays small in your context.** m3 ships 87 MCP tools but
> groups them into 8 domains (memory, chatlog, files, entity, agent, tasks,
> conversations, admin). Only ~6 essentials load at MCP startup
> (~2,400 tokens vs ~16,100 if all 87 loaded eagerly). The agent pulls in
> a domain on demand — just say "load the files tools" and it does. Set
> `M3_TOOLS_LAZY=0` to disable.

### claude.ai (web/desktop) integration

```bash
m3 serve --host 127.0.0.1 --port 8080
```

Then expose `127.0.0.1:8080/mcp` via Cloudflare Tunnel / Tailscale Funnel /
ngrok / a reverse proxy and paste the URL into claude.ai's connector
settings. Full self-host walkthrough at
[claude_ai_connector.md](./claude_ai_connector.md).

### Already have the repo cloned?

If you cloned `m3-memory` and did `pip install -e .`, everything works
without further action — the CLI auto-detects a sibling
`bin/memory_bridge.py` via its package path and uses that.

---

## 2️⃣ The embedder is already set up

`m3 setup` installed the sovereign CPU embedder (BGE-M3, runs as a small
always-on service via the m3-core-rs `oxidation` extra). No LM Studio,
no Ollama, no GPU, no internet required for embedding to work.

For ~10–50× faster embeddings, the wizard offers an opt-in GPU build
(CUDA / Vulkan / Metal autodetected). You can add it later with
`m3 embedder install-gpu`.

### Optional: load a small chat model for enrichment

Some features — `auto_classify`, conversation summaries, write-time
enrichment — call your local LLM with short prompts. M3 picks up any
OpenAI-compatible endpoint via `LLM_ENDPOINTS_CSV`; no extra config
needed once a server is running.

Pick whichever fits your hardware and runtime:

| Runtime | Example small model | Size |
|---|---|---|
| **Ollama** | `ollama pull qwen2.5:0.5b` or `ollama pull llama3.2:1b` | ~400 MB / ~1.3 GB |
| **LM Studio** | Qwen2.5-0.5B-Instruct (GGUF, Q8) | ~500 MB |
| **llama.cpp** | `llama-server -m qwen2.5-0.5b-instruct-q8_0.gguf` | ~500 MB |
| **vLLM / LocalAI** | Any HF-compatible 0.5B–1B instruct model | varies |

M3 picks the largest loaded chat model for enrichment. If you only want
embedding-based memory, skip this — those features simply become no-ops.

---

## 3️⃣ Configure your agent

`m3 setup` wires every agent it detects on PATH. If you skipped the
wizard or add an agent later, here's the manual recipe per agent.

**Claude Code** — the [plugin route](./claude_code_plugin.md) is
recommended. Manual:

```bash
claude mcp add memory m3
```

Or edit `~/.claude/settings.json`:
```json
{
  "mcpServers": {
    "memory": { "command": "m3" }
  }
}
```

**Gemini CLI** (`~/.gemini/settings.json`):
```json
{
  "mcpServers": {
    "memory": { "command": "m3" }
  }
}
```

**OpenCode** (`opencode.json` in project root or `~/.config/opencode/`):
```json
{
  "$schema": "https://opencode.ai/config.json",
  "mcp": {
    "memory": {
      "type": "local",
      "command": ["m3"],
      "enabled": true
    }
  }
}
```

Restart your agent after saving the config.

---

### Agents without native MCP support

Aider and OpenClaw can't speak MCP directly. Route them through the
bundled [`mcp_proxy`](../bin/mcp_proxy.py) — an OpenAI-compatible server
on `localhost:9000` that injects m3-memory tools into every request and
executes `tool_calls` by calling bridge functions directly.

**High-level flow:** agent → `localhost:9000/v1` (OpenAI-compatible) →
proxy injects tools → real model provider (Anthropic / Google / xAI) →
model emits `tool_calls` → proxy executes them against m3-memory →
results fed back → final answer returned to agent.

The proxy routes by model name: `claude-*` → Anthropic, `gemini-*` →
Google AI, `grok-*` → xAI, `sonar-*` → Perplexity. Set
`MCP_PROXY_ALLOW_DESTRUCTIVE=1` to expose `memory_delete`, `gdpr_*`,
`*_export` etc. (off by default).

#### Starting the proxy

**Foreground (development):**
```bash
python bin/mcp_proxy.py
# or:
bash bin/start_mcp_proxy.sh           # POSIX only — prints URL and tails stdout
```

**Background (daily use):**
```bash
bash bin/start_mcp_proxy.sh --background
# writes PID to   ${TMPDIR:-~/.cache}/mcp_proxy.pid
# writes logs to  ${TMPDIR:-~/.cache}/mcp_proxy.log
# stop:           kill $(cat ~/.cache/mcp_proxy.pid)
```

**Windows native (no WSL):**
```powershell
Start-Process -WindowStyle Hidden `
  -FilePath "C:\Users\<you>\m3-memory\.venv\Scripts\python.exe" `
  -ArgumentList "bin\mcp_proxy.py" `
  -WorkingDirectory "C:\Users\<you>\m3-memory" `
  -RedirectStandardOutput "$env:TEMP\mcp_proxy.log" `
  -RedirectStandardError  "$env:TEMP\mcp_proxy.err"
```

**Boot-time autostart:**
- Linux: systemd user unit running `python bin/mcp_proxy.py` with `Restart=on-failure`
- macOS: launchd `~/Library/LaunchAgents/ai.m3-memory.mcp-proxy.plist` with `KeepAlive` + `RunAtLoad`
- Windows: Task Scheduler `At log on` → `python.exe bin\mcp_proxy.py`, or NSSM for a real service

**Health check:** `curl -sf http://localhost:9000/v1/models && echo "proxy OK"`

> **Important:** Aider / OpenClaw will fail to reach a model if the proxy
> isn't running — their `OPENAI_BASE_URL` points at `localhost:9000`. Start
> the proxy before launching those agents, or use one of the autostart
> options above.

#### Aider

```yaml
# ~/.aider.conf.yml
openai-api-base: http://localhost:9000/v1
```

Export the API key for whichever upstream you're routing to
(`ANTHROPIC_API_KEY`, `OPENAI_API_KEY`, `XAI_API_KEY`, `GEMINI_API_KEY`).
The proxy forwards the key to the provider matching the model prefix.

Keep `CONVENTIONS.md` at the repo root pointing at `AGENT_INSTRUCTIONS.md`
so Aider gets the "always use memory_search first" rules in its system
prompt — without that, the tools are available but unused.

#### OpenClaw

Edit `~/.openclaw/openclaw.json`'s `env` block:
```json
"env": {
  "OPENAI_API_KEY": "sk-...existing...",
  "OPENAI_BASE_URL": "http://localhost:9000/v1"
}
```

Back up first: `cp ~/.openclaw/openclaw.json ~/.openclaw/openclaw.json.bak`

Seed the system prompt via OpenClaw's `hooks.internal.entries.boot-md`
(enabled by default) — tell the model to call `memory_search` before
answering and `memory_write` after learning anything important. Without
that instruction the tools are available but the model won't know to use
them.

OpenClaw's own `session-memory` hook can stay enabled in parallel, or
disable it with `hooks.internal.entries.session-memory.enabled = false`
to make m3-memory the sole store. Caveat: when the proxy is down,
OpenClaw's chat completions will fail.

#### Migrating existing flat-file memory

If you already have memories in Claude Code flat files, `GEMINI.md`'s
added-memories section, or OpenClaw's SQLite, use
[`bin/migrate_flat_memory.py`](../bin/migrate_flat_memory.py). Idempotent
(safe to re-run), SHA-256 round-trip verified, never deletes source files
itself.

```bash
python bin/migrate_flat_memory.py --dry-run                    # preview
python bin/migrate_flat_memory.py                              # migrate + verify
python bin/migrate_flat_memory.py --sources claude,gemini      # subset
python bin/migrate_flat_memory.py --include-rules              # also import CLAUDE.md etc.
```

### Disable your host agent's built-in memory

- **Claude Code** has a built-in flat-file memory at
  `~/.claude/projects/<project>/memory/`. This project's
  [AGENT_INSTRUCTIONS.md](./AGENT_INSTRUCTIONS.md) already instructs
  Claude to ignore it; migrate any existing flat-file memories with the
  script above, then delete the flat files.
- **Gemini CLI, Aider, OpenCode** — no built-in memory to disable. They
  pick up `GEMINI.md` / `CONVENTIONS.md` / `AGENTS.md` respectively (all
  shims pointing at `AGENT_INSTRUCTIONS.md`).

---

## 4️⃣ Verify it works

In your agent session, write a test memory:

```
Write a memory: "M3 Memory installed successfully"
```

Your agent should call `memory_write` and return a UUID. That confirms
the MCP bridge is connected, SQLite is working, and embeddings are being
generated.

Now open a **new session** and search for it:

```
Search for: "M3 install"
```

If the memory you wrote comes back, everything is working.

### What success looks like

- `memory_write` returns a UUID (e.g., `Created: a1b2c3d4-...`)
- `memory_search` returns the memory you wrote, with a relevance score
- No errors about embedding failures or connection refused

### What failure looks like

| Symptom | Cause | Fix |
|---------|-------|-----|
| "Embedding failed" or "Connection refused" | Sovereign CPU embedder not running | `m3 embedder status`; if not running, `m3 embedder start` (or `m3 embedder install` first time) |
| "m3: command not found" | Package not on PATH | `pip install m3-memory` and check `which m3` (`mcp-memory` is the backwards-compatible alias) |
| Memory tools don't appear in agent | Config not loaded | Check JSON syntax, ensure `"mcpServers"` key, restart agent fully |
| Search returns nothing in new session | Different working directory | Run from same directory, or set `M3_MEMORY_ROOT` env var |

---

## 5️⃣ Optional: cross-device sync

M3 Memory works standalone with local SQLite — no additional
infrastructure needed. For multi-device sync, you can optionally connect:

- **PostgreSQL** — bi-directional delta sync across machines
- **ChromaDB** — federated vector search across your LAN

See [ENVIRONMENT_VARIABLES.md](./ENVIRONMENT_VARIABLES.md) for `PG_URL`
and `CHROMA_BASE_URL` configuration.

---

## ▶️ Next steps

- [CORE_FEATURES.md](./CORE_FEATURES.md) — what M3 Memory can do
- [AGENT_INSTRUCTIONS.md](./AGENT_INSTRUCTIONS.md) — all MCP tools and agent behavioral rules
- [TECHNICAL_DETAILS.md](./TECHNICAL_DETAILS.md) — search internals, schema, sync, security
- [ENVIRONMENT_VARIABLES.md](./ENVIRONMENT_VARIABLES.md) — credentials and runtime config
