¿Qué hace Construcción de modelos dbt?
Cuándo usarlo
- Crear o refactorizar modelos
.sqlen un proyecto dbt. - Decidir la materialización (vista / tabla / incremental / efímera).
- Estructurar capas (staging → intermediate → marts).
- Escribir modelos incrementales para tablas grandes y en crecimiento.
- NO usar para la autoría de pruebas (usa
testing-dbt-projects) o fallos de ejecución (usadebugging-dbt-runs).
Flujo de trabajo
- [ ] Colocar el modelo en la capa correcta (staging/intermediate/marts)
- [ ] Referenciar solo upstream mediante ref()/source() — nunca nombres codificados
- [ ] Elegir materialización según el tamaño y las necesidades de actualización
- [ ] Para incremental, establecer unique_key + filtro is_incremental()
- [ ] Agregar una entrada en schema.yml con pruebas
- Capas.
staging/= un modelo por tabla fuente, renombrado/tipado ligero, materializado como vistas.intermediate/= lógica de negocio reutilizable.marts/= modelos dimensionales finales consumidos por BI, materializados como tablas. - Referenciar correctamente. Usa
{{ ref('stg_orders') }}y{{ source('shop', 'orders') }}para que dbt construya el DAG y gestione los entornos. Nunca escribas esquema.tabla sin formato. - Elegir materialización: vista (barata, siempre fresca, pequeña), tabla (lecturas rápidas, reconstruida cada ejecución), incremental (tablas grandes de añadir/actualizar), efímera (CTE en línea, sin objeto).
- Modelos incrementales procesan solo filas nuevas o cambiadas.
Patrones
Modelo staging — uno por fuente, delgado y consistente:
-- models/staging/shop/stg_orders.sql
with source as (select * from {{ source('shop', 'orders') }})
select
order_id,
customer_id,
cast(order_ts as timestamp) as ordered_at,
round(amount_cents / 100.0, 2) as amount
from source
Modelo incremental — filtra filas nuevas y establece una clave de fusión idempotente:
{{ config(materialized='incremental', unique_key='order_id',
incremental_strategy='merge') }}
select * from {{ ref('stg_orders') }}
{% if is_incremental() %}
-- solo filas más recientes que las ya cargadas, con una ventana de retroceso para datos tardíos
where ordered_at >= (select coalesce(max(ordered_at), '1900-01-01') from {{ this }})
- interval '3 days'
{% endif %}
El unique_key + merge hace que las re-ejecuciones sean idempotentes; la ventana de retroceso captura
filas que llegan tarde. En BigQuery/Spark, prefiere insert_overwrite en una partición por fecha.
Errores comunes
- Nombres de tabla codificados en lugar de
ref()/source()— rompe el DAG, el linaje y el cambio de entorno. - Incremental sin
unique_key— las re-ejecuciones añaden duplicados. - Filtro incremental
max(id)sin ventana de retroceso — descarta silenciosamente datos tardíos. - Lógica de negocio en staging — mantener staging delgado; las uniones/agregaciones pertenecen a intermediate/marts.
- Todo materializado como
table— desperdicia tiempo del almacén; usa vistas para modelos pequeños/baratos e incremental para los grandes. - Un modelo gigante — dividir en pasos intermedios para capacidad de prueba y reutilización.