# समर्पित Engine में Filtering: Qdrant — Vector Databases

Source: https://www.geekswithgeeks.com/hi/vector-databases/f-qdrant

> उन्हें केंद्र में रखकर बने engine में payload filters देखें।

## Payload filters प्रमुख सुविधा हैं

**Qdrant** Rust में लिखा open-source vector database है। इसका मॉडल: **points** की **collection**, हर एक की ID, एक या अधिक vectors और JSON **payload**। आप vector आकार और दूरी metric के साथ collection बनाते हैं, points `upsert` करते हैं, और vector के साथ वैकल्पिक **filter** से `query` करते हैं जो payload fields पर `must`, `should` और `must_not` शर्तों (match, range, geo आदि) से बनता है। Qdrant की HNSW खोज **filter-जागरूक** है: वह graph पार करते हुए payload शर्तें जाँचती है (और जिन fields पर filter करते हैं उन पर **payload indexes** बनाने चाहिए), जो सीधे post-filtering के ख़ाली-परिणाम जाल से बचाता है। Python client में **स्थानीय in-memory mode** भी है, जो यहाँ उपयोग हुआ, बिना server चलाए वही API देता है, जो tests के लिए उत्कृष्ट है।

## Qdrant: upsert, खोज, filter, delete, चलाकर

मैंने यह Python virtual environment में qdrant-client 1.19.1 (स्थानीय in-memory mode) और chromadb 1.5.9 (in-memory client) के साथ चलाया। Collection में चार points हैं। सादी query points 1, 4 और 2 लौटाती है (4 दूसरे tenant का है)। Tenant `acme` और वर्ष 2025 के filter के साथ सिर्फ़ points 1 और 3 योग्य हैं। Point 4 हटाने के बाद गिनती 4 से 3 हो जाती है। Local mode उपयोग हुआ है, इसलिए कोई server शामिल नहीं।

```python
from qdrant_client import QdrantClient, models

client = QdrantClient(":memory:")              # local mode: same API as a server, nothing to install or run
client.create_collection("docs", vectors_config=models.VectorParams(size=3, distance=models.Distance.COSINE))
client.upsert("docs", points=[
    models.PointStruct(id=1, vector=[0.9, 0.1, 0.0], payload={"tenant": "acme", "year": 2025, "text": "leave policy 2025"}),
    models.PointStruct(id=2, vector=[0.8, 0.2, 0.1], payload={"tenant": "acme", "year": 2022, "text": "old leave policy"}),
    models.PointStruct(id=3, vector=[0.1, 0.9, 0.1], payload={"tenant": "acme", "year": 2025, "text": "travel and hotels"}),
    models.PointStruct(id=4, vector=[0.9, 0.0, 0.2], payload={"tenant": "beta", "year": 2025, "text": "beta confidential memo"}),
])
print("points:", client.count("docs").count)

hits = client.query_points("docs", query=[1, 0, 0], limit=3).points
print("no filter :", [(h.id, round(h.score, 3)) for h in hits])

only_acme_2025 = models.Filter(must=[
    models.FieldCondition(key="tenant", match=models.MatchValue(value="acme")),
    models.FieldCondition(key="year", match=models.MatchValue(value=2025)),
])
hits = client.query_points("docs", query=[1, 0, 0], query_filter=only_acme_2025, limit=3).points
print("with filter:", [(h.id, h.payload["text"]) for h in hits])

client.delete("docs", points_selector=models.PointIdsList(points=[4]))
print("after delete:", client.count("docs").count)

```

Output:

```
points: 4
no filter : [(1, 0.994), (4, 0.976), (2, 0.963)]
with filter: [(1, 'leave policy 2025'), (3, 'travel and hotels')]
after delete: 3
```

## Payload indexes बनाएँ

समर्पित engine में हर उस payload field को index करें जिस पर filter करते हैं, वरना filtered खोज धीमे रास्तों पर लौट सकती है।

**Quiz:** Qdrant की filtered खोज को मज़बूत क्या बनाता है?

- [ ] वह सिर्फ़ सटीक खोज समर्थित करता है
- [ ] वह filters अनदेखे करता है
- [x] Payload शर्तें graph traversal के दौरान जाँची जाती हैं, payload indexes के साथ
- [ ] Filters browser में चलते हैं

*Answer:* Payload शर्तें graph traversal के दौरान जाँची जाती हैं, payload indexes के साथ. Filter-जागरूक traversal बहुत कम परिणाम लौटाने से बचाता है।
