Skip to content

JackALaing/reflect-markdown-mirror

Repository files navigation

reflect-markdown-mirror

reflect-markdown-mirror creates a one-way local Markdown cache from Reflect Notes data so local tools such as QMD can index and search your notes.

Reflect remains the source of truth. The generated Markdown folder is a disposable cache, not an editing target.

What it does

  • Reads a copied snapshot of Reflect's local SQLite database, or a Reflect backup ZIP JSON export.
  • Renders live notes to Markdown with frontmatter metadata.
  • Moves root-level mirror files into .state/deleted/ when their reflect_id is no longer present in the current live snapshot. In normal use, that means the note was deleted or is otherwise no longer live in Reflect.
  • Optionally runs collection-scoped qmd update and qmd embed.
  • Provides a scheduled-sync wrapper and read-only health check.

What it does not do

  • It does not write back to Reflect.
  • It does not edit Reflect's local database or OPFS files.
  • It does not make the mirror safe to publish. Your generated mirror contains your private notes.

How the mirror, QMD, and MCP fit together

Use the Markdown mirror as a local retrieval/indexing cache, not as a collaboration surface:

  1. Sync Reflect into the mirror.
  2. Index the mirror with QMD.
  3. Use QMD to find relevant notes and snippets across the mirror.
  4. Read the note's reflect_id, reflect_url, or reflect_deep_link from the mirror frontmatter.
  5. Use that note ID with Reflect MCP, or open the URL/deep link in Reflect, when you need source-of-truth context or edits.

Example mirrored frontmatter:

---
reflect_id: NOTE_ID
title: Example note
reflect_url: https://reflect.app/g/YOUR_GRAPH_ID/NOTE_ID
reflect_deep_link: reflect://reflect?command=edit-notes&id=NOTE_ID
---

QMD is good for local lexical/semantic retrieval and citations over the generated files. Reflect MCP is the write/edit/source-of-truth interface. Do not edit mirrored Markdown and expect changes to sync back.

Install for local development

This repository is packaged as a small Python project so the CLI commands can be installed cleanly while developing:

python3 -m venv .venv
. .venv/bin/activate
python -m pip install -e .
python -m unittest discover -s tests

pip install -e . installs the console commands from pyproject.toml in editable mode. You can also run the modules directly with PYTHONPATH=src python -m reflect_markdown_mirror.local_sync.

Basic usage

# Full local SQLite snapshot -> Markdown mirror dry run
reflect-markdown-mirror   --source sqlite   --graph-id YOUR_GRAPH_ID   --mirror-dir ~/.local/share/reflect-markdown-mirror/mirror   --dry-run   --json

# Real sync, then QMD update/embed for the reflect collection
reflect-markdown-mirror   --source sqlite   --graph-id YOUR_GRAPH_ID   --qmd-collection reflect   --json

# Read-only health check
reflect-markdown-mirror-health   --graph-id YOUR_GRAPH_ID   --qmd-collection reflect   --json

--mirror-dir is the local folder where generated Markdown cache files are written. The default is ~/.local/share/reflect-markdown-mirror/mirror, but you can set it to any private local path. Do not point it at a Git repository or a folder you edit by hand.

If you omit --graph-id, the SQLite sync includes all live graph rows visible in the local database. You can also set REFLECT_GRAPH_ID in the environment.

QMD setup

qmd collection add ~/.local/share/reflect-markdown-mirror/mirror --name reflect
qmd context add qmd://reflect "Markdown mirror of Reflect notes. Reflect remains source of truth."
qmd update -c reflect
qmd embed -c reflect

Routine runs should stay collection-scoped, e.g. qmd embed -c reflect.

Tested QMD -> MCP handoff

A practical handoff looks like this:

qmd search "distinctive phrase" -c reflect -n 5
qmd get "path-from-result.md" -c reflect -l 25

Then copy reflect_id from the frontmatter and call Reflect MCP's get_note / edit tools with that ID. This was tested against a mirrored note: QMD found the note, qmd get exposed reflect_id and Reflect URLs in frontmatter, and MCP get_note resolved the same ID.

Scheduling on macOS

See examples/launchagents/com.example.reflect-markdown-mirror-sync.plist. Copy it to ~/Library/LaunchAgents/, replace placeholders, then load it with launchctl bootstrap.

The scheduled wrapper writes compact JSONL state under the mirror .state/ directory and can run a postflight health check. If you use a non-default mirror location, pass the same --mirror-dir and --state-dir to reflect-markdown-mirror-scheduled so sync, locking, health checks, and QMD all refer to the same cache.

Privacy and repository hygiene

Do not commit generated mirror output or Reflect source data:

  • mirror Markdown files
  • .state/manifest.json
  • .state/deleted/
  • scheduled-sync.jsonl
  • Reflect SQLite files
  • Reflect backup ZIPs or exports
  • launchd logs

This repo is only for the service code, tests, examples, and docs.

About

One-way local Reflect Notes to Markdown mirror for QMD and other local search tools

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages