Search Overview
How QANATIX hybrid search works — semantic + keyword + identifier detection.
Search
QANATIX uses hybrid search combining dense vectors (semantic), sparse vectors (keyword), and exact-match identifier detection to return the most relevant results in < 200ms.
Query classification
Every query is automatically classified:
| Type | Detection | Strategy |
|---|---|---|
| Identifier | Part numbers, EANs, CAS numbers, DIN/ISO/EN standards, SKUs | Exact match on indexed identifiers |
| Keyword | 1-3 words | Sparse vector (BM25) weighted |
| Semantic | 4+ words, natural language | Dense + sparse fusion |
Examples:
SS-M8-40-A2→ identifier — exact match, score = 1.0stainless bolt→ keyword — BM25 weightedISO 9001 certified M8 suppliers in Germany→ semantic — hybrid fusion
Hybrid fusion
For semantic and keyword queries, QANATIX runs two searches in parallel:
- Dense vector search — semantic similarity (OpenAI, Cohere, or BGE-M3)
- Sparse vector search — keyword relevance (BM25 or model-learned sparse)
Results are fused using Distribution-Based Score Fusion (DBSF) — scores normalized by their statistical distribution, not min/max. Prefetch: 50 candidates per signal.
With BGE-M3 embeddings, a third signal is available:
- ColBERT reranking — token-level late interaction for fine-grained matching (top 20 candidates)
Reranking
When enabled (default), results are re-scored with a cross-encoder model (BAAI/bge-reranker-v2-m3):
- Triggered when 10+ results are returned and
rerank=true - Over-fetches
max(limit * 2, 20)candidates for the reranker pool - Final score:
0.3 * retrieval_score + 0.7 * reranker_score
Zero-result fallback
If hybrid search returns no results, QANATIX automatically:
- Relaxes filters (removes all filter constraints)
- Falls back to dense-only search
- Falls back to Postgres full-text search (degraded mode)
The response metadata.search_mode indicates which strategy was used.
Scoring
Results are scored 0-1 (DBSF normalized). Higher is better.
| Score range | Interpretation |
|---|---|
| 0.8 - 1.0 | Excellent match |
| 0.6 - 0.8 | Good match |
| 0.3 - 0.6 | Partial match |
| < 0.3 | Weak match |
Results with score < 0.05 are filtered out.
Identifier matches always return score = 1.0.
Caching
| Cache | TTL | Key |
|---|---|---|
| Response cache | 30 seconds | tenant + vertical + normalized query |
| Query embedding cache | 1 hour | provider + model + dimensions + query hash |
| Entity embedding cache | 7 days | provider + model + dimensions + text hash |
Next
- REST API — full endpoint reference
- Filters — structured filtering with range operators
- Response Formats — compact, full, yaml