Knowledge Guide
HomeSystem DesignData Partitioning

hard Rebalancing Strategies (Beyond Consistent Hashing)

Mechanism: partitions must move when the node count changes — the only real question is HOW

Every partitioned datastore eventually adds or removes a node, and when it does, some fraction of the data has to relocate so load stays roughly even on the new set of machines. What separates a good rebalancing strategy from a bad one is not whether data moves, but how MUCH moves and how CLEANLY — does the whole cluster reshuffle, or does only the minimum necessary slice change hands? Three real strategies answer this differently, plus one anti-pattern that should never ship in an elastic system:

Before: 4 nodes each holding 250 of 1000 fixed partitions. Node N5 joins. After: 5 nodes each holding 200 partitions; N5's 200 are composed of four 50-partition stripes donated from N1 through N4 respectively. Only whole partitions relocate; nothing is rehashed at the key level.
Before: 4 nodes each holding 250 of 1000 fixed partitions. Node N5 joins. After: 5 nodes each holding 200 partitions; N5's 200 are composed of four 50-partition stripes donated from N1 through N4 respectively. Only whole partitions relocate; nothing is rehashed at the key level.

Traced: 1000 fixed partitions, 4 nodes → 5 nodes

Start with 4 nodes and 1000 partitions split evenly: 250 partitions per node. A 5th node joins.

  1. Compute the new even split. 1000 partitions ÷ 5 nodes = 200 partitions per node.
  2. Each existing node donates the surplus. N1–N4 each currently hold 250; the new fair share is 200, so each donates its surplus of 50 (250 − 200 = 50) to N5.
  3. N5 fills up from four donors. 4 × 50 = 200 — exactly N5's fair share. No node did any hashing; whole partitions were physically handed over as units.
  4. Result. Total partition count is still 1000, fixed since creation. Roughly 1/5 of all keys moved — the same fraction as the new node's share of the cluster — but every key that moved did so as part of an already-existing, self-contained partition. No key inside a partition that stayed put was ever touched.

Compare this to hash mod N on the same cluster growth: mod-N would recompute hash(key) % 5 for every one of the (say) hundreds of millions of keys behind those 1000 partitions and copy roughly 80% of them individually. Fixed partitioning turns that into a bulk transfer of 200 pre-existing, self-contained partitions — a segment/file copy the storage layer can do in one shot, not a row-by-row rewrite.

Dynamic partitioning: split when large, merge when small

Fixed partitioning has one weakness: the count is chosen once, at creation, and never changes. If the dataset grows 100× past what that count was sized for, every partition individually becomes huge and hot, and there is no lever left to pull except "re-partition everything" — a migration project, not a routine operation. Dynamic partitioning solves this the way a B-tree solves the same problem for its own pages: each partition monitors its own size, and when it crosses a threshold, it splits into two roughly-equal halves that keep serving traffic without any global recomputation. Symmetrically, when neighbouring partitions shrink — old data was deleted, or a range simply never grew — they can be merged back into one. HBase (region splits) and MongoDB (chunk splitting) both work this way: the partition count is a function of live data volume, not a number fixed on day one.

Split: partition P2 covering keys H to N grows past its 10 GB threshold at 12 GB and splits into P2a (H to K, 6 GB) and P2b (L to N, 6 GB). Merge: adjacent partitions P5 (0.4 GB) and P6 (0.3 GB), each below a 1 GB minimum, merge into P5+6 at 0.7 GB. Partition count is not fixed; it grows and shrinks with data volume.
Split: partition P2 covering keys H to N grows past its 10 GB threshold at 12 GB and splits into P2a (H to K, 6 GB) and P2b (L to N, 6 GB). Merge: adjacent partitions P5 (0.4 GB) and P6 (0.3 GB), each below a 1 GB minimum, merge into P5+6 at 0.7 GB. Partition count is not fixed; it grows and shrinks with data volume.

Judgment: fixed count vs. dynamic vs. consistent-hash vnodes — how a senior engineer decides

StrategyWhat moves on scale-outChoose when…Cost
Fixed # of partitionswhole partitions only, ~1/N of the datadata volume is roughly predictable at design time; want the simplest possible rebalancer (Elasticsearch, Riak, Couchbase)partition count is welded in at creation — too few caps future scale, too many adds per-partition overhead
Dynamic partitioningwhole partitions, and the count itself changesdata volume is unpredictable or grows by orders of magnitude (HBase, MongoDB)real operational complexity — split/merge logic, and a write burst can trigger a "split storm"
Consistent hashing + vnodes~K/N keys, not whole partitionselastic key-value workloads with point lookups and frequent membership churn (Dynamo, Cassandra)needs many vnodes to avoid lumpy arcs; no ordered range scans (see Data Sharding Techniques)

The real axis all three sit on is: how much are you willing to decide up front, versus let the system decide at runtime? Fixed partitioning asks you to guess final scale once, correctly, and rewards that guess with the simplest possible logic — no splitting code to write or debug, no split-storm failure mode. Dynamic partitioning removes the guess entirely at the price of runtime complexity: you are now shipping and operating a splitter, and it can misfire under a sudden burst. Consistent hashing sits at a different granularity altogether — it doesn't reshuffle whole partitions, it reshuffles individual keys along a ring, which is the right tool when your unit of data is a single key-value pair rather than a coarse range, and cluster membership itself is expected to churn often rather than grow in occasional, planned steps.

Pitfalls

Takeaways


Synthesized from Martin Kleppmann, Designing Data-Intensive Applications (O'Reilly, 2017), Ch. 6, "Partitioning and Rebalancing" — covering fixed number of partitions, dynamic partitioning, and partitioning proportional to nodes — plus Elasticsearch, Riak, Couchbase, HBase, and MongoDB documentation on their respective rebalancing mechanics. Re-authored/Deepened for this guide.

🤖 Don't fully get this? Learn it with Claude

Stuck on Rebalancing Strategies (Beyond Consistent Hashing)? Open Claude, copy a block below, and it'll teach you this exact concept — visually and interactively.

🎨 Explain it visually

Build the mental picture, not memorization.

I just read a lesson on **Rebalancing Strategies (Beyond Consistent Hashing)** (System Design) and want to truly understand it. Explain Rebalancing Strategies (Beyond Consistent Hashing) from first principles using ONE vivid real-world analogy and a visual mental model — draw it as ASCII art or a clear step-by-step diagram — with a concrete example using real numbers. Then ask me one question to check I got the mental picture, and wait for my reply. If you're unsure or a claim isn't standard, say so and reason from first principles instead of guessing.
🤔 Walk me through it (interactive)

Socratic — adapts to where you're stuck.

Teach me **Rebalancing Strategies (Beyond Consistent Hashing)** interactively. Ask me ONE guiding question at a time, wait for my answer, and adapt to my confusion — build the idea with me step by step instead of explaining it all at once. If you're unsure or a claim isn't standard, say so and reason from first principles instead of guessing.
🧪 Quiz me & fix my gaps

Active recall exposes what you missed.

Quiz me on **Rebalancing Strategies (Beyond Consistent Hashing)** with 5 questions, easy to tricky, ONE at a time. Tell me if each answer is right; at the end, explain clearly what I got wrong and why. If you're unsure or a claim isn't standard, say so and reason from first principles instead of guessing.
🧠 Make it stick

Intuition + hook + flashcards for long-term memory.

Help me remember **Rebalancing Strategies (Beyond Consistent Hashing)** for the long term: give the one-sentence intuition, a memorable hook/mnemonic, a tiny worked example, and 3 active-recall flashcards (Q -> A). If you're unsure or a claim isn't standard, say so and reason from first principles instead of guessing.

📝 My notes