Cassandra Compaction

Compaction is the background process that merges multiple SSTables into fewer, larger ones. It removes expired data, purges tombstones, and keeps read performance healthy over time. Without compaction, the number of SSTables on disk would grow indefinitely, slowing every read query.

Why Compaction Is Necessary

Cassandra never overwrites SSTables. When you update or delete data, Cassandra writes a new SSTable with the updated value or a tombstone. Over time, many SSTables accumulate for the same data. A read query must check all of them to find the latest version. Compaction merges those SSTables and keeps only the freshest values, so reads scan fewer files.

Before compaction (5 SSTables for the same partition):
  SSTable 1: row A (v1), row B (v1)
  SSTable 2: row A (v2)              ← overwrite
  SSTable 3: row C (tombstone)       ← deletion
  SSTable 4: row B (v2)              ← overwrite
  SSTable 5: row D (v1)

Read must check all 5 files to assemble current state.

After compaction (1 SSTable):
  SSTable merged: row A (v2), row B (v2), row D (v1)
  row C removed (tombstone expired).

Read checks 1 file. Much faster.

Compaction Strategies

1. SizeTieredCompactionStrategy (STCS) — Default

STCS groups SSTables of similar size into tiers and merges a batch of them when a tier fills up. It is efficient for write-heavy workloads because it defers compaction until several SSTables of similar size accumulate.

STCS Tier Example:

Tier 1 (small, ~10 MB): [SST-1] [SST-2] [SST-3] [SST-4]
  → merge into one ~40 MB SSTable → moves to Tier 2

Tier 2 (medium, ~40 MB): [SST-5] [SST-6] [SST-7] [SST-8]
  → merge into one ~160 MB SSTable → moves to Tier 3

Best for: write-heavy workloads, time-series inserts, batch ingestion.

Downside: high temporary disk space usage during compaction (up to 50% extra space).

ALTER TABLE sensor_data
  WITH compaction = {'class': 'SizeTieredCompactionStrategy',
                     'min_threshold': 4,
                     'max_threshold': 32};

2. LeveledCompactionStrategy (LCS)

LCS organizes SSTables into levels. Each SSTable at Level N is at most 160 MB. Level N+1 holds 10 times the data of Level N. An SSTable from a lower level merges with overlapping SSTables in the next level continuously. This keeps the number of SSTables per read very low (typically 1–2).

LCS Level Structure:

Level 0 (L0): newly flushed SSTables, any size (overlap allowed)
Level 1 (L1): non-overlapping SSTables, each ≤ 160 MB
Level 2 (L2): non-overlapping SSTables, each ≤ 160 MB, 10× more total
Level 3 (L3): non-overlapping, 10× more than L2

Read: at most 1 SSTable at any level except L0. Very fast reads.

Best for: read-heavy workloads with frequent updates and overwrites.

Downside: higher write amplification — data gets rewritten more often.

ALTER TABLE customer_profiles
  WITH compaction = {'class': 'LeveledCompactionStrategy',
                     'sstable_size_in_mb': 160};

3. TimeWindowCompactionStrategy (TWCS)

TWCS is designed for time-series data. It groups SSTables written in the same time window (for example, one day) and compacts them together. When a time window closes, its SSTables compact into one and never merge with SSTables from other windows. This makes expiration of old time windows very cheap.

TWCS Windows (1 day each):

Window: 2024-06-01
  → [SST-1a] [SST-1b] [SST-1c]
     compact into [SST-DAY-1]   ← sealed, never touched again

Window: 2024-06-02
  → [SST-2a] [SST-2b]
     compact into [SST-DAY-2]   ← sealed

Window: 2024-06-03 (current, still accumulating)
  → [SST-3a] [SST-3b] ...

Best for: append-only time-series data with TTL expiration.

Downside: poor performance for workloads with many updates to old data.

ALTER TABLE iot_readings
  WITH compaction = {
    'class': 'TimeWindowCompactionStrategy',
    'compaction_window_unit': 'DAYS',
    'compaction_window_size': 1
  };

4. UnifiedCompactionStrategy (UCS) — Cassandra 5+

UCS is a new strategy introduced in Cassandra 5.0 that combines the benefits of STCS and LCS. It adapts its behavior based on workload patterns. UCS is the recommended default for Cassandra 5.x clusters.

Compaction Strategy Comparison

Strategy   Read Perf   Write Perf  Disk Space   Best Workload
──────────────────────────────────────────────────────────────────
STCS       Medium      Best        High temp     Write-heavy
LCS        Best        Medium      Low           Read-heavy updates
TWCS       Good        Good        Low           Time-series + TTL
UCS        Good        Good        Medium        General (Cassandra 5+)

Monitoring Compaction

# View active compaction tasks:
nodetool compactionstats

# See compaction history:
nodetool compactionhistory

# Force compaction on a keyspace and table immediately:
nodetool compact mykeyspace mytable

Compaction and Tombstones

Tombstones are only removed during compaction if the gc_grace_seconds window has passed. A tombstone younger than gc_grace_seconds is preserved in the compacted SSTable to ensure offline replicas receive the deletion before the marker disappears.

Tombstone lifecycle:

Row deleted → tombstone written to SSTable
                │
         gc_grace_seconds pass (default 10 days)
                │
         compaction runs
                │
         tombstone purged from disk ✓

Summary

Compaction merges SSTables, removes stale data, and purges tombstones to keep Cassandra read performance healthy. STCS suits write-heavy workloads, LCS suits read-heavy workloads with frequent updates, and TWCS is the best choice for time-series data with TTL. Choose the strategy that matches your table's access pattern and monitor compaction activity with nodetool to catch any backlog early.

Leave a Comment

Your email address will not be published. Required fields are marked *