fix: await ensure_collection and survive partial embed failures in document sync
- ensure_collection was called without await, so the coroutine never ran and fresh tenants had no collection when the upsert hit Qdrant - a single None entry from embed_batch poisoned the point batch and aborted the whole document upsert; failed chunks are now skipped with a warning (all-failed raises and the IndexResult reports failure) - raw client.delete/client.upsert calls now go through the async wrapper (delete_by_filter and the new batch upsert_points method) Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01QbFZyDvYksazX6nYQYZ67L
This commit is contained in:
@@ -467,6 +467,43 @@ class QdrantClientWrapper:
|
||||
logger.error(f"Failed to upsert vector: {e}", exc_info=True)
|
||||
return False
|
||||
|
||||
async def upsert_points(
|
||||
self,
|
||||
collection_name: str,
|
||||
points: List[Dict[str, Any]]
|
||||
) -> int:
|
||||
"""
|
||||
Upsert a batch of vector points in a single request.
|
||||
|
||||
Args:
|
||||
collection_name: Collection name
|
||||
points: List of {"id": str, "vector": List[float], "payload": dict}
|
||||
|
||||
Returns:
|
||||
Number of points upserted
|
||||
|
||||
Raises:
|
||||
Exception: If the upsert fails (callers decide how to degrade)
|
||||
"""
|
||||
if not points:
|
||||
return 0
|
||||
|
||||
structs = [
|
||||
PointStruct(
|
||||
id=p["id"],
|
||||
vector=p["vector"],
|
||||
payload=p.get("payload", {})
|
||||
)
|
||||
for p in points
|
||||
]
|
||||
|
||||
await self.client.upsert(
|
||||
collection_name=collection_name,
|
||||
points=structs
|
||||
)
|
||||
logger.info(f"Upserted {len(structs)} points into {collection_name}")
|
||||
return len(structs)
|
||||
|
||||
async def delete_by_filter(
|
||||
self,
|
||||
collection_name: str,
|
||||
|
||||
Reference in New Issue
Block a user