Skip to main content

QQL — Qdrant Query Language

SQL-like query language and CLI for Qdrant vector database.

PyPI version Python 3.12+ MIT License Tests

Write INSERT, SELECT, SEARCH, SCROLL, RECOMMEND, UPDATE, DELETE, and CREATE COLLECTION statements instead of Python SDK calls. Supports hybrid dense+sparse vector search, grouped search (GROUP BY), cross-encoder reranking, quantization (scalar, turbo, binary, product), SQL-style WHERE filters, script execution, and collection dump/restore.

qql> INSERT INTO COLLECTION notes VALUES {'text': 'Qdrant is a vector database', 'author': 'alice', 'year': 2024}
✓ Inserted 1 point [3f2e1a4b-8c91-4d0e-b123-abc123def456]

qql> SEARCH notes SIMILAR TO 'vector storage engines' LIMIT 3 WHERE year >= 2023
✓ Found 1 result(s)
 Score  │ ID                                   │ Payload
────────┼──────────────────────────────────────┼──────────────────────────────────────
 0.8931 │ 3f2e1a4b-8c91-4d0e-b123-abc123def456 │ {'text': 'Qdrant is a ...', 'author': 'alice', 'year': 2024}

qql> SEARCH notes SIMILAR TO 'vector databases' LIMIT 5 USING HYBRID RERANK
✓ Found 1 result(s) (hybrid, reranked)
 Score  │ ID                                   │ Payload
────────┼──────────────────────────────────────┼──────────────────────────────────────
 5.3754 │ 3f2e1a4b-8c91-4d0e-b123-abc123def456 │ {'text': 'Qdrant is a ...', 'author': 'alice', 'year': 2024}

How It Works

QQL is a thin translation layer between a SQL-like query language and the Qdrant Python client. Every statement you type goes through three stages:

Your query string
      │
      ▼
  [ Lexer ]      — tokenizes the input into keywords, identifiers, literals
      │
      ▼
  [ Parser ]     — builds a typed AST node (e.g. InsertStmt, SearchStmt)
      │
      ▼
  [ Executor ]   — maps the AST node to a Qdrant client call
      │
      ▼
  Qdrant instance

When you run INSERT, the text field is automatically converted into a dense vector using Fastembed. In hybrid mode (USING HYBRID), a sparse BM25 vector is also generated alongside the dense vector, and searches use Qdrant's Reciprocal Rank Fusion (RRF) by default to merge the results of both retrieval methods. You can switch hybrid search to DBSF with FUSION 'dbsf'.

QQL also exposes a programmatic API for use inside Python applications — no CLI required:

from qql import Connection

with Connection("http://localhost:6333") as conn:
    conn.run_query("INSERT INTO COLLECTION notes VALUES {'text': 'Qdrant is fast'}")
    result = conn.run_query("SEARCH notes SIMILAR TO 'vector database' LIMIT 5")
    for hit in result.data:
        print(hit["score"], hit["payload"])

Installation

Requirements: Python 3.12+, a running Qdrant instance.

pip install qql-cli

Connect to a Qdrant instance:

# Local
qql connect --url http://localhost:6333

# Qdrant Cloud
qql connect --url https://<your-cluster>.qdrant.io --secret <your-api-key>

Then type qql to open the interactive shell.


Documentation

Full documentation lives in the docs/ folder and at pavanjava.github.io/qql:

Topic Description
Getting Started Installation, connecting, first queries
INSERT / INSERT BULK Adding documents, batch inserts, payload types
SEARCH / SELECT / SCROLL / RECOMMEND / Hybrid / GROUP BY / RERANK Semantic search, grouped search, point retrieval, pagination, hybrid, reranking, recommendations
WHERE Filters Full SQL-style filter operators
Collections & Quantization SHOW, CREATE, DROP, QUANTIZE (scalar/turbo/binary/product), CREATE INDEX, UPDATE VECTOR, UPDATE PAYLOAD
Scripts: EXECUTE / DUMP Script files, collection backup/restore
Programmatic Usage Use QQL as a Python library via Connection or run_query()
Reference: Models / Config / Errors Embedding models, config file, error reference

Quick Syntax Reference

-- Insert
INSERT INTO COLLECTION articles VALUES {'text': '...', 'year': 2024}
INSERT BULK INTO COLLECTION articles VALUES [{'text': '...'}, {'text': '...'}]

-- Search
SEARCH articles SIMILAR TO 'query' LIMIT 10
SEARCH articles SIMILAR TO 'query' LIMIT 10 WHERE year >= 2020
SEARCH articles SIMILAR TO 'query' LIMIT 10 WHERE active = true
SEARCH articles SIMILAR TO 'query' LIMIT 10 WITH { mmr_diversity: 0.5, mmr_candidates: 50 }
SEARCH articles SIMILAR TO 'query' LIMIT 10 USING HYBRID
SEARCH articles SIMILAR TO 'query' LIMIT 10 USING HYBRID FUSION 'dbsf'
SEARCH articles SIMILAR TO 'query' LIMIT 10 WITH { indexed_only: true }
SEARCH articles SIMILAR TO 'query' LIMIT 10 WITH { quantization: { ignore: true, oversampling: 2 } }
SEARCH articles SIMILAR TO 'query' LIMIT 10 USING HYBRID RERANK

-- Scroll
SCROLL FROM articles LIMIT 50
SCROLL FROM articles WHERE year >= 2024 LIMIT 50
SCROLL FROM articles AFTER 'cursor-id' LIMIT 50

-- Recommend
RECOMMEND FROM articles POSITIVE IDS (1001, 1002) LIMIT 5

-- Select (retrieve a point by ID)
SELECT * FROM articles WHERE id = '3f2e1a4b-...'

-- Collections
CREATE COLLECTION articles
CREATE COLLECTION articles HYBRID
CREATE COLLECTION articles WITH HNSW { payload_m: 16 }
CREATE COLLECTION articles WITH VECTORS { on_disk: true } WITH HNSW { full_scan_threshold: 10000 }
ALTER COLLECTION articles WITH OPTIMIZERS { indexing_threshold: 10000 }
ALTER COLLECTION articles WITH PARAMS { read_fan_out_factor: 4, on_disk_payload: false }
ALTER COLLECTION articles QUANTIZE DISABLED
CREATE COLLECTION articles QUANTIZE SCALAR
CREATE COLLECTION articles QUANTIZE TURBO
CREATE COLLECTION articles QUANTIZE TURBO BITS 2
CREATE COLLECTION articles QUANTIZE TURBO BITS 1.5 ALWAYS RAM
CREATE INDEX ON COLLECTION articles FOR year TYPE integer
CREATE INDEX ON COLLECTION articles FOR tenant_id TYPE keyword WITH { is_tenant: true, on_disk: true }
CREATE INDEX ON COLLECTION articles FOR doc_id TYPE uuid
CREATE INDEX ON COLLECTION articles FOR title TYPE text WITH { tokenizer: 'word', min_token_len: 2, lowercase: true }
SHOW COLLECTIONS
SHOW COLLECTION articles
DROP COLLECTION articles

-- Search with grouping
SEARCH articles SIMILAR TO 'query' LIMIT 5 GROUP BY category
SEARCH articles SIMILAR TO 'query' LIMIT 5 GROUP BY category GROUP_SIZE 3
SEARCH articles SIMILAR TO 'query' LIMIT 5 WHERE year >= 2020 GROUP BY category GROUP_SIZE 2
SEARCH articles SIMILAR TO 'query' LIMIT 5 USING HYBRID GROUP BY category

-- Update
UPDATE articles SET VECTOR WHERE id = '3f2e1a4b-...' [0.1, 0.2, 0.3, 0.4]
UPDATE articles SET PAYLOAD WHERE id = '3f2e1a4b-...' {'year': 2025, 'status': 'active'}
UPDATE articles SET PAYLOAD WHERE category = 'draft' {'status': 'published'}

-- Delete
DELETE FROM articles WHERE id = '3f2e1a4b-...'
DELETE FROM articles WHERE year < 2020

-- Scripts
EXECUTE /path/to/script.qql
DUMP articles /path/to/backup.qql

Running Tests

Tests do not require a running Qdrant instance — the Qdrant client is mocked.

pytest tests/ -v

Expected: 549 tests passing.


License

MIT © Kameshwara Pavan Kumar Mantha

Metadata

Release files for qql-cli 2.6.0

For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.

Source distribution (sdist)

Source distribution for qql-cli 2.6.0
File Size Uploaded Provenance
qql_cli-2.6.0.tar.gz 1.6 MB Without provenance Details

Built distribution (wheel)

Table of built distributions (wheels) for qql-cli 2.6.0
File Interpreter ABI Platform
qql_cli-2.6.0-py3-none-any.whl Python 3 none any Details

Total release size: 1.7 MB

Release files / qql_cli-2.6.0.tar.gz

Download URL qql_cli-2.6.0.tar.gz
Size 1.6 MB
Tags Source
SHA-256 checksum
How to use checksums
3fda7ac400421b858e9009e532d6908223437380bbf8b133d47938ba3e461230
BLAKE2b-256 checksum
How to use checksums
2e8c8f92ade77ce63a013faf94353f76a27f2306886f2718fe89c14cbda81907
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/6.2.0 CPython/3.12.13

Release files / qql_cli-2.6.0-py3-none-any.whl

Download URL qql_cli-2.6.0-py3-none-any.whl
Size 51.5 kB
Tags Python 3
SHA-256 checksum
How to use checksums
e9e6573a1ef71825ad46c459a25ba288668716a377352044058a83c6afc9b17f
BLAKE2b-256 checksum
How to use checksums
766cc8727a48546491a028288d1c427fc29eb48ad9cc45c66189a592438239ef
Upload date
Uploaded using Trusted Publishing?
What is trusted publishing?
No
Uploaded via twine/6.2.0 CPython/3.12.13

Security for qql-cli 2.6.0

Provenance

Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.

No provenance found

None of the files in this release were uploaded with provenance metadata.

A note on package security

PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.

To learn more about protecting yourself from malicious actors, visit our package security documentation.

Anthropic, PBC Visionary sponsor Bloomberg Visionary sponsor Hudson River Trading Visionary sponsor Meta Visionary sponsor NVIDIA Visionary sponsor Microsoft Sustainability sponsor Depot Continuous Integration AWS Cloud computing and Security Sponsor Datadog Monitoring Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page