Optimización del procesamiento paralelo de datos en el mundo moderno
En un mundo donde la velocidad lo es todo, el procesamiento eficiente de datos es clave para cualquier flujo de datos exitoso, especialmente al manejar grandes volúmenes de información. Recientemente, enfrenté un desafío que consistía en extraer numerosos archivos, aplicar transformaciones específicas del negocio y cargarlos en un resultado consolidado, todo dentro del entorno de Microsoft Fabric. Este artículo explora las técnicas que utilicé para optimizar el rendimiento, incluyendo multithreading, configuraciones de Spark y diseño personalizado de pipelines de datos.
Caso práctico: Procesamiento paralelo de datos
Mi tarea era procesar un gran volumen de archivos JSON. Cada archivo contenía datos en un formato no estándar, incluyendo caracteres especiales y delimitadores personalizados. Los principales requisitos eran:
- Procesamiento eficiente de archivos: Aplicar lógica de negocio a los archivos JSON semiestructurados de entrada y generar un archivo CSV consolidado como salida. La conversión a CSV requería procesamiento adicional específico del negocio.
- Formato y codificación personalizados: Los datos debían conservar su formato original, incluidos caracteres especiales y delimitadores únicos.
- Asignación dinámica de recursos: Configurar Spark para escalar de manera óptima según la carga de trabajo.
- Solución rentable: Diseñar el pipeline para optimizar el uso de cómputo y asegurar un procesamiento rápido.
Enfoque y soluciones
Dividí la solución en componentes manejables, priorizando el rendimiento y la escalabilidad.
1. Procesamiento paralelo con multithreading y Spark
Primero, cargué los datos JSON en una tabla delta, aplanando su estructura anidada. Esto simplificó la aplicación de la lógica de negocio mientras gestionaba la complejidad. Para procesar los archivos JSON en paralelo, diseñé un pipeline de datos que permitiera la ejecución simultánea de notebooks, utilizando Azure Pipelines y multithreading con Spark.
Multithreading en Spark: Aunque inicialmente utilicé el comando mssparkutils.notebook.runMultiple()
para ejecutar notebooks en paralelo, encontré problemas de rendimiento. Como alternativa, usé ThreadPoolExecutor
de Python para dividir el procesamiento en subconjuntos de datos y ejecutar trabajos en paralelo.
from concurrent.futures import ThreadPoolExecutor def process_file(start_row, end_row): mssparkutils.notebook.run('ProcessCSV', 60, {'startRow': start_row, 'endRow': end_row}) with ThreadPoolExecutor(max_workers=20) as executor: batch_size = 1000 for i in range(0, 5000, batch_size): executor.submit(process_file, i, i + batch_size)
2. Configuración optimizada de Spark para la gestión de recursos
El siguiente reto fue configurar Spark para manejar tareas paralelas eficientemente:
- Capacidad de Microsoft Fabric: Utilicé F64, que ofrece 128 núcleos Spark V-core y un factor de ráfaga de 3, permitiendo hasta 384 V-cores.
- Autoscaling: Ajusté la asignación dinámica de recursos para que Spark escalara según la carga de trabajo, evitando la sobrecarga del sistema.
- Pool personalizado: Configuré un pool con nodos pequeños, un límite de autoscaling de 32 y asignación dinámica de ejecutores.
3. Procesamiento y consolidación de CSVs
Preservar el formato original de los archivos CSV fue un desafío. Usé técnicas de streaming para leer y consolidar archivos directamente desde las rutas de lakehouse:
Lectura directa de CSVs: Evité cargar los CSVs en un DataFrame, que podría alterar el formato, y utilicé open()
de Python para manejar el contenido como texto bruto.
Consolidación de archivos: Tras leer múltiples CSVs, concatené su contenido en una única variable y escribí los datos consolidados en el lakehouse.
csv_files = mssparkutils.fs.ls(csv_folder_path) consolidated_data = "" for file_info in csv_files: if file_info.name.endswith('.csv'): file_path = file_info.path.replace('abfss://{LakehouseName}', '/lakehouse/default') with open(file_path, 'r') as file_object: consolidated_data += file_object.read() + '\n' mssparkutils.fs.put(final_output_path, consolidated_data, "True")
4. Diseño personalizado del pipeline para procesamiento por lotes
Utilicé Azure Pipelines con la actividad ‘ForEach’ para ejecutar notebooks en paralelo según rangos de filas. Esto permitió escalar los trabajos concurrentemente.
Conclusión
Al combinar multithreading, configuraciones optimizadas de Spark y diseño de pipelines, mejoré significativamente el rendimiento del procesamiento de archivos en Microsoft Fabric. La estrategia permitió escalar dinámicamente el sistema y manejar grandes volúmenes de datos sin cuellos de botella, manteniendo la integridad de los datos en todo momento.
Puntos clave
- El multithreading habilita el procesamiento paralelo de grandes datasets.
- Configurar el cluster de Spark optimiza la utilización de recursos.
- Azure Pipelines gestiona eficazmente la ejecución concurrente de notebooks.
Estas técnicas pueden ayudarte a aumentar el rendimiento y mantener la integridad de los datos en entornos de alta demanda.
Devoteam te ayuda a transformar los datos en impacto con las soluciones de Microsoft Data.
Con un equipo de más de 1.200 expertos en Microsoft, 18 especializaciones avanzadas y el reconocimiento como Partner preferente de Microsoft para consultoría premium, soluciones y servicios gestionados en toda EMEA, Devoteam te ayuda a convertir los datos en insights accionables para generar un impacto real en tu negocio.