El Stack Moderno Local
Vamos a construir una infraestructura de datos profesional en tu máquina local. Usaremos Spark como motor de cómputo distribuido (que ya posees en tu entorno Docker) y dbt como el "cerebro" que orquesta, compila y testea las transformaciones SQL.
Flujo de Arquitectura
dbt no procesa datos, dbt gestiona la lógica. Spark hace el trabajo pesado.
Spark (El Músculo)
Ejecuta las queries masivas. Escala horizontalmente. Lee formatos complejos (Parquet, Delta).
dbt (El Cerebro)
Gestiona dependencias. Aplica tests de calidad. Documenta el linaje. Versiona la lógica.
Preparando el Entorno Docker
DEPENDENCIAS DE SISTEMA
Antes de instalar dbt, necesitamos preparar el terreno. El adaptador dbt-spark utiliza una librería llamada PyHive o conectores Thrift que requieren compilación de C++ y librerías SASL.
Estos comandos deben ejecutarse DENTRO de tu contenedor Docker (donde corre Jupyter/Spark), no en tu máquina host.
# 1. Actualizar la lista de paquetes del sistema operativo (Debian/Ubuntu)
apt-get update
# 2. Instalar dependencias críticas para compilar conectores SASL
# - python3-dev: Headers de Python para compilar extensiones C
# - libsasl2-dev: Librería para autenticación SASL (usada por Thrift)
# - gcc: Compilador C necesario para pyhive/sasl
apt-get install -y python3-dev libsasl2-dev libsasl2-modules gcc
# 3. Verificar versión de Python (Idealmente 3.8 o superior)
python3 --version
Si obtienes errores de permisos (EACCES), asegúrate de estar ejecutando como usuario root dentro del contenedor o usa sudo si está disponible. En muchas imágenes de Jupyter, puedes cambiar a root con USER root en el Dockerfile o ejecutando docker exec -u 0 -it nombre_contenedor bash.
Instalando dbt-spark
PIP INSTALL & INITIALIZATION
dbt es modular. No instalamos "dbt" a secas, instalamos el adaptador específico para nuestra base de datos. Al instalar dbt-spark, pip resolverá e instalará automáticamente el núcleo dbt-core.
# Instalar el adaptador con soporte para PyHive (Thrift)
pip install "dbt-spark[PyHive]"
# Verificar que la instalación fue exitosa
dbt --version
# Deberías ver algo como:
# Core: 1.x.x
# Spark: 1.x.x
Iniciando el Proyecto
El comando dbt init es un asistente interactivo que crea la estructura de carpetas necesaria. Vamos a crear un proyecto llamado data_lakehouse.
# Navega a tu carpeta de trabajo persistente (importante para no perder cambios al reiniciar docker)
cd /home/jovyan/work
# Ejecuta el asistente
dbt init data_lakehouse
# --- RESPUESTAS AL ASISTENTE ---
# 1. Which database would you like to use?
# [1] spark <-- Escribe el número correspondiente a spark
# 2. host (thrift server host):
# spark-master <-- O 'localhost' si estás dentro del mismo contenedor, pero usualmente es el nombre del servicio en docker-compose
# 3. port [10000]:
# 10000 <-- Puerto estándar de Thrift
# 4. method [thrift]:
# thrift
# 5. schema (default schema):
# analytics <-- Esto creará una base de datos 'analytics' en Spark
# 6. threads [1]:
# 4
Configuración de Conexión
PROFILES.YML
dbt separa la lógica del código (en tu proyecto) de las credenciales de conexión (en profiles.yml). Esto es por seguridad. Por defecto, busca este archivo en ~/.dbt/.
Método A: Thrift (Recomendado)
Se conecta al Spark Thrift Server via JDBC/ODBC. Es más estable y permite concurrencia real. Requiere que el servicio Thrift esté activo en el puerto 10000.
Método B: Session
Levanta una sesión de PySpark localmente cada vez que corres dbt. Es más lento de iniciar pero no requiere configurar servidor.
data_lakehouse:
target: dev
outputs:
dev:
type: spark
method: thrift # Usa 'session' si falla thrift
schema: analytics # Base de datos destino (Hive/Delta)
host: spark-master # DNS del contenedor Spark (o localhost)
port: 10000 # Puerto del Thrift Server
user: dbt_user # Usuario genérico
threads: 4 # Hilos paralelos para ejecutar modelos
connect_retries: 3
connect_timeout: 60
Si quieres tener el profiles.yml dentro de la carpeta de tu proyecto (para que sea fácil de compartir en el Lab), puedes moverlo y ejecutar dbt con el flag: dbt run --profiles-dir .
Anatomía del Proyecto
DIRECTORIOS CLAVE
Un proyecto dbt no es solo archivos SQL sueltos. Es una aplicación estructurada.
El corazón del proyecto. Aquí van tus archivos .sql.
• staging/: Limpieza inicial (Bronce).
• marts/: Tablas de negocio (Plata/Oro).
Archivos CSV estáticos (ej: códigos de países, categorías fijas) que dbt carga a Spark automáticamente. Es como un "INSERT INTO" masivo gestionado.
Tests singulares (SQL queries que deben retornar 0 filas). Si retornan filas, el test falla. Ideal para reglas de negocio complejas.
El archivo de configuración maestro. Define variables globales, rutas, y cómo se materializan los modelos por defecto (tabla o vista).
Ejecución y Verificación
HELLO WORLD
Vamos a probar la conexión end-to-end. Si esto funciona, tienes un Data Lakehouse local funcional.
# 1. Test de Conectividad
dbt debug
# Deberías ver:
# Found dbt_project.yml
# ...
# Connection:
# host: spark-master
# port: 10000
# ...
# Connection test: [OK connection ok]
Creando tu Primer Modelo
/*
Este es un modelo de ejemplo.
dbt lo compilará en una sentencia:
CREATE OR REPLACE TABLE analytics.hola_spark AS ...
*/
{{ config(materialized='table') }}
select
1 as id,
'Sistema Configurado Correctamente' as mensaje,
current_timestamp() as fecha_prueba
# 2. Compilar y Ejecutar (Materializar tablas en Spark)
dbt run
# 3. Validar resultados (Opcional - dbt test)
dbt test
# 4. Verificar visualmente (Abre un Notebook PySpark y ejecuta):
# spark.sql("SELECT * FROM analytics.hola_spark").show()