LeanCorpus
A fast, embeddable full-text search engine for modern .NET. Zero dependencies, AOT-ready, segment-centric design.
dotnet add package LeanCorpus
Five-minute quick start
using Rowles.LeanCorpus.Document;
using Rowles.LeanCorpus.Document.Fields;
using Rowles.LeanCorpus.Index.Indexer;
using Rowles.LeanCorpus.Search.Queries;
using Rowles.LeanCorpus.Search.Searcher;
using Rowles.LeanCorpus.Store;
// Create an index
using var dir = new MMapDirectory("./my-index");
using var writer = new IndexWriter(dir, new IndexWriterConfig());
// Add documents
var doc = new LeanDocument();
doc.Add(new TextField("title", "The quick brown fox"));
doc.Add(new StringField("id", "1"));
writer.AddDocument(doc);
writer.Commit();
// Search
using var searcher = new IndexSearcher(dir);
var hits = searcher.Search(new TermQuery("title", "fox"), topN: 10);
foreach (var hit in hits.ScoreDocs)
Console.WriteLine($"docId={hit.DocId} score={hit.Score:F3}");
Why LeanCorpus
| Zero allocations in the hot path | Ref-struct token pipeline. No per-token heap allocation during analysis or scoring. |
| Modern scoring | BM25 (default), BM25+, BM25L, TF-IDF, Dirichlet, Jelinek-Mercer, and SIMD-accelerated cosine. Block-Max WAND for sublinear top-k. |
| Vector search built in | HNSW graphs with pre/post-filtering and BBQ quantisation (32x compression). Not a plugin. |
| Native AOT | Trim-safe, publish-ready with PublishAot. Validated by a dedicated smoke-test suite. |
| LINQ queries | IQueryable<T> provider translates expression trees to LeanCorpus queries. |
| Observability built in | OpenTelemetry tracing and metrics, slow-query log, Aspire dashboard integration. |
| Competitive performance | Benchmarks against Lucene.Net 4.8 on 100k-document corpora. Up to 63x faster highlighting, 33x faster geo-distance queries, with 10x to 100x less allocation. |
Feature tour
Analysis
Zero-allocation span-based pipeline: tokenisers, 28 token filters, 11 language stemmers, synonym graphs, Hunspell dictionary stemming, ICU, CJK tokenisation, pattern tokenisers, phonetic filters (Metaphone, Beider-Morse style). Browse analysis docs
Search
25 query types including term, boolean, phrase, fuzzy (Myers bit-parallel), regexp (FST automaton), span, intervals, block-join, geo, and vector. Browse search docs
Scoring
BM25, BM25+, BM25L, TF-IDF (classic plus three variants), three language-model similarities, and SIMD cosine. Pluggable similarity API with expression-free function scoring. Browse scoring docs
Concurrency
Multi-threaded indexing with per-thread DWPT pools. Near-real-time readers via SearcherManager. Background merges that never block commits. Lease-protected segment caches.
Browse concurrency docs
Observability
DefaultMetricsCollector, MeterMetricsCollector (System.Diagnostics.Metrics), OpenTelemetry tracing, structured slow-query log, Aspire dashboard integration.
Browse observability docs
Extensibility
CodecKit for custom storage formats. Pluggable compression (LZ4, Snappy, Zstandard). Source-generated document schemas. Index codec migrator for format upgrades. Browse codec docs
Packages
All packages target net10.0 and net11.0.
Navigate
- Getting started
- Architecture overview
- Why LeanCorpus?
- Performance
- vs Lucene.Net
- API reference
- Benchmarks