graph-rag-obsidian
Click on "Install Server".
Wait a few minutes for the server to deploy. Once ready, it will show a "Started" state.
In the chat, type
@followed by the MCP server name and your instructions, e.g., "@graph-rag-obsidianwhat are key insights from my project notes?"
That's it! The server will respond to your query, and you can continue using it as needed.
Here is a step-by-step guide with screenshots.
Graph RAG MCP Server for Obsidian
A powerful local-first Graph-RAG system that combines ChromaDB unified store with metadata-based graph relationships and Gemini 2.5 Flash for intelligent Q&A over your Obsidian vault.
π Features
π Unified Database Architecture: ChromaDB with metadata-based graph relationships for both semantic search and graph traversal
π§ Intelligent Semantic Chunking: Respects markdown structure (headers, sections, lists, code blocks)
π― PARA Taxonomy Classification: AI-powered organization using Projects, Areas, Resources, Archive system
π€ RAG-Powered Q&A: Multi-hop retrieval with Gemini 2.5 Flash
πΈοΈ Graph Navigation: Explore backlinks, tags, and semantic relationships
π Real-time Sync: File watcher for automatic indexing
π Local-First: All processing happens locally (except Gemini API calls)
π Multi-Client MCP Support: Works with Claude Desktop, Cursor, and Raycast
β‘ Dual Transport Modes: stdio for Claude Desktop, HTTP for other clients
π οΈ Automated Installation: One-command setup with client detection
π Strongly Typed: Pydantic models throughout for reliability
π― Supported MCP Clients
π€ Claude Desktop: Full stdio integration with automatic configuration
π Cursor: HTTP mode with MCP extension support
β‘ Raycast: HTTP API with custom extension templates
π Any MCP Client: Standard MCP protocol support (stdio/HTTP)
ποΈ Architecture
βββββββββββββββββββ βββββββββββββββββββ
β Obsidian β β ChromaDB β
β Vault βββββΆβ (Unified Store) β
β β β Vector + Graph β
βββββββββββββββββββ β Metadata β
β βββββββββββββββββββ
β β
β βΌ
β βββββββββββββββββββ
β β DSPy β
βββββββββββββββΆβ RAG Engine β
β + Gemini 2.5 β
β (Multi-hop β
β Retrieval) β
βββββββββββββββββββ
β
βΌ
βββββββββββββββββββ
β MCP Server β
β (FastMCP) β
βββββββββββββββββββ
β
βΌ
βββββββββββββββββββ
β Claude Desktop β
β Integration β
βββββββββββββββββββπ Quick Start
Automated Installation (Recommended)
The easiest way to get started with Claude Desktop, Cursor, or Raycast:
# Interactive setup wizard
uv run install.py
# Or non-interactive with your settings
uv run install.py --vault "/path/to/your/vault" --api-key "your_key"The installer will:
β Detect your installed MCP clients (Claude Desktop, Cursor, Raycast)
βοΈ Configure each client automatically
π¦ Install all dependencies
π§ͺ Test the installation
π Create environment configuration
Manual Installation
If you prefer manual setup:
1. Install uv (if not installed)
curl -LsSf https://astral.sh/uv/install.sh | sh # macOS/Linux2. Install Dependencies
uv sync3. Configure Environment
cp configs/.env.example .env
# Edit .env and add your GEMINI_API_KEY and vault paths4. Index Your Vault
# Full indexing (unified ChromaDB store)
uv run scripts/reindex.py all
# Check indexing status
uv run scripts/reindex.py status5. Configure Your MCP Client
Claude Desktop (stdio mode):
{
"mcpServers": {
"graph-rag-obsidian": {
"command": "uvx",
"args": ["--python", "3.13", "--from", ".", "graph-rag-mcp-stdio"],
"cwd": "/path/to/graph-rag-mcp-server",
"env": {
"GEMINI_API_KEY": "your_api_key_here",
"OBSIDIAN_RAG_VAULTS": "/path/to/your/vault"
}
}
}
}Cursor (HTTP mode):
# Start HTTP server
uv run graph-rag-mcp-http
# Configure Cursor MCP extension to use http://localhost:8765Raycast (HTTP mode):
# Start HTTP server
uv run graph-rag-mcp-http
# Install generated Raycast extensionFor detailed configuration instructions, see SETUP.md.
π οΈ Available Commands
MCP Server Modes
# Interactive installer
uv run install.py
# Claude Desktop (stdio mode)
uvx --python 3.13 --from . graph-rag-mcp-stdio
# Cursor/Raycast (HTTP mode)
uv run graph-rag-mcp-http
# HTTP with custom port
uv run graph-rag-mcp-http --port 9000
# Direct stdio runs (alternative)
uv run main.py # stdio mode
uv run src/mcp_server.py # stdio mode Indexing Scripts
# Full indexing
uv run scripts/reindex.py all
# ChromaDB unified store
uv run scripts/reindex.py unified
# Check status
uv run scripts/reindex.py statusReal-time Watching
# Start file watcher
uv run scripts/reindex_watch.py start
# Test file detection
uv run scripts/reindex_watch.py testPARA Taxonomy Enrichment
Enhance your vault with intelligent PARA system classification using DSPy:
# Analyze current vault taxonomy state
uv run scripts/enrich_para_taxonomy.py analyze --sample 100
# Preview enrichment (dry run) on sample notes
uv run scripts/enrich_para_taxonomy.py enrich --limit 10 --dry-run
# Apply enrichment to specific notes
uv run scripts/enrich_para_taxonomy.py enrich "path/to/note.md" --apply
# Bulk enrichment with filters
uv run scripts/enrich_para_taxonomy.py enrich --limit 50 --folder "Projects" --apply
# FULL VAULT ENRICHMENT (new!)
# Preview entire vault enrichment
uv run scripts/enrich_para_taxonomy.py enrich-all --dry-run
# Apply to entire vault (skips already enriched by default)
uv run scripts/enrich_para_taxonomy.py enrich-all --apply
# Force re-enrichment of entire vault
uv run scripts/enrich_para_taxonomy.py enrich-all --apply --force-all
# Customize batch size for large vaults
uv run scripts/enrich_para_taxonomy.py enrich-all --apply --batch-size 25PARA Classification Features:
π― Intelligent Classification: Uses Gemini 2.5 Flash to classify notes into Projects, Areas, Resources, Archive
π·οΈ Hierarchical Tags: Suggests structured tags like
#para/project/ai/automationπ Relationship Discovery: Finds potential links between related notes with validation
π‘ Concept Extraction: Identifies key concepts and themes
π‘οΈ Safe Updates: Only adds frontmatter, never modifies content
π Confidence Scoring: Provides reasoning and confidence for classifications
β‘ Batch Processing: Process entire vaults efficiently with configurable batch sizes
π Smart Deduplication: Avoids reprocessing already enriched notes
π§ MCP Tools
The server exposes these tools for Claude:
Search & Q&A
search_notes: Vector search across vaultanswer_question: RAG-powered Q&A with citationsgraph_neighbors: Find related notes via graphget_subgraph: Extract note subgraphs
Note Operations
create_note: Create new notes with auto-enriched frontmatterlist_notes: Browse vault contentsread_note: Get full note contentget_note_properties: Read frontmatterupdate_note_properties: Modify frontmatteradd_content_to_note: Append content
Graph Navigation
get_backlinks: Find notes linking to targetget_notes_by_tag: Find notes by tag
Management
archive_note: Move notes to archivecreate_folder: Create directoriesreindex_vault: Reindex unified ChromaDB storeenrich_notes: Apply PARA taxonomy enrichment to notes
βοΈ Configuration
Key settings in .env:
# Required
GEMINI_API_KEY=your_key_here
# ChromaDB configuration
OBSIDIAN_RAG_CHROMA_DIR=/custom/path/to/.chroma_db
OBSIDIAN_RAG_COLLECTION=vault_collection
# Optional customization
OBSIDIAN_RAG_EMBEDDING_MODEL=all-MiniLM-L6-v2
OBSIDIAN_RAG_GEMINI_MODEL=gemini-2.5-flash
# Semantic chunking configuration
OBSIDIAN_RAG_CHUNK_STRATEGY=semantic # or "character" for simple chunking
OBSIDIAN_RAG_SEMANTIC_MIN_CHUNK_SIZE=100
OBSIDIAN_RAG_SEMANTIC_MAX_CHUNK_SIZE=3000
OBSIDIAN_RAG_SEMANTIC_MERGE_THRESHOLD=200πββοΈ Usage Examples
Search Your Vault
# Vector search
results = search_notes("machine learning algorithms", k=5)
# Q&A with context
answer = answer_question("What did I learn about transformers?")Explore Relationships
# Find related notes
neighbors = graph_neighbors("Deep Learning", depth=2)
# Get backlinks
backlinks = get_backlinks("Neural Networks")
# Find by tag
tagged_notes = get_notes_by_tag("ai")Manage Notes
# Create a new note with auto-enrichment
note = create_note(
title="Machine Learning Breakthrough",
content="# Key Findings\n\nDiscovered new optimization technique...",
folder="Research",
tags=["ml", "optimization"],
para_type="project", # Hint for PARA classification
enrich=True # Apply AI enrichment
)
# Read note
content = read_note("Research/AI Progress.md")
# Update properties
update_note_properties("Research/AI Progress.md", {
"status": "completed",
"tags": ["ai", "research", "finished"]
})Creating Notes with Auto-Enrichment
The create_note tool creates properly formatted Obsidian notes with:
Clean YAML frontmatter
Automatic PARA classification (if content provided)
Intelligent tag suggestions
Potential link discovery
Timestamps and metadata
Example created note:
---
created: '2025-08-23T20:30:00.000000'
modified: '2025-08-23T20:30:00.000000'
para_type: project
para_category: ai/research
para_confidence: 0.85
key_concepts:
- Machine Learning Optimization
- Gradient Descent Improvements
- Performance Benchmarking
tags:
- ml
- optimization
- para/project
- para/project/ai/research
- tech/ai/ml/optimization
potential_links:
- '[[Optimization Techniques]]'
- '[[Research Log 2025]]'
enrichment_version: '1.0'
last_enriched: '2025-08-23T20:30:00.000000'
enrichment_model: gemini-2.5-flash
---
# Machine Learning Breakthrough
Your content here...PARA Enrichment Workflow
Step 1: Analyze your vault
uv run scripts/enrich_para_taxonomy.py analyze --sample 100Shows current taxonomy state and enrichment potential.
Step 2: Test on subset (dry run)
uv run scripts/enrich_para_taxonomy.py enrich --limit 5 --dry-runPreview classifications without making changes.
Step 3: Apply enrichment
# Start small
uv run scripts/enrich_para_taxonomy.py enrich --limit 20 --apply
# Scale up
uv run scripts/enrich_para_taxonomy.py enrich --limit 100 --applyExample enriched note:
---
para_type: project
para_category: AI/Automation
para_confidence: 0.9
key_concepts:
- AI Agent Development
- Computer Use Automation
- Grounded AI Systems
tags:
- "#project/ai/automation"
- "#area/ai/development"
potential_links:
- "Related Project Name"
enrichment_version: "1.0"
last_enriched: "2025-08-23T17:59:32"
---
# Your original note content remains unchangedπ How It Works
File Parsing: Extracts markdown content, frontmatter, wikilinks, and tags
Semantic Chunking: Intelligent chunking based on markdown structure (headers, sections, lists)
Vector Indexing: Stores semantic chunks with embeddings in ChromaDB
Graph Metadata: Stores notes, links, tags, and chunk relationships as ChromaDB metadata
PARA Classification: Uses DSPy + Gemini to classify notes into Projects, Areas, Resources, Archive
RAG Pipeline: Multi-hop retrieval combining vector search with graph traversal
MCP Interface: Exposes all capabilities via Model Context Protocol
π What's New
Unified ChromaDB Architecture (Latest Update!)
β‘ Simplified Architecture: Single database for both vector search and graph relationships
ποΈ Metadata-based Graph: Efficient graph storage using ChromaDB's native metadata capabilities
π§ Colocated Data: Vector embeddings and graph relationships stored together for optimal query performance
π¦ Reduced Dependencies: No need for separate RDF libraries or stores
π Performance: Streamlined queries with direct metadata access
πΎ Efficient Storage: Single store with optimized embedding and metadata storage
Enhanced PARA Taxonomy
π€ AI-Powered Classification: Automatic categorization into Projects, Areas, Resources, Archive
π·οΈ Smart Tagging: Hierarchical tags like
#para/project/ai/automationπ Validated Wikilinks: Only suggests links to existing notes in your vault
π Batch Processing: Process entire vaults with configurable batch sizes
π― Obsidian-Native: Clean YAML frontmatter without markdown formatting
ChromaDB Metadata Schema
The system stores graph relationships as ChromaDB metadata:
# Note-level metadata
metadata = {
"note_id": "my_note",
"title": "My Note Title",
"path": "/path/to/note.md",
"tags": "important,ai,project",
"links_to": "other_note,related_note",
"backlinks_from": "source_note,another_note",
"vault": "my_vault"
}
# Chunk-level metadata (semantic chunking)
chunk_metadata = {
"chunk_id": "my_note#chunk_0",
"chunk_type": "section",
"header_text": "Introduction",
"header_level": 2,
"importance_score": 0.8,
"sequential_next": "my_note#chunk_1",
"sequential_prev": "",
"parent_chunk": "my_note#header_0",
"child_chunks": "my_note#chunk_1,my_note#chunk_2",
"sibling_chunks": "my_note#chunk_3",
"semantic_chunk": True
}π‘οΈ Security & Privacy
Local-First: All data processing happens on your machine
API Calls: Only Gemini API for text generation (optional)
No Data Leakage: Vault content never leaves your control
Path Validation: Prevents directory traversal attacks
π§ͺ Testing
Test Suite (pytest)
Install test dependencies and run the suite:
# Using uv (recommended)
uv sync --extra test
uv run pytest -q
# Or using the local virtualenv
PYTHONPATH=. .venv/bin/pytest -qCommon invocations:
# Only unit / integration
PYTHONPATH=. .venv/bin/pytest tests/unit -q
PYTHONPATH=. .venv/bin/pytest tests/integration -q
# Coverage (threshold configured in pytest.ini)
PYTHONPATH=. .venv/bin/pytest --cov -q
# Markers
pytest -m unit
pytest -m integration
pytest -m "not slow"Notes:
If you see
ModuleNotFoundError: No module named 'tests', prefix commands withPYTHONPATH=..Integration tests run without network. Embeddings fall back to a builtβin default and DSPy caches write to
.cache/. Override withXDG_CACHE_HOMEorDSPY_CACHEDIRif needed.
Operational Smoke Checks
# Test indexing
uv run scripts/reindex.py status
# Test file watching
uv run scripts/reindex_watch.py test
# Test unified store
uv run python -c "
from src.unified_store import UnifiedStore
from src.config import settings
store = UnifiedStore(
client_dir=settings.chroma_dir,
collection_name=settings.collection,
embed_model=settings.embedding_model
)
stats = store.get_stats()
print(f'Store stats: {stats}')
"π Smart Search Response Contract
The smart_search MCP tool now returns a typed SmartSearchResponse payload:
schema_version,status(ok/degraded/error), and compositeconfidence.diagnosticswith retrieval method, intent + confidence, mean distance, retry count, circuit-breaker state, and warnings.recommendations(up to three actionable suggestions) whenever the response is degraded or fails.Legacy keys (
hits,total_results,strategy_used) remain for one release to ease migration.
Inspect responses locally with the updated CLI helper:
uv run scripts/dspy_mcp_client.py --vault /path/to/vault --query "My quarterly goals" --jsonAdditional MCP tools complement the contract:
health_checkβ runs registered probes, returning cache stats, rate limiter tokens, circuit-breaker state, and metrics counters.get_dspy_optimization_statusβ surfaces optimizer schedule/lock state and whether a background run is pending.force_dspy_optimizationβ triggers an optimization cycle (guarded by async/file locks, executed via a background thread).
Each smart-search invocation also emits a structured log line (SMART_SEARCH_RESULT { ... }) containing the query, status, confidence, retrieval method, retries, circuit-breaker state, warnings, and duration. Simple in-process counters (smart_search_ok/degraded/error, cb_open_events, embed_fallback_events) are exposed via health_check for quick instrumentation.
π§ Troubleshooting
ChromaDB Issues
ChromaDB stores data in
.chroma_db/directoryCheck disk space and permissions
Try full reindex:
uv run scripts/reindex.py unified --fullDatabase is automatically created on first run
Unified Store Issues
Check disk space for
.chroma_db/Try full reindex:
uv run scripts/reindex.py unified --fullEnsure notes are properly deduplicated (fixed in latest version)
Gemini API Issues
Verify API key:
uv run scripts/reindex.py statusCheck rate limits and quotas
For enrichment errors, try smaller batch sizes
Enrichment Issues
Use
--dry-runto preview changes firstCheck note has content (empty files are skipped)
Reduce batch size if hitting API limits:
--batch-size 10
π Project Structure
graph-rag-mcp-server/
βββ src/
β βββ config.py # Configuration management
β βββ fs_indexer.py # File parsing & metadata extraction
β βββ semantic_chunker.py # Intelligent markdown-aware chunking
β βββ chroma_store.py # Vector database operations
β βββ unified_store.py # ChromaDB unified operations (vectors + graph metadata)
β βββ dspy_rag.py # RAG engine with Gemini 2.5 Flash
β βββ mcp_server.py # FastMCP server & tool definitions
βββ scripts/
β βββ reindex.py # Database indexing utilities
β βββ reindex_watch.py # Real-time file monitoring
β βββ enrich_para_taxonomy.py # PARA classification & enrichment
β βββ migrate_rdf_store.py # (removed)
βββ configs/
β βββ claude-desktop.json # Claude Desktop MCP configuration template
β βββ cursor-mcp.json # Cursor MCP configuration template
β βββ raycast-config.json # Raycast extension configuration template
β βββ .env.example # Environment configuration template
βββ install.py # Automated installer & configurator
βββ main.py # Alternate MCP server entry point (stdio)
βββ pyproject.toml # Dependencies & entry points (uv managed)
βββ SETUP.md # Comprehensive setup guide
βββ README.md # Project overview & quick startπ€ Contributing
Fork the repository
Create a feature branch
Add tests for new functionality
Submit a pull request
π License
MIT License - see LICENSE file for details.
Built with modern python stack: Pydantic, ChromaDB, DSPy, FastMCP, and the latest google-genai SDK.
Comprehensive Test Framework & Evaluation Suite
This repo includes a comprehensive test framework with structured fixtures at tests/fixtures/content/ and an evaluation runner that executes deterministic evals for the MCP tools. The evals use distinctive phrases and low-temperature LLM configs so results are stable across embedding and Gemini model choices.
Running Tests:
Unit tests:
uv run python -m pytest tests/unit/ -vAll tests:
uv run python scripts/run_tests.py allEvaluation suite:
uv run python tests/evals/runner.py
Test Categories:
Unit Tests (
tests/unit/): Query intent detection, fuzzy matching, relationship weighting, URI generationIntegration Tests (
tests/integration/): Full MCP server component integrationEvaluation Suite (
tests/evals/): Performance metrics and quality assessmentTest Fixtures (
tests/fixtures/): Structured test content (planets, health, projects)
The evaluation framework creates temporary test environments, reinitializes app state, reindexes content, and validates:
search_notesandsmart_searchwith strategy routinggraph_neighbors,get_subgraph,get_backlinks,get_notes_by_tagCRUD operations:
create_note,add_content_to_note,archive_noteNote management:
read_note,get_note_properties,update_note_properties,list_notes
Test environments are automatically created and cleaned up. All test content uses structured Pydantic models with proper type validation.
This server cannot be installed
Resources
Unclaimed servers have limited discoverability.
Looking for Admin?
If you are the server author, to access and configure the admin panel.
Latest Blog Posts
MCP directory API
We provide all the information about MCP servers via our MCP API.
curl -X GET 'https://glama.ai/api/mcp/v1/servers/nickshffer/graph-rag-mcp-server'
If you have feedback or need assistance with the MCP directory API, please join our Discord server