Pure TypeScript port of the Kotlin querylight library, packaged for browsers and Node.js.
Querylight TS is an in-process search toolkit for static sites, browser apps, and Node.js projects that need more than fuzzy matching but do not want a separate search server. It is positioned as the most feature-rich local search library in this category: BM25 and TF-IDF ranking, structured queries, aggregations, highlighting, geo search, dense vector search, sparse vector search, and hybrid reranking behind one API.
The vector story is a first-class part of the library:
- dense vector search with
VectorFieldIndexfor semantic retrieval, ANN lookup, related-content features, and vector rescoring - sparse vector search with
SparseVectorFieldIndexfor learned token-weight retrieval in the style of OpenSearch neural sparse search - hybrid search patterns that combine lexical retrieval with dense or sparse vector ranking
That makes it practical to ship lexical, dense, sparse, and hybrid search locally in one package instead of stitching together multiple narrower tools.
Project links:
- Documentation:
docs/ - Live demo and documentation portal: https://querylight.tryformation.com/
Querylight TS can cover a wide range of local search problems without forcing you into a backend search stack.
Open the live documentation portal and demo on Cloudflare Pages:
It is both the main documentation site and the live product demo. Use it to read the docs, inspect the indexed content, and compare lexical, dense vector, sparse vector, and hybrid retrieval in the browser.
packages/querylight: the library package (@tryformation/querylight-ts)apps/demo: a Hugo-based static demo site with generated docs content and bundled client-side enhancements
- In-memory reverse index for structured documents
- TF-IDF and BM25 ranking
- Reciprocal rank fusion for combining lexical, geo, filter, and vector results
- Dense vector retrieval with
VectorFieldIndex - Sparse vector retrieval with
SparseVectorFieldIndex - Hybrid retrieval with vector rescoring and rank fusion
- Boolean, term, terms, wildcard, regex, exists, range, phrase, prefix, multi-match, dis-max, boosting, and match-all queries
- Numeric/date field indexes plus distance-feature, rank-feature, and JS script scoring queries
- Beginner-friendly plain JSON indexing with
simpleTextSearch - Offset-based exact, phrase, prefix, and fuzzy highlighting
- Analyzer/tokenizer/token-filter pipeline
- Trie-backed prefix expansion
- Aggregations and significant terms
- Approximate nearest-neighbour dense vector search
- Basic geo point/polygon queries
- Portable JSON-serializable index state
Querylight TS supports two different vector retrieval models.
- Dense vectors use
VectorFieldIndex. This is the right fit for embeddings, semantic similarity, related-content features, ANN lookup, and lexical-first reranking withVectorRescoreQuery. - Sparse vectors use
SparseVectorFieldIndex. This is the right fit when your model produces token-weight maps and you want a retrieval path closer to an inverted index. - Hybrid search works with both. You can fuse lexical and vector result sets with
reciprocalRankFusion(...), or retrieve lexically first and rescore a smaller candidate window with vectors.
Start here if vector search is the reason you are evaluating the library:
- Dense vector search: docs/features/approximate-nearest-neighbor-vector-search.md
- Sparse vector search: docs/features/sparse-vector-search.md
- Hybrid reranking: docs/features/vector-rescoring-for-faster-hybrid-search.md
- Demo internals: docs/demo/ask-the-docs-end-to-end.md
Browse the canonical documentation source in docs/ or open the published documentation portal and live demo at https://querylight.tryformation.com/.
Install the published package in another project with:
npm install @tryformation/querylight-tsFor local development in this repository:
npm installIf you want a reasonable default without composing your own queries, use createSimpleTextSearchIndex and simpleTextSearch:
import { createSimpleTextSearchIndex, simpleTextSearch } from "@tryformation/querylight-ts";
const search = createSimpleTextSearchIndex({
documents: [
{
id: "intro",
title: "Querylight TS",
description: "Portable browser and Node.js search",
body: "A compact search toolkit with BM25, phrase search, and fuzzy recovery."
}
],
primaryFields: ["title"],
secondaryFields: ["description", "body"]
});
const hits = simpleTextSearch(search, { query: "portble sear", limit: 5 });If you need highlight fragments, run highlighting as a second step on the returned ids:
import { MatchQuery } from "@tryformation/querylight-ts";
const query = new MatchQuery("title", "range filters");
const hits = search.documentIndex.searchRequest({ query, limit: 5 });
const highlight = search.documentIndex.highlight(hits[0]![0], query, {
fields: ["title", "body"]
});npm install
npm test
npm run build
npm run devThis is intended as a broader client-side search toolkit than fuzzy-match-only libraries such as fuse.js: it combines ranking, boolean logic, multi-field search, phrase search, prefixes, aggregations, dense vector search, sparse vector search, and geo support behind one small pure TypeScript API. For a fuller comparison with fuse.js, Lunr, MiniSearch, FlexSearch, Pagefind, and Orama, see the comparison article.
Parts of this project were developed with AI-assisted agentic coding tools, with design, review, and release decisions still made manually.
Most of the documentation was also AI-generated. That makes broad docs coverage easier to maintain, and it provides a large enough corpus for the demo application to showcase lexical, dense-vector, sparse-vector, and hybrid search modes.