Convex → ClickHouse · reactive sync
ClickHouse,
but reactive.
Every Convex write streams into ClickHouse through an outbox. When the insert is acked, a scoped watermark bumps and every query watching it refetches. No polling.
commit → fresh aggregate
000ms
press mutate and follow the row
events.add(…)events.add
component table
empty
debounce 250ms
action
idle
—
batchSize 200
JSONEachRow insert
0 rows
async_insert=1
bump after ack
events—
/team:t1—
/team:t2—
useClickHouseQuery
subscribed · team:t1
0 refetches
push —
docIdString
verUInt64
teamIdString
userIdString
kindString
valueFloat64
createdAtDateTime64(3)
SELECT kind, count() AS n, sum(value) AS total FROM events FINAL WHERE teamId = {teamId:String} GROUP BY kind
Team t1
case notesJun 2026
cvx-ch-sync
Replicates Convex tables into ClickHouse in ~300ms, and keeps queries reactive
What it is
A Convex component that streams table writes into ClickHouse through an outbox, then bumps a watermark so analytics queries refetch the moment fresh rows land. Your dashboards stay live without polling.
The bit I'm proud of
It keeps ClickHouse queries reactive, the way Convex queries already are. Writes land in about 200 to 500ms.
On this tab: The pipeline itself. Press the button and follow the row.