How ClickHouse Shapes the Warehouse Contract
July 2026
ClickHouse is a good warehouse contract only when the team understands that current state converges through merges and that fresh, correctness-sensitive reads may need FINAL.
Short Answer
ClickHouse shapes the warehouse contract around tables written over the HTTP interface, but the important part is the CDC read model behind those tables. The docs are explicit that Skippr uses ReplacingMergeTree semantics for CDC, adds _skippr_order_token String, and creates tombstone tables. Newer rows win during merges, not through an immediate row-store update.
That means the main table is still the contract, but readers need to understand how to query it. A table like raw.orders may briefly show more than one version of the same business key after fresh writes until background merges complete. When a query needs point-in-time correctness immediately after CDC activity, ClickHouse requires FINAL. That is not an implementation footnote. It is part of the warehouse contract.
Why Teams Struggle with This
Teams often choose ClickHouse for speed and then describe it as if it will behave like BigQuery or Snowflake on fresh CDC data. The connector can be correct while the warehouse contract is still misunderstood, especially when deduplication timing matters to consumers.
- Successful writes do not mean freshly queried rows are already deduplicated in the way analysts may expect.
- If the team never teaches
FINAL, correctness-sensitive reads will look broken even though the CDC contract is operating as designed. - Ignoring tombstone tables makes delete behavior harder to explain during retries and replays.
- A broad write user or unclear target database weakens operations, but the deeper risk is usually an unclear read model.
How Skippr Handles It
Skippr keeps the ClickHouse destination honest by exposing url, database, user, and password directly and by documenting the CDC behavior instead of hiding it. The warehouse contract stays visible: current state converges through ReplacingMergeTree, order tokens decide which row version wins, and tombstones protect deletes.
That gives teams a concrete way to teach downstream use. Standard analytic reads may be fine without FINAL when freshness lag is acceptable. Operationally sensitive reads right after updates should use FINAL and be described that way in examples and dashboards.
- Loads data into ClickHouse over the documented HTTP interface.
- Uses ReplacingMergeTree-style final-state CDC reconciliation.
- Adds
_skippr_order_tokenand tombstone tables automatically. - Requires
FINALfor point-in-time correctness on fresh data when merge lag matters.
What the First Useful Version Looks Like
The first useful version is one destination database and one CDC-managed table that you query both normally and with FINAL after an update sequence. That shows the actual ClickHouse contract better than any amount of abstract explanation.
If the team does not want to own that read-model nuance, choose a destination with an immediately reconciled table model. ClickHouse is strongest when its merge behavior is an explicit design choice, not a surprise.
