Repository navigation
[vector store 2/13] Remove custom sharding from the Qdrant store (speedkick) - #1654
Merged
edwinyyyu merged 1 commit intoSep 16, 2026
Conversation
This was referenced Sep 16, 2026
[session storage 2/2] Remove open-or-create from both stores, and close from the segment store
#1625
Draft
Closed
Draft
[qdrant options] Let a deployment tune a Qdrant collection's HNSW, optimizers and quantization
#1618
Draft
edwinyyyu
force-pushed
the
feat/qdrant-remove-custom-sharding-speedkick
branch
from
September 16, 2026 18:57
b6850d3 to
b488238
Compare
The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Co-Authored-By: Claude Opus 5 (1M context) <[email protected]> Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn
edwinyyyu
force-pushed
the
feat/qdrant-remove-custom-sharding-speedkick
branch
from
September 16, 2026 19:02
b488238 to
bf33c42
Compare
This was referenced Sep 16, 2026
Merged
Closed
This was referenced Sep 17, 2026
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 17, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]>
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 17, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 408b0a9)
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 17, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 408b0a9)
edwinyyyu
commented
Sep 17, 2026
edwinyyyu
left a comment
Contributor
Author
There was a problem hiding this comment.
Found while auditing the main port, #1671. "is_distributed was never documented; a configuration naming it is rejected": the second half does not hold. SupportedDB.build_config does conf_cls(**conf), no configuration model sets extra="forbid", and pydantic's default is extra="ignore", so SupportedDB.QDRANT.build_config({"host": "h", "registry_database": "r", "is_distributed": True}) returns a QdrantConf with no error: the key is silently ignored. Same sentence on #1671.
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 18, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 779362c)
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 18, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 779362c)
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 18, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 779362c)
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 18, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 779362c)
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 21, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 779362c)
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 21, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 779362c)
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 21, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 779362c)
edwinyyyu
added a commit
to edwinyyyu/MemMachine
that referenced
this pull request
Sep 25, 2026
…edkick) (MemMachine#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in MemMachine#1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn Co-authored-by: Claude Opus 5 (1M context) <[email protected]> (cherry picked from commit 779362c)
edwinyyyu
added a commit
that referenced
this pull request
Sep 25, 2026
…tore (port of #1654) (#1671) [vector store 2/13] Remove custom sharding from the Qdrant store (speedkick) (#1654) Remove custom sharding from the Qdrant store The Qdrant store could shard its native collection by logical collection (`QdrantConf.is_distributed`, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant. A shard key is a physical structure, and its cost is per tenant. Measured in #1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit `create_shard_key` call of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap `--uri`. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value. What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one. `is_distributed` was never documented; a configuration naming it is rejected. Claude-Session: https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn (cherry picked from commit 779362c) Co-authored-by: Claude Opus 5 (1M context) <[email protected]>
This was referenced Oct 1, 2026
Draft
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Purpose of the change
The Qdrant store could shard its native collection by logical collection (
QdrantConf.is_distributed, CUSTOM sharding, one shard key per logical collection, a shard-key selector on every operation) so that a logical collection could be deleted by dropping its shard. The payload partition key was written and filtered in both modes, with the shard key on top, so no query changes here; what changes is the cost of a tenant.A shard key is a physical structure, and its cost is per tenant. Measured in #1564 (Qdrant 1.19.0, one hundred tenants): admitting a tenant is an explicit
create_shard_keycall of about 450 ms, 45 s for the hundred against 0.3 s with payload partitioning alone, including 10,000 points; 505 segments against 5, and still 5 after deleting and reusing tenants; and cluster mode is required, with a bootstrap--uri. At ten thousand tenants that is over an hour of shard-key creation and some 50,000 segments before a point is written. Qdrant's own guidance says the same: a physical structure per tenant is for the few oversized ones, the long tail is a payload value.What the shard bought was the O(1) delete, and with it a kind of fencing (a write to a dropped shard fails). Deletion is about to become a registry write that is O(1) and atomic as seen by every reader, a stale handle is fenced by that registry, and the points are reclaimed afterward by a filter-delete off the request path, so a shard per logical collection would only add its cost; it goes now, on the current shape, so the later changes do not carry it. Promoting a single oversized tenant to its own custom-sharded collection later, Qdrant's tiered arrangement, stays open: it is a separate collection, not a flag on this one.
is_distributedwas never documented; a configuration naming it is rejected.Stack
Slice 2 of 13, every PR targeting
speedkick; merge bottom-up.This PR's own change is its last commit,
bf33c427(7 files changed, 9 insertions(+), 192 deletions(-)); it sits directly onspeedkick, and #1630 is stacked on it.Verification
ruff check,ruff format --check,ty check(two pre-existing spacy diagnostics),pytest packages/server/server_tests packages/client/client_tests: 2212 passed, 3 skipped, on the slice-11 tree (speedkick973aad52plus slices 2-11), 2026-09-16; every slice passed its own affected suites when built.🤖 Generated with Claude Code
https://claude.ai/code/session_01ESpWYTmCR7X3bJEpoA8SAn