Apache Cassandra

Compaction Strategies: STCS, LCS, TWCS

Choose the right compaction strategy to balance read performance, write throughput, and space amplification for different workloads.

Cassandra never modifies a file it has written. Writes go to memory, get flushed to an immutable SSTable, and that file is never edited again.

STCS is like periodically merging piles of similarly-sized papers on your desk into one bigger pile. LCS is like maintaining strict alphabetized filing drawers where each drawer never has duplicate/overlapping labels. TWCS is like using a new labeled box for each week's mail and simply throwing out the entire box once its contents are no longer needed.

Key Concepts

1
So an updated row does not replace the old one. It is written again in a newer file, and the old version stays where it is.
2
Which means reads get slower over time. A row updated five times may live in five SSTables. A read must check all of them and keep the newest value:
3
    SSTable 5 (newest)   user 7: email = new@x.com     <- winner
    SSTable 3            user 7: email = old@x.com
    SSTable 1            user 7: email = older@x.com
4
Compaction is the background job that merges SSTables, keeps the newest value of each column, drops expired tombstones, and writes one file to replace several. The strategy you pick decides when and how.
5
STCS — merge files of similar size. The default. Wait until several SSTables of roughly the same size exist, then merge them into one bigger one:
6
    4 x 100 MB  ->  1 x 400 MB
    4 x 400 MB  ->  1 x 1.6 GB
7
Cheap on write-heavy workloads, because compaction runs rarely. Two costs: a row can still be spread over many files, so reads check several; and merging four 400 MB files needs 1.6 GB of free space before the originals can go, so keep substantial disk headroom.
8
LCS — keep levels with no overlap. SSTables are organised into levels, each ten times the size of the one above, and within a level no two SSTables cover the same keys.
9
That non-overlap is the point: inside one level a key can be in at most one file, so a read touches very few files regardless of how many exist. Good for read-heavy workloads and for rows updated repeatedly.
10
The price is write amplification — the same data is rewritten as it is promoted level by level, often ten times or more. On a write-heavy table LCS will fall behind and never catch up.
11
TWCS — group by time and then leave it alone. SSTables are bucketed by time window, say one day. Compaction happens within a window, and finished windows are never touched again.
12
This exists for time-series data with a TTL. When every row in Monday's window expires, the whole SSTable is deleted as a file — no merging, no tombstone scanning, no read cost.
13
Under STCS the same workload mixes old and new data into shared files, so expired data can only be removed by rewriting files full of live data. That is the classic cause of a time-series cluster slowly filling up.
14
Choosing. Write-heavy or unsure: STCS. Read-heavy with frequent updates: LCS. Time-series with a TTL, where rows are written once and never updated: TWCS.
15
What the interviewer is probing.1. "Why is compaction necessary at all?" Probing: the storage engine. Stalls: "To save space." Moves up: writes go to immutable SSTables, so a row's versions spread across files; compaction merges them and drops tombstones.
16
2. "Which strategy for a write-heavy workload?" Probing: the fit. Stalls: "LCS." Moves up: size-tiered, which has the lowest write amplification — at the cost of read amplification and temporary space spikes.
17
3. "Which for read-heavy with updates?" Probing: the second case. Stalls: "STCS." *Moves up:* levelled, which bounds how many SSTables a read touches, at higher write amplification.
18
4. "Which for time-series?" Probing: the third. Stalls: "Any." Moves up: time-windowed, which groups data by time window so expired windows are dropped whole rather than compacted.