Skip to content

/query_multiple returns documents without an authorization check (cross-tenant IDOR) #301

Description

@nangelovv

Summary

POST /query_multiple returns matching document chunks filtered by file_id only, with no user_id authorization check. Any authenticated caller can read another tenant's document text by supplying that tenant's file_id.

Details

The single-file POST /query enforces ownership — after the similarity search it checks the matched document's user_id against the requester:

if doc_user_id is None or doc_user_id == user_authorized:
    authorized_documents = documents

query_embeddings_by_file_ids (/query_multiple) has no equivalent. It filters purely by file_id and returns whatever matched:

documents = await vector_store.asimilarity_search_with_score_by_vector(
    embedding, k=body.k, filter={"file_id": {"$in": body.file_ids}}, ...
)
...
return documents

Impact

In a multi-tenant deployment (e.g. LibreChat), a user who learns another user's file_id can retrieve that file's chunk text via /query_multiple, bypassing the per-user isolation that /query enforces.

Fix

Apply the same per-document ownership filter as /query: keep only chunks whose user_id is None (unowned) or matches the authenticated identity. PR to follow.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions