βββ ββββββ ββββββββββ βββββββ ββββββββββ βββββββ ββββββ βββββββ
βββ βββββββ βββββββββββββββββββββββββββββββββββββββββββββββββββββββ
ββββββββ βββββββ ββββββββββββββββββββββ ββββββββββββββββββββββ ββββ
ββββββββ βββββ ββββββββββββββββββββββ ββββββββββββββββββββββ βββ
βββ βββ βββ βββββββββββ βββββββββββββββββ ββββββ ββββββββββββ
βββ βββ βββ βββββββ βββ βββββββββββββ βββ ββββββ βββ βββββββ
Stop syncing 4 databases. Store vectors, graphs, and docs in one ACID-compliant MongoDB document.
Features β’ MongoDB 8.2 β’ Quick Start β’ Documentation β’ Contributing
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β THE FRAGMENTED WAY β
β β
β ββββββββββββ ββββββββββββ ββββββββββββ ββββββββββββ β
β β Pinecone β β Neo4j β β Redis β β Postgres β β
β β Vectors β β Graph β β Cache β β Metadata β β
β ββββββ¬ββββββ ββββββ¬ββββββ ββββββ¬ββββββ ββββββ¬ββββββ β
β β β β β β
β βββββββββββββββ΄ββββββββββββββ΄ββββββββββββββ β
β β β
β SYNC HELL π± β
β If one write fails, your RAG returns β
β vectors for deleted text β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
VS
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β THE HYBRIDRAG WAY β
β β
β βββββββββββββββββββββββ β
β β MongoDB Atlas β β
β β βββββ βββββ βββββ β β
β β β V β β G β β K β β β
β β βββββ βββββ βββββ β β
β β Vector Graph KV β β
β βββββββββββββββββββββββ β
β β β
β ONE DOCUMENT = ATOMIC β
β
β All or nothing. Never inconsistent. β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
|
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β EMBEDDINGS β LLM PROVIDERS β OBSERVABILITY β UI β
β ββββββββββββ β βββββββββββββ β ββββββββββββ β ββ β
β β Voyage AI β β Claude β β Langfuse β β Chainlit β
β β voyage-4-large β β GPT-4 β β RAGAS Eval β β Rich CLI β
β β Reranking β β Gemini β β β REST API β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
HybridRAG is built for MongoDB 8.2 with native support for the latest search operators.
from hybridrag import (
# 1. Vector Search Filters (MQL - for $vectorSearch)
VectorSearchFilterConfig,
build_vector_search_filters,
# 2. Atlas Search Filters (for $search compound queries)
AtlasSearchFilterConfig,
build_atlas_search_filters,
# 3. Lexical Prefilters (NEW - for $search.vectorSearch)
LexicalPrefilterConfig,
build_lexical_prefilters,
TextFilter, FuzzyFilter, PhraseFilter, WildcardFilter, GeoFilter,
)The game-changer: Apply Atlas Search operators (fuzzy, phrase, wildcard, geo) BEFORE vector search.
from hybridrag import LexicalPrefilterConfig, HybridRAG
# Create a lexical prefilter config
filter_config = LexicalPrefilterConfig(
# Fuzzy text matching (typo-tolerant)
fuzzy_filters=[{"path": "content", "query": "machin lerning", "maxEdits": 2}],
# Exact phrase matching
phrase_filters=[{"path": "title", "query": "vector database"}],
# Wildcard patterns
wildcard_filters=[{"path": "tags", "query": "tech*"}],
# Date range filtering
range_filters={"timestamp": {"gte": "2024-01-01"}},
# Geospatial (find docs near a location)
geo_filters=[{"path": "location", "geometry": {"type": "Point", "coordinates": [-73.9, 40.7]}}],
)
# Use with hybrid search
results = await rag.query(
query="machine learning best practices",
mode="hybrid",
lexical_filter_config=filter_config,
)| Scenario | Legacy $vectorSearch | New $search.vectorSearch |
|---|---|---|
| "Find docs about machin lerning" | β No fuzzy support | β
fuzzy: {maxEdits: 2} |
| "Exact phrase 'machine learning'" | β Vector similarity only | β
phrase: {slop: 0} |
| "Tags matching tech*" | β No wildcards | β
wildcard: {query: "tech*"} |
| "Docs within 10km of NYC" | β No geo filtering | β
geoWithin |
| "Combined filters" | β MQL only ($eq, $gte) | β Full Atlas Search syntax |
# CRITICAL: Each operator uses a DIFFERENT $meta field!
OPERATOR_SCORE_FIELDS = {
"$vectorSearch": "vectorSearchScore", # Legacy
"$search.vectorSearch": "searchScore", # MongoDB 8.2+
"$rankFusion": "rankFusionScore",
"$scoreFusion": "scoreFusionScore",
} βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β $rankFusion (MongoDB 8.2 Native) β
β β
β βββββββββββββββββββββββββ βββββββββββββββββββββββββ β
β β VECTOR PIPELINE β β TEXT PIPELINE β β
β β $search.vectorSearch β β $search.compound β β
β β β β β β
β β βββββββββββββββββββ β β βββββββββββββββββββ β β
β β β Lexical Prefilterβ β β β Fuzzy Matching β β β
β β β (fuzzy/phrase/ β β β β β β β
β β β wildcard/geo) β β β β β β β
β β ββββββββββ¬βββββββββ β β ββββββββββ¬βββββββββ β β
β β β β β β β β
β β βββββββββββββββββββ β β βββββββββββββββββββ β β
β β β Vector Similarityβ β β β BM25 Scoring β β β
β β ββββββββββ¬βββββββββ β β ββββββββββ¬βββββββββ β β
β βββββββββββββΌββββββββββββ βββββββββββββΌββββββββββββ β
β β β β
β ββββββββββββββββ¬ββββββββββββββββββββ β
β β β
β βββββββββββββββββββββββββ β
β β Weighted Fusion β β
β β vector: 0.6 β β
β β text: 0.4 β β
β β scoreDetails: true β β
β βββββββββββββββββββββββββ β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β KNOWLEDGE GRAPH ($graphLookup) β
β β
β Entity Boosting: KG relationships enhance reranking scores β
β Mix Mode: Combines vector + text + graph for comprehensive RAG β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
# Clone and install
git clone https://github.com/romiluz13/HybridRAG.git
cd HybridRAG
# First-time setup (recommended)
make first-time-setup
# Or manual installation
pip install -e ".[all]"# Create .env file
cat > .env << EOF
MONGODB_URI=mongodb+srv://user:pass@cluster.mongodb.net
MONGODB_DATABASE=hybridrag
VOYAGE_API_KEY=pa-xxxxxxxxxxxxx
ANTHROPIC_API_KEY=sk-ant-xxxxxxxxxxxxx
EOFimport asyncio
from hybridrag import create_hybridrag, LexicalPrefilterConfig
async def main():
# Initialize
rag = await create_hybridrag()
# Ingest documents
await rag.ingest_files("./documents/")
# Simple query
result = await rag.query_with_memory(
query="What are the key findings?",
mode="mix", # Vector + Graph + Keyword
)
print(result["answer"])
# Advanced: Query with lexical prefilters
filter_config = LexicalPrefilterConfig(
fuzzy_filters=[{"path": "content", "query": "machin lerning", "maxEdits": 2}],
range_filters={"timestamp": {"gte": "2024-01-01"}},
)
result = await rag.query(
query="machine learning trends",
mode="hybrid",
lexical_filter_config=filter_config,
)
asyncio.run(main())# Launch interactive CLI
hybridrag chat
# Or use Typer commands
hybridrag ingest ./documents/
hybridrag query "What is MongoDB Atlas?"
hybridrag status
hybridrag benchmark| Mode | Description | Use Case |
|---|---|---|
mix |
KG + Vector + Keyword | Recommended - General queries |
hybrid |
Vector + Keyword ($rankFusion) | Fast hybrid search |
local |
Entity-focused retrieval | Specific entities |
global |
Community summaries | High-level overview |
naive |
Vector search only | Simple similarity |
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β HybridRAG β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β β
β ββββββββββββββββββ ββββββββββββββββββ ββββββββββββββββββββββββββββββ β
β β Voyage AI β β Claude/GPT/ β β MongoDB Atlas 8.2 β β
β β Embeddings β β Gemini β β β β
β β + Reranking β β β β ββββββββββββββββββββββββ β β
β ββββββββββββββββββ ββββββββββββββββββ β β $rankFusion β β β
β β β $scoreFusion β β β
β β β $search.vectorSearch β β β
β β β $graphLookup β β β
β β ββββββββββββββββββββββββ β β
β ββββββββββββββββββββββββββββββ β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β β FILTER SYSTEMS ββ
β β VectorSearchFilterConfig β AtlasSearchFilterConfig β LexicalPrefilterββ
β β (MQL: $eq, $gte, $in) β (Atlas: range, equals) β (fuzzy,phrase) ββ
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β β ENHANCEMENTS ββ
β β Entity Boosting β Query Optimizer β Self-Compacting Memory ββ
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ€
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β β INTERFACES ββ
β β Chainlit UI β Typer CLI β REST API β Python SDK ββ
β ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
| Document | Description |
|---|---|
| Cookbook | 8 production recipes for building AI apps |
| Installation Guide | Setup and configuration |
| Architecture Decisions | ADRs for key decisions |
| Enhanced Search | Graph traversal, mix mode |
| Notebooks | Interactive tutorials (5) |
| Examples | Code examples (8) |
| Recipe | Topic | Description |
|---|---|---|
| 01 | Hybrid Search | MongoDB $rankFusion implementation |
| 02 | Lexical Prefilters | MongoDB 8.2 fuzzy/phrase/wildcard/geo |
| 03 | Conversation Memory | Multi-turn chat with self-compaction |
| 04 | Vector Optimization | numCandidates, quantization, tuning |
| 05 | Knowledge Graph | $graphLookup for entity relationships |
| 06 | Filtering Strategies | Three filter systems explained |
| 07 | Agent Memory | Long-term, working, episodic memory |
| 08 | Production | Scaling, monitoring, security |
- ADR-001: MongoDB Single Database
- ADR-002: Voyage AI Embeddings
- ADR-003: Hybrid Search RRF
- ADR-004: Prompts Module
- ADR-005: Filter Builder Systems
- ADR-006: Lexical Prefilters
# Setup development environment
make first-time-setup
# Run tests
make test # All tests
make test-quick # Fast unit tests
make test-cov # With coverage
# Code quality
make lint # Ruff linting
make format # Auto-format
make typecheck # MyPy
# Full CI suite
make ci| Task | Postgres + pgvector | HybridRAG + MongoDB |
|---|---|---|
| Add metadata field | ALTER TABLE + backfill + reindex |
Just add it |
| Change embedding model | Rewrite entire table (MVCC bloat) | Bulk update, no rewrite |
| Hybrid search | Manual result merging in app code | Single $rankFusion pipeline |
| Lexical prefilters | Not supported | $search.vectorSearch native |
| Filter vectors by metadata | Separate index, query planner struggles | Compound index, native |
| Time to first query | Hours (extensions, schema, indexes) | 30 minutes (Atlas free tier) |
We welcome contributions! See CONTRIBUTING.md for guidelines.
# Development setup
git clone https://github.com/romiluz13/HybridRAG.git
cd HybridRAG
make first-time-setup
# Run tests before submitting
make ciApache License 2.0 - see LICENSE for details.
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β β
β MongoDB 8.2 Native: $rankFusion β’ $scoreFusion β’ $search.vectorSearch β
β β
β Three Filter Systems: Vector (MQL) β’ Atlas β’ Lexical Prefilters β
β β
β One MongoDB document. Atomic updates. Never inconsistent. β
β β
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
Built with MongoDB 8.2 β’ Voyage AI β’ Claude