Usar BigQuery DataFrames en dbt

dbt (data build tool) es un framework de línea de comandos de código abierto diseñado para la transformación de datos en almacenes de datos modernos. dbt facilita las transformaciones de datos modulares mediante la creación de modelos reutilizables basados en SQL y Python. La herramienta coordina la ejecución de estas transformaciones en el almacén de datos de destino y se centra en el paso de transformación de la canalización ELT. Para obtener más información, consulta la documentación de dbt.

En dbt, un modelo de Python es una transformación de datos que se define y se ejecuta mediante código Python en tu proyecto de dbt. En lugar de escribir código SQL para la lógica de transformación, escribes secuencias de comandos de Python que dbt orquesta para que se ejecuten en el entorno del almacén de datos. Un modelo de Python te permite realizar transformaciones de datos que pueden ser complejas o ineficientes de expresar en SQL. De esta forma, se aprovechan las funciones de Python y, al mismo tiempo, se sacan partido de las funciones de estructura de proyectos, orquestación, gestión de dependencias, pruebas y documentación de dbt. Para obtener más información, consulta Modelos de Python.

El adaptador dbt-bigquery admite la ejecución de código de Python definido en BigQuery DataFrames. Esta función está disponible en dbt Cloud y dbt Core. También puedes obtener esta función clonando la última versión del adaptador dbt-bigquery.

Roles obligatorios

El adaptador dbt-bigquery admite la autenticación basada en OAuth y en cuentas de servicio.

Si tienes previsto autenticarte en el adaptador dbt-bigquery mediante OAuth, pide a tu administrador que te conceda los siguientes roles:

Si tienes previsto autenticarte en el adaptador dbt-bigquery mediante una cuenta de servicio, pide a tu administrador que conceda los siguientes roles a la cuenta de servicio que quieras usar:

Si te autenticas con una cuenta de servicio, asegúrate de que se le haya concedido el rol de usuario de cuenta de servicio (roles/iam.serviceAccountUser) a la cuenta de servicio que quieras usar.

Entorno de ejecución de Python

El adaptador dbt-bigquery utiliza el servicio de ejecución de cuadernos de Colab Enterprise para ejecutar el código de Python de BigQuery DataFrames. El adaptador dbt-bigquery crea y ejecuta automáticamente un cuaderno de Colab Enterprise por cada modelo de Python. Puedes elegir elGoogle Cloud proyecto en el que quieres ejecutar el cuaderno. El cuaderno ejecuta el código de Python del modelo, que la biblioteca BigQuery DataFrames convierte en SQL de BigQuery. A continuación, se ejecuta el SQL de BigQuery en el proyecto configurado. En el siguiente diagrama se muestra el flujo de control:

Entorno de ejecución de Python de BigQuery DataFrames para un cuaderno

Si no hay ninguna plantilla de cuaderno disponible en el proyecto y el usuario que ejecuta el código tiene los permisos para crearla, el adaptador dbt-bigquery crea y usa automáticamente la plantilla de cuaderno predeterminada. También puedes especificar otra plantilla de cuaderno mediante una configuración de dbt.

La ejecución del cuaderno requiere un segmento de Cloud Storage de staging para almacenar el código y los registros. Sin embargo, el adaptador dbt-bigquery copia los registros en los registros de dbt, por lo que no tienes que buscar en el contenedor.

Funciones compatibles

El adaptador dbt-bigquery admite las siguientes funciones para los modelos de Python de dbt que ejecutan BigQuery DataFrames:

  • Cargar datos de una tabla de BigQuery con la macro dbt.source().
  • Cargar datos de otros modelos de dbt con la macro dbt.ref() para crear dependencias y gráficos acíclicos dirigidos (DAGs) con modelos de Python.
  • Especificar y usar paquetes de Python de PyPi que se pueden usar con la ejecución de código Python. Para obtener más información, consulta Configuraciones.
  • Especificar una plantilla de tiempo de ejecución de cuaderno personalizada para tus modelos de BigQuery DataFrames.

El adaptador dbt-bigquery admite las siguientes estrategias de materialización:

  • Materialización de tablas, en la que los datos se vuelven a compilar como una tabla en cada ejecución.
  • Materialización incremental con una estrategia de combinación, en la que se añaden datos nuevos o actualizados a una tabla, a menudo mediante una estrategia de combinación para gestionar los cambios.

Configurar dbt para usar DataFrames de BigQuery

Si usas dbt Core, debes usar un archivo profiles.yml para usarlo con BigQuery DataFrames. En el siguiente ejemplo se usa el método oauth:

your_project_name:
  outputs:
    dev:
      compute_region: us-central1
      dataset: your_bq_dateset
      gcs_bucket: your_gcs_bucket
      job_execution_timeout_seconds: 300
      job_retries: 1
      location: US
      method: oauth
      priority: interactive
      project: your_gcp_project
      threads: 1
      type: bigquery
  target: dev

Si usas dbt Cloud, puedes conectarte a tu plataforma de datos directamente en la interfaz de dbt Cloud. En este caso, no necesitas un archivo profiles.yml. Para obtener más información, consulta el artículo Acerca de profiles.yml.

Este es un ejemplo de configuración a nivel de proyecto para el archivo dbt_project.yml:

# Name your project! Project names should contain only lowercase characters
# and underscores. A good package name should reflect your organization's
# name or the intended use of these models.
name: 'your_project_name'
version: '1.0.0'

# Configuring models
# Full documentation: https://docs.getdbt.com/docs/configuring-models

# In this example config, we tell dbt to build all models in the example/
# directory as views. These settings can be overridden in the individual model
# files using the config(...) macro.

models:
  your_project_name:
    submission_method: bigframes
    notebook_template_id: 7018811640745295872
    packages: ["scikit-learn", "mlflow"]
    timeout: 3000
    # Config indicated by + and applies to all files under models/example/
    example:
      +materialized: view

Algunos parámetros también se pueden configurar mediante el método dbt.config en tu código de Python. Si estos ajustes entran en conflicto con el archivo dbt_project.yml, las configuraciones con dbt.config tendrán prioridad.

Para obtener más información, consulta Configuraciones de modelos y dbt_project.yml.

Configuraciones

Puedes configurar lo siguiente con el método dbt.config en tu modelo de Python. Estas configuraciones anulan la configuración a nivel de proyecto.

Configuración Obligatorio Uso
submission_method submission_method=bigframes
notebook_template_id No Si no se especifica, se crea y se usa una plantilla predeterminada.
packages No Especifica la lista adicional de paquetes de Python, si es necesario.
timeout No Opcional: Amplía el tiempo de espera de la ejecución del trabajo.

Ejemplos de modelos de Python

En las siguientes secciones se muestran ejemplos de situaciones y modelos de Python.

Cargar datos de una tabla de BigQuery

Para usar datos de una tabla de BigQuery como fuente en tu modelo de Python, primero debes definir esta fuente en un archivo YAML. El siguiente ejemplo se define en un archivo source.yml.

version: 2

sources:
  - name: my_project_source   # A custom name for this source group
    database: bigframes-dev   # Your Google Cloud project ID
    schema: yyy_test_us       # The BigQuery dataset containing the table
    tables:
      - name: dev_sql1        # The name of your BigQuery table

A continuación, crea tu modelo de Python, que puede usar las fuentes de datos configuradas en este archivo YAML:

def model(dbt, session):
    # Configure the model to use BigFrames for submission
    dbt.config(submission_method="bigframes")

    # Load data from the 'dev_sql1' table within 'my_project_source'
    source_data = dbt.source('my_project_source', 'dev_sql1')

    # Example transformation: Create a new column 'id_new'
    source_data['id_new'] = source_data['id'] * 10

    return source_data

Hacer referencia a otro modelo

Puedes crear modelos que dependan de la salida de otros modelos de dbt, como se muestra en el siguiente ejemplo. Esto resulta útil para crear flujos de datos modulares.

def model(dbt, session):
    # Configure the model to use BigFrames
    dbt.config(submission_method="bigframes")

    # Reference another dbt model named 'dev_sql1'.
    # It assumes you have a model defined in 'dev_sql1.sql' or 'dev_sql1.py'.
    df_from_sql = dbt.ref("dev_sql1")

    # Example transformation on the data from the referenced model
    df_from_sql['id'] = df_from_sql['id'] * 100

    return df_from_sql

Especificar una dependencia de paquete

Si tu modelo de Python requiere bibliotecas de terceros específicas, como MLflow o Boto3, puedes declarar el paquete en la configuración del modelo, como se muestra en el siguiente ejemplo. Estos paquetes se instalan en el entorno de ejecución.

def model(dbt, session):
    # Configure the model for BigFrames and specify required packages
    dbt.config(
        submission_method="bigframes",
        packages=["mlflow", "boto3"]  # List the packages your model needs
    )

    # Import the specified packages for use in your model
    import mlflow
    import boto3

    # Example: Create a DataFrame showing the versions of the imported packages
    data = {
        "mlflow_version": [mlflow.__version__],
        "boto3_version": [boto3.__version__],
        "note": ["This demonstrates accessing package versions after import."]
    }
    bdf = bpd.DataFrame(data)

    return bdf

Especificar una plantilla que no sea la predeterminada

Si quieres tener más control sobre el entorno de ejecución o usar ajustes preconfigurados, puedes especificar una plantilla de cuaderno que no sea la predeterminada para tu modelo de DataFrame de BigQuery, como se muestra en el siguiente ejemplo.

def model(dbt, session):
    dbt.config(
        submission_method="bigframes",
     # ID of your pre-created notebook template
        notebook_template_id="857350349023451yyyy",
    )

    data = {"int": [1, 2, 3], "str": ['a', 'b', 'c']}
    return bpd.DataFrame(data=data)

Materializar las tablas

Cuando dbt ejecuta tus modelos de Python, necesita saber cómo guardar los resultados en tu almacén de datos. Este proceso se denomina materialización.

En la materialización de tablas estándar, dbt crea o sustituye por completo una tabla en tu almacén con el resultado de tu modelo cada vez que se ejecuta. Esto se hace de forma predeterminada o asignando explícitamente la propiedad materialized='table', como se muestra en el siguiente ejemplo.

def model(dbt, session):
    dbt.config(
        submission_method="bigframes",
     # Instructs dbt to create/replace this model as a table
        materialized='table',
    )

    data = {"int_column": [1, 2], "str_column": ['a', 'b']}
    return bpd.DataFrame(data=data)

La materialización incremental con una estrategia de combinación permite a dbt actualizar tu tabla solo con las filas nuevas o modificadas. Esto resulta útil en el caso de conjuntos de datos de gran tamaño, ya que volver a crear una tabla por completo cada vez puede ser ineficiente. La estrategia de combinación es una forma habitual de gestionar estas actualizaciones.

Este enfoque integra los cambios de forma inteligente haciendo lo siguiente:

  • Actualizar las filas que han cambiado.
  • Añadir filas nuevas.
  • Opcional, según la configuración: elimina las filas que ya no están presentes en la fuente.

Para usar la estrategia de combinación, debe especificar una propiedad unique_key que dbt pueda usar para identificar las filas coincidentes entre la salida de su modelo y la tabla, como se muestra en el siguiente ejemplo.

def model(dbt, session):
    dbt.config(
        submission_method="bigframes",
        materialized='incremental',
        incremental_strategy='merge',
        unique_key='int',  # Specifies the column to identify unique rows
    )

    # In this example:
    # - Row with 'int' value 1 remains unchanged.
    # - Row with 'int' value 2 has been updated.
    # - Row with 'int' value 4 is a new addition.
    # The 'merge' strategy will ensure that only the updated row ('int 2')
    # and the new row ('int 4') are processed and integrated into the table.
    data = {"int": [1, 2, 4], "str": ['a', 'bbbb', 'd']}
    return bpd.DataFrame(data=data)

Solución de problemas

Puedes observar la ejecución de Python en los registros de dbt.

Además, puedes ver el código y los registros (incluidas las ejecuciones anteriores) en la página Ejecuciones de Colab Enterprise.

Ir a Ejecuciones de Colab Enterprise

Facturación

Cuando se usa el adaptador dbt-bigquery con DataFrames de BigQuery, Google Cloud se aplican cargos por lo siguiente:

  • Ejecución de cuadernos: se te cobra por el tiempo de ejecución del cuaderno. Para obtener más información, consulta los precios del tiempo de ejecución de los cuadernos.

  • Ejecución de consultas de BigQuery: en el cuaderno, BigQuery DataFrames convierte Python en SQL y ejecuta el código en BigQuery. Se te cobrará según la configuración de tu proyecto y tu consulta, tal como se describe en los precios de los DataFrames de BigQuery.

Puede usar la siguiente etiqueta de facturación en la consola de facturación de BigQuery para filtrar el informe de facturación de la ejecución de cuadernos y de las ejecuciones de BigQuery activadas por el adaptador dbt-bigquery:

  • Etiqueta de ejecución de BigQuery: bigframes-dbt-api

Siguientes pasos