Cómo escalar sus canales de datos y productos de datos con pruebas de contrato y Dbt

Primero, necesitamos agregar dos nuevos paquetes dbt, expectativas-dbt y dbt-utils, que nos permitirá hacer afirmaciones sobre el esquema de nuestras fuentes y los valores aceptados.

# packages.yml

packages:
- package: dbt-labs/dbt_utils
version: 1.1.1

- package: calogica/dbt_expectations
version: 0.8.5

Probando las fuentes de datos

Comencemos definiendo una prueba de contrato para nuestra primera fuente. Extraemos datos de altura_brutauna tabla que contiene información de altura de los usuarios de la app del gimnasio.

Acordamos con nuestros productores de datos que recibiremos la medida de altura, las unidades de medida y la identificación del usuario. Estamos de acuerdo en los tipos de datos y en que sólo se admiten como unidades ‘cm’ y ‘pulgadas’. Con todo esto, ya podremos definir nuestro primer contrato en el archivo YAML fuente de dbt.

Los bloques de construcción

Si observamos la prueba anterior, podemos ver varias de las macros de prueba unitaria de dbt en uso:

  • dbt_expectations.expect_column_values_to_be_of_type: Esta afirmación nos permite definir el tipo de datos de columna esperado.
  • valores_aceptados: Esta afirmación nos permite definir una lista de los valores aceptados para una columna específica.
  • dbt_utils.accepted_range: Esta afirmación nos permite definir un rango numérico para una columna determinada. En el ejemplo, esperábamos que el valor de la columna no fuera menor que 0.
  • no nulo: Finalmente, las afirmaciones integradas como “no nulo” nos permiten definir restricciones de columna.

Utilizando estos componentes básicos, agregamos varias pruebas para definir las expectativas del contrato descritas anteriormente. Observe también cómo hemos etiquetado las pruebas como “fuente-prueba-contrato”. Esta etiqueta nos permite ejecutar todas las pruebas de contrato de forma aislada, tanto localmente como, como veremos más adelante, en el proceso de CI/CD:

dbt test --select tag:contract-test-source

Hemos visto lo rápido que podemos crear pruebas de contrato para las fuentes de nuestra aplicación dbt, pero ¿qué pasa con las interfaces públicas de nuestro canal de datos o producto de datos?

Como productores de datos, queremos asegurarnos de que producimos datos de acuerdo con las expectativas de nuestros consumidores de datos para que podamos satisfacer el contrato que tenemos con ellos y hacer que nuestro canal de datos o producto de datos sea confiable y confiable.

Una forma sencilla de garantizar que cumplimos con nuestras obligaciones con nuestros consumidores de datos es agregar pruebas de contrato para nuestras interfaces públicas.

DBT lanzó recientemente una nueva característica para modelos SQL, contratos modelo, que permite definir el contrato para un modelo dbt. Mientras construye su modelo, dbt verificará que la transformación de su modelo producirá un conjunto de datos que coincida con su contrato, o no se podrá construir.

Veámoslo en acción. Nuestro mercado, índices_masa_corporal, produce una métrica de IMC a partir de los datos de medición de peso y altura que obtenemos de nuestras fuentes. El contrato con nuestro proveedor establece lo siguiente:

  • Tipos de datos para cada columna.
  • Los ID de usuario no pueden ser nulos
  • Los ID de usuario siempre son mayores que 0

Definamos el contrato del modelo body_mass_indexes usando contratos modelo dbt:

Los bloques de construcción

Mirando el archivo de especificación del modelo anterior, podemos ver varios metadatos que nos permiten definir el contrato.

  • contrato.aplicado: Esta configuración le dice a dbt que queremos hacer cumplir el contrato cada vez que se ejecuta el modelo.
  • tipo de datos: Esta afirmación nos permite definir el tipo de columna que esperamos producir una vez que se ejecute el modelo.
  • restricciones: Finalmente, el bloque de restricciones nos brinda la oportunidad de definir restricciones útiles como que una columna no puede ser nula, establecer claves primarias y expresiones personalizadas. En el ejemplo anterior, definimos una restricción para indicarle a dbt que user_id siempre debe ser mayor que 0. Puede ver todas las restricciones disponibles. aquí.

Una diferencia entre las pruebas de contrato que definimos para nuestras fuentes y las definidas para nuestros mercados o puertos de salida es cuando los contratos son verificados y ejecutados.

Los contratos modelo se aplican cuando el modelo se genera mediante dbt run, mientras que los contratos basados ​​en las pruebas dbt se aplican cuando se ejecutan las pruebas dbt.

Si uno de los contratos modelo no se cumple, verá un error al ejecutar ‘dbt run’ con detalles específicos sobre el error. Puede ver un ejemplo en el siguiente resultado de la consola de ejecución de dbt.

1 of 4 START sql table model dbt_testing_example.stg_gym_app__height ........... [RUN]
2 of 4 START sql table model dbt_testing_example.stg_gym_app__weight ........... [RUN]
2 of 4 OK created sql table model dbt_testing_example.stg_gym_app__weight ...... [SELECT 4 in 0.88s]
1 of 4 OK created sql table model dbt_testing_example.stg_gym_app__height ...... [SELECT 4 in 0.92s]
3 of 4 START sql table model dbt_testing_example.int_weight_measurements_with_latest_height [RUN]
3 of 4 OK created sql table model dbt_testing_example.int_weight_measurements_with_latest_height [SELECT 4 in 0.96s]
4 of 4 START sql table model dbt_testing_example.body_mass_indexes ............. [RUN]
4 of 4 ERROR creating sql table model dbt_testing_example.body_mass_indexes .... [ERROR in 0.77s]

Finished running 4 table models in 0 hours 0 minutes and 6.28 seconds (6.28s).

Completed with 1 error and 0 warnings:

Database Error in model body_mass_indexes (models/marts/body_mass_indexes.sql)
new row for relation "body_mass_indexes__dbt_tmp" violates check constraint
"body_mass_indexes__dbt_tmp_user_id_check1"
DETAIL: Failing row contains (1, 2009-07-01, 82.5, null, null).
compiled Code at target/run/dbt_testing_example/models/marts/body_mass_indexes.sql

Hasta ahora contamos con un conjunto de pruebas de potentes pruebas de contrato, pero ¿cómo y cuándo las ejecutamos?

Podemos ejecutar pruebas de contrato en dos tipos de tuberías.

  • Canalizaciones de CI/CD
  • Canalizaciones de datos

Por ejemplo, puede ejecutar las pruebas del contrato de origen según una programación en un Canalización de CI/CD apuntar a las fuentes de datos disponibles en entornos inferiores, como pruebas o puesta en escena. Puede configurar la canalización para que falle cada vez que no se cumpla el contrato.

Estas fallas brindan información valiosa sobre los cambios que rompen el contrato introducidos por otros equipos antes de que estos cambios lleguen a producción.