Bruin CLI Step 3 of 6

ClickHouse + Bruin 101

1) Replace the requested date slice

daily_order_snapshot.sql depends on raw_orders. It uses time_interval materialization with order_date as its incremental key and filters the query with Bruin's {{ start_date }} and {{ end_date }} variables.

The asset definition tells Bruin which destination slice it may replace:

/* @bruin

name: daily_order_snapshot
type: clickhouse.sql

materialization:
  type: table
  strategy: time_interval
  incremental_key: order_date
  time_granularity: date

depends:
  - raw_orders

@bruin */

depends adds raw_orders to the graph before this model runs. incremental_key: order_date and time_granularity: date tell the time_interval materialization how to identify the destination rows for one requested date range.

The query selects exactly that range:

SELECT
    order_id,
    customer_id,
    order_date,
    order_status,
    amount,
    updated_at
FROM raw_orders
WHERE order_date BETWEEN toDate('{{ start_date }}') AND toDate('{{ end_date }}')

{{ start_date }} and {{ end_date }} are Jinja variables that Bruin renders before it sends SQL to ClickHouse. For a run from 2024-04-01 through 2024-04-15, the final predicate becomes order_date BETWEEN toDate('2024-04-01') AND toDate('2024-04-15'). The toDate() calls make the rendered strings match the Date column. Keep this filter aligned with incremental_key: otherwise Bruin could replace one interval while the query returns rows from another.

For a run window, Bruin replaces just the rows in that date interval. This makes a backfill explicit: the same model can rebuild 1-15 April without rewriting every date. time_granularity: date documents the intended grain. See Bruin variables for the run values available in SQL.

Sign up to our newsletter

Practical updates on open-source data pipelines, AI analysts, governance, and what we are shipping at Bruin.