Unified coding-agent session memory for Pi, Factory Droid, OpenCode, Claude Code, Amp, and Codex, plus separate local-document indexing/search in the same SQLite database.
Tired of hunting through multiple agent transcript formats and folders? Remi gives you one searchable memory layer.
Remi ingests local agent transcripts into one SQLite database, keeps sync state with checkpoints, supports ranked session search, lets you index local documentation roots for separate docs search, and provides safe archive/restore workflows.
Current support status: Linux-first (default source discovery paths are validated on Linux).
- What Remi does
- Demo
- Quickstart
- Install / build
- Data locations
- Supported agent sources
- CLI reference
- Semantic search (optional feature)
- End-to-end workflow examples
- Helper scripts (examples)
- Architecture at a glance
- Release artifacts
- Homebrew (optional)
- License
- Incremental sync from multiple coding-agent sources.
- Deterministic IDs (
blake3) for idempotent upserts. - Checkpointed ingestion using a composite cursor (
timestamp + source_id) to avoid missing same-timestamp records. - Structured content normalization including tool-call/tool-result payloads into searchable text.
- Separate local docs indexing for user-selected directories, stored in the same SQLite DB as sessions.
- Lexical search using SQLite FTS5 + BM25.
- Ranking fusion with recency via Reciprocal Rank Fusion (RRF).
- Substring fallback when lexical matches are empty.
- Two-layer search UX: ranked session list first, then export selected session to HTML/Markdown (or emit JSON).
- Dedicated docs search UX: query indexed docs directly without mixing them into session search results.
- Archive planning/execution/restore with dry-run defaults and verification before optional deletion.
Full CLI demo (55s):
remi init && remi sync --agent all && remi search query "panic"
remi docs index --root ~/docs && remi docs search "retry budget"If remi is not on your path yet, run from source:
cargo run -p cli -- init
cargo run -p cli -- sync --agent all
cargo run -p cli -- search query "panic"
cargo run -p cli -- docs index --root ~/docs
cargo run -p cli -- docs search "retry budget"cargo install --path crates/clicargo install --git https://github.com/lsj5031/Remi --bin remicargo build --workspacecargo run -p cli -- --helpDefault paths on Linux (via dirs crate):
- Database:
~/.local/share/remi/remi.db - Search exports (HTML/Markdown default output):
~/.local/share/remi/exports/ - Archive bundles:
~/.local/share/remi/archive/<run_id>/
The same database stores both synced sessions and indexed local docs. Docs roots are user-selected via remi docs index --root <PATH> rather than auto-discovered.
macOS and Windows builds are available in releases, but default agent source discovery paths are currently Linux-oriented.
Remi currently discovers and ingests from:
| Agent | Paths scanned |
|---|---|
| Pi | ~/.pi/agent/sessions/**/*.jsonl, ~/.pi/sessions/**/*.jsonl |
| Factory Droid | ~/.factory/sessions/**/*.jsonl, ~/.local/share/factory-droid/sessions/**/*.jsonl |
| OpenCode | ~/.local/share/opencode/opencode.db (preferred) or legacy ~/.local/share/opencode/storage/message/**/*.json (+ part text from ~/.local/share/opencode/storage/part/<message_id>/*.json; session metadata from ~/.local/share/opencode/storage/session/**/*.json) |
| Claude Code | ~/.claude/transcripts/**/*.jsonl, ~/.claude/projects/**/*.jsonl, ~/.local/share/claude-code/**/*.jsonl |
| Amp | ~/.local/share/amp/threads/**/*.json |
| Codex | ~/.codex/sessions/**/*.jsonl |
Top-level commands:
remi init
remi sync --agent <pi|droid|opencode|claude|amp|codex|all>
remi docs <index|search>
remi sessions <list|show>
remi search query <QUERY> [options]
remi archive <plan|run|restore>
remi doctor
If built with --features semantic, Remi also supports:
remi embed --rebuild- Global flags:
remi --ort-dylib-path <PATH> ...andremi --auto-ort ...
Initializes/open database schema (schema is also initialized automatically by other commands).
remi initSync a specific adapter or all adapters:
remi sync --agent pi
remi sync --agent droid
remi sync --agent opencode
remi sync --agent claude
remi sync --agent amp
remi sync --agent codex
remi sync --agent allBehavior:
- Discovers source files.
- Scans only records after the last checkpoint.
- Normalizes to canonical sessions/messages/provenance.
- Upserts into SQLite + refreshes FTS rows for touched sessions.
- Updates checkpoint cursor.
Usage:
remi docs index --root <PATH>
remi docs search [OPTIONS] <QUERY>docs index indexes one local directory root at a time. You can rerun it for the same root to refresh incrementally, or run it again with another root to add more docs roots to the same DB.
Supported document file types:
.md.markdown.txt.rst
Indexing behavior:
- canonicalizes the requested root path before storing it
- skips hidden files/directories
- skips symlinks
- skips unreadable or non-UTF-8 files
- updates changed files in place
- treats rename/delete as reconciliation on the next successful re-index
Example:
remi docs index --root ~/notes/project-docsTypical output:
root=/home/alice/notes/project-docs
indexed=42
updated=3
skipped=5
deleted=1
errors=0
docs search searches only indexed docs; it does not mix docs into remi search query session results.
Options:
--raw-fts--limit <N>(default:20)
Examples:
remi docs search "retry budget"
remi docs search "fts5 NEAR tokenizer" --raw-fts --limit 10Output includes the doc title, relative path, and a content snippet for each hit.
List sessions:
remi sessions listShow one session’s messages:
remi sessions show <session_id>Example:
remi sessions show 0d5f0e...c9aUsage:
remi search query [OPTIONS] <QUERY>Options:
--format <html|markdown|json>(default:html)--no-interactive--select <auto|index>(default:auto)--index <N>(required when--select indexin non-interactive mode)--agent <STRING>--title <STRING>--id <STRING>--contains <STRING>--raw-fts--html-safety <strict|relaxed|trusted>(default:relaxed)--output-dir <PATH>
remi search query "retry logic"Flow:
- Remi ranks matching sessions.
- You can type an optional fuzzy filter.
- You choose an index.
- Remi exports selected session (HTML by default) and prints the file path.
Interactive fuzzy filter supports field prefixes:
agent:claude title:auth contains:oauth refresh token
Supported fuzzy fields:
agent:title:id:contains:
Auto-select top result, export Markdown:
remi search query "panic on startup" \
--no-interactive \
--select auto \
--format markdownSelect exact ranked session index:
remi search query "sql migration" \
--no-interactive \
--select index \
--index 2 \
--format html \
--output-dir ./exportsEmit JSON instead of writing HTML/Markdown:
remi search query "cache invalidation" \
--no-interactive \
--select auto \
--format jsonFilter sessions before selection:
remi search query "build failure" \
--no-interactive \
--agent droid \
--title release \
--contains linkerremi archive plan --older-than 30d --keep-latest 5--older-thanuses human duration parsing (examples:30d,12h,90m)--keep-latestis applied per agent- Output format includes:
plan <run_id>
remi archive run --plan <run_id>Equivalent explicit dry-run:
remi archive run --plan <run_id> --dry-runremi archive run --plan <run_id> --executeThis writes:
~/.local/share/remi/archive/<run_id>/sessions.json~/.local/share/remi/archive/<run_id>/manifest.json
Remi verifies the bundle checksum after writing before allowing deletion.
remi archive run --plan <run_id> --execute --delete-sourceFlag precedence:
- Writes/deletes only occur when
--executeis set. - If both
--executeand--dry-runare passed,--dry-runwins and execution is suppressed.
remi archive restore --bundle ~/.local/share/remi/archive/<run_id>/sessions.jsonRun integrity checks and basic stats:
remi doctorCurrent output includes:
- SQLite
PRAGMA integrity_checkresult - total session count
Semantic support is feature-gated at compile time.
cargo build -p cli --features semanticWhen built with semantic, additional CLI surface is enabled:
- Global flags on
remi:--ort-dylib-path <PATH>--auto-ort
remi embed --rebuildremi search query ... --semantic <auto|on|off>
~/.config/remi/config.toml:
[semantic]
enabled = true
model_path = "/path/to/bge-small-en-v1.5"
pooling = "cls" # or "mean"
query_prefix = "Represent this sentence for searching relevant passages: "Model directory must contain:
model.onnxtokenizer.json
If model_path is not set, Remi checks:
<binary_dir>/models/bge-small-en-v1.5<binary_dir>/model~/.cache/remi/bge-small-en-v1.5
Rebuild embeddings:
remi embed --rebuildSearch with semantic mode:
remi search query "memoization strategy" --semantic auto
remi search query "memoization strategy" --semantic on
remi search query "memoization strategy" --semantic offSet ONNX Runtime path explicitly:
remi --ort-dylib-path /opt/onnx/libonnxruntime.so search query "vector index" --semantic onAuto-detect ONNX Runtime shared library:
remi --auto-ort search query "vector index" --semantic autoremi init
remi sync --agent all
remi sessions listThen inspect a session:
remi sessions show <session_id>remi search query "panic: index out of bounds" --format markdownOpen the emitted .md export path and review the full conversation.
remi search query "release tagging" --no-interactive --format json --select auto# plan
remi archive plan --older-than 60d --keep-latest 10
# inspect impact
remi archive run --plan <run_id>
# execute archive without deletion
remi archive run --plan <run_id> --execute
# optional deletion after validation
remi archive run --plan <run_id> --execute --delete-sourceRestore when needed:
remi archive restore --bundle ~/.local/share/remi/archive/<run_id>/sessions.jsonremi docs index --root ~/docs/remi-notes
remi docs search "retry budget"If you rename or remove files under the indexed root, rerun:
remi docs index --root ~/docs/remi-notesand Remi will reconcile deleted/renamed paths before the next docs search.
This repo includes helper scripts in scripts/:
scripts/remi-diary.sh— generate a daily Markdown summary fromremi.db, with optional Telegram send.scripts/markie-export.sh— render Markdown to SVG/PNG using localmarkieCLI (MarkieCli).
Example diary usage:
# Generate today's diary markdown
scripts/remi-diary.sh --date today
# Generate today's diary with structured progress events
DIARY_PROGRESS_JSONL=/tmp/remi-diary.progress.jsonl scripts/remi-diary.sh --date today --sync
# Generate and send yesterday's diary image to Telegram
scripts/remi-diary.sh --date yesterday --sendExample Markdown → SVG rendering:
scripts/markie-export.sh \
--input ~/diary/remi/$(date +%F).md \
--output /tmp/remi-diary.svg \
--format svgremi-diary.sh prints a safety warning by default because it may send transcript data to external services:
- your configured summary command/provider (default:
codex exec ...) for summary generation - Telegram (when
--sendis enabled)
If you intentionally want to suppress the warning:
DIARY_SKIP_EXTERNAL_WARNING=1 scripts/remi-diary.sh --date todayIf you want machine-readable progress for timers or other automation, set DIARY_PROGRESS_JSONL or pass --progress-jsonl <path>; the script will append one JSON object per phase transition, including per-agent sync events.
Use DIARY_* environment overrides (shown in scripts/remi-diary.sh --help) to adapt paths/commands for your environment.
Workspace crates:
core-model: canonical types + adapter trait + deterministic IDsstore-sqlite: SQLite schema, session/doc upserts, FTS index maintenance, archive planning helpersingest: sync orchestration with progress phasessearch: session ranking plus separate docs lexical/substring search helpersarchive: plan/run/restore archive workflowsadapter-common(atcrates/adapters/common): shared file/JSON parsing + cursor logicadapters/{pi,droid,opencode,claude,amp,codex}: per-agent ingestion adaptersembeddings(optional): ONNX + tokenizer embedding generationcli:remicommand-line interface for session sync/search, docs index/search, archive, and doctor flows
GitHub release workflow publishes:
remi-linux-x64-simple.tar.gz(binary only)remi-linux-x64-bundled.tar.gz(binary + ONNX Runtime + BGE model files)
As of v0.1.0 (April 1, 2026), published assets are Linux x64.
The workflow in this repo is set up to also produce macOS/Windows simple artifacts on future tagged releases.
Homebrew tap setup (recommended layout):
- Create a tap repo, e.g.
lsj5031/homebrew-remi. - Start from this repo’s
Formula/remi.rband update URL/version/SHA per tagged release. - Update SHA256 per release.
End-user install:
brew tap lsj5031/remi
brew install remiDual-licensed under:
- MIT
- Apache-2.0
