Azure ML Services, nuestro punto de encuentro para ML en la nube
Azure se ha convertido en la pieza central de la plataforma de análisis de datos de Microsoft desde hace años. En los últimos meses el área de Machine Learning se ha visto enriquecida con funcionalidades y servicios que forman una plataforma que permite centralizar los desarrollos de Machine Learning, así como proveer de todas las piezas necesarias para consumir datos, entrenar nuestros modelos y productivizarlos de la manera que necesitemos. El hecho de ser una colección de servicios de Azure nos permite además combinarlos fácilmente con otros que no están dentro del área de ML pero que sí forman parte de arquitecturas de nivel empresarial, desde Azure Kubernetes Services a Azure SQL pasando por Key Vault o Container Registry.
En éste artículo vamos a repasar los puntos fundamentales de Azure ML Services y cómo nos permiten acelerar nuestros proyectos de ML, pero antes repasaremos la idea global de Azure ML Services. Su objetivo es servir a todas las fases del proceso de desarrollo y puesta en producción de los modelos, y por tanto, como comentábamos, nos sirve de todos los servicios cubriendo el ciclo de vida de una solución de ML
En el diagrama se muestra el ciclo desde el desarrollo con scripts Python a la docu del SDK (ahora también R, en preview) y cómo se van usando los diferentes servicios y recursos disponibles. Se observa que el cómputo, los repositorios de datos y el servicio de registro de experimentos están desacoplados. De esta manera los diferentes experimentos son flexibles en cuanto a paso entre entornos (apuntar a datos de producción / desarrollo / QA es tan fácil como pasar un argumento diferente a nuestro script) como en el escalado de datos y cómputo. Bastaría con especificar otra configuración a la hora de lanzar nuestro experimento.
Este modo de ejecución con los recursos intercambiables pero entornos, scripts y dependencias constantes resuelve algunos de los puntos más problemáticos del desarrollo de soluciones de ML: la reproducibilidad y la puesta en producción de modelos (y ya de paso, la gestión de dependencias de librerías, otro caballo de batalla histórico).
Workspace en Azure ML Services
El Azure ML Services Workspace es el punto central de gestión y exploración de experimentos. Ahora cuenta con una nueva página dedicada, ya no se encuentra dentro del portal de Azure (ml.azure.com). Aquí podemos ver todos los elementos disponibles en el servicio. Además de usar la página web y la interfaz gráfica que nos ofrece podemos acceder a los diferentes recursos a través de los SDK de Python o R (en preview en éste último caso), Azure CLI o API REST. Sin embargo, dada la rápida evolución del servicio y las mejoras que se aplican, a veces tenemos funcionalidad disponible a través del SDK de Python o Azure CLI que no tenemos en el sitio web.
El Workspace, al centralizar todos los recursos, sirve como hub de exploración y monitorización de experimentos y desarrollos. Y lo primero que tenemos que tener para poner en marcha estos desarrollos son datos!
Datos
En Azure ML Services se pueden obtener datos de diferentes maneras. El propio servicio tiene dos almacenamientos propios, un Blob Storage y un File Share. El almacenamiento por defecto inicial es el File Share, pero podemos cambiarlo a través del SDK. Las diferentes maneras a través de las que podemos trabajar con datos son las siguientes
- Subiendo nuestros propios datos a los almacenamientos propios que se crean como parte del servicio (los citados Blob Storage y File Share)
- Registrando datastores dentro del workspace, con credenciales específicas para acceder a ellos. Esta tarea puede ser parte de las tareas del equipo IT para liberar a los desarrolladores de ML de acceder a las fuentes externas, obtener claves de acceso o SAS keys (los dos modos soportados en éste momento). Podemos registrar los siguientes orígenes de datos como datastores:
- Azure Blob Storage
- Azure File Share
- Azure Data Lake Storage Gen1&2
- Azure SQL Database
- Azure PostgreSQL database
- Azure MySQL database
- Accediendo directamente a las fuentes dentro de los scripts:
- Si la fuente de datos no se puede registrar como Datastore (un bucket S3 de Amazon, por ejemplo), se puede acceder directamente a la fuente desde nuestro script Python. Las credenciales, idóneamente, deberán estar securizadas en un Key Vault.
Datastores
Podemos crear datastores desde el SDK y desde la interfaz gráfica. La configuración es bastante directa si tenemos los datos de acceso (cuenta y account key o SAS key)
Si estamos en las opciones 1 o 2, donde tenemos nuestros datos registrados en un datastore (sea externo o propio del servicio), podremos acceder al datastore completo pasándolo a nuestros scripts especificando el tipo de acceso. Así podríamos acceder a todo el datastore.
Datasets
Sin embargo, si además tenemos identificados conjuntos de datos que querremos utilizar y que, idealmente, han sido validados por el grupo de ingeniería del dato o por los data scientist si también cubren ese rol, podremos registrar datasets concretos y pasarlos a nuestros scripts como “named inputs” para poder acceder incluso más fácilmente a ellos.
Podemos crearlos tanto desde la interfaz web como desde el SDK, como la mayoría de operaciones del servicio
Por ejemplo, una vez tenemos un dataset registrado y obtenida su referencia
from azureml.core import Workspace, Datastore, Dataset, ScriptRunConfig, ComputeTarget, Experiment from azureml.train.sklearn import SKLearn #cogemos la referencia al workspace ws = Workspace.from_config(auth=int_auth) #apuntamos al dataset previamente registrado dataset = Dataset.get_by_name(workspace=ws, name = 'wine') #creamos el estimador para ejecutar nuestro experimento est = SKLearn( source_directory='./scripts', entry_script='train.py', compute_target=comp, inputs = [dataset.as_named_input('train')], #al pasarlo como named_input lo hacemos visible dentro del script de entrenamiento pip_packages=['azureml-sdk', 'pyarrow>=0.12.0'] )
Podríamos acceder dentro de nuestro script de entrenamiento sólo con el siguiente código
#dentro del script train.py #obtener el contexto en el cual está corriendo el script para poder acceder a los objetos run = Run.get_context() #leer la referencia desde el input y pasarlo a un DataFrame de Pandas para empezar a operar df = run.input_datasets['train'].to_pandas_dataframe()
Los datasets que registremos y usemos pueden ser de dos tipos:
- Tabular: datasets con estructura tabular. Todos los que provengan de bases de datos relacionales serán de éste tipo, y muchos de los que tengamos en almacenamientos como Blob Storage también. CSVs, Parquet, Excel, etc. siguen siendo los formatos más populares y la gran mayoría de problemas de ML (especialmente los que resuelven problemas de negocio habituales) se basan en datos en formato tabular.
- Ficheros: Las soluciones de ML que usan datos en formato semi-estructurado o no estructurado (JSON, XML, video, fotos, audio, etc.) son cada vez más habituales. Para poder entrenar modelos que usan éste dato podemos registrar datasets en formato fichero, donde no hay una estructura pre-fijada y realmente acabamos creando un puntero a una lista de ficheros en un almacenamiento como Blob Storage o Azure Data Lake Gen1 ó Gen2
Una vez registrados podemos usarlos como citábamos anteriormente pero también aplicar perfilado de datos sobre ellos. El perfilado de los datos y la exploración visual y estadística de los mismos es una fase fundamental en los proyectos de ML. Además Azure ML incorpora una funcionalidad llamada Data Drift, que basándose en éste perfilado nos informa de cuan diferentes son dos conjuntos de datos. Esto es realmente importante para entender ciertas situaciones donde el mismo modelo puede estar dando resultados muy diferentes sobre conjuntos de datos diferentes y queremos evaluar si se debe a diferencias en el dato o a que nuestro modelo es muy inestable y tenemos que re-evaluar cómo lo hemos construido o incluso la aproximación al problema.
Computación
¡Una vez obtenido el dato deberemos ejecutar nuestros procesos y entrenar nuestros modelos en algún lado! Azure ML Services nos ofrece 4 tipos de cómputo para diferentes escenarios:
- Compute Instances: Son máquinas virtuales con Jupyter, JupyterLab y R Studio instalados y accesibles a través del navegador. Son ideales para prototipado, experimentación y escalado de experimentos si hemos empezado el desarrollo en local y necesitamos VMs que sean fácilmente desplegables y que no se usen constantemente.
- Training clusters: Clústeres de máquinas virtuales que pueden actuar cada una por su lado para escenarios de computación paralela (búsquedas de hiperparámetros, por ejemplo) pero que también pueden actuar como una sola super-máquina si incluimos un controlador MPI (entrenamiento de grandes redes neurales con máquinas que equipan GPUs, por ejemplo).
- Inference clusters: Son clústeres de Azure Kubernetes Services, ideales para desplegar nuestros modelos en contenedores y crear endpoints que pueden consumirse desde el SDK de Python / R o bien como API REST
- Attached Compute: Se trata de recursos de computación en Azure que podemos reaprovechar para ejecutar experimentos. Podemos usar:
- DSVMs
- Azure Databricks
- Azure Data Lake Analytics
- Azure HDInsight
- Azure Batch
Además de todas estas opciones, siempre podemos empezar desarrollando en local y una vez tenemos un prototipo que funciona empezar a testearlo y escalarlo con los recursos de computo de los que dispongamos. Puedes encontrar más información sobre cómputo remoto en Azure ML Services aquí
Para ejecutar un script en el compute instance que se muestra en la captura, podríamos definir un estimador de tipo SKLearn (que ya incluye la librería scikit-learn que usaremos en el experimento), seleccionar nuestro cómputo, crear un experimento y enviarlo para su ejecución:
#apuntar al contexto de computación comp = ComputeTarget(ws, name = 'compute-instance-demo') #%% # estimador que ya incluye la librería SKLearn est = SKLearn( source_directory='./scripts', entry_script='train.py', compute_target=comp, inputs = [dataset.as_named_input('train')], #input para leer desde el script de entrenamiento pip_packages=['azureml-sdk', 'pyarrow>=0.12.0'] #ademas de sklearn necesitamos pyarrow y azureml-sdk para poder trabajar con los métodos de obtención de datos ) # creamos el experimento (o una nueva ejecución si ya existe) y lo enviamos. # esto creará una imagen Docker que se montará en nuestro Compute Instance con las dependencias que hemos declarado en el estimador. # Será éste contenedor donde se ejecutará nuestro script "train.py" exp = Experiment(workspace=ws, name = 'submitted_wine') run = exp.submit(est) #enviamos el experimento con el estimador run.wait_for_completion(show_output=True)
Nuestro script train.py completo
from azureml.core import Workspace, Datastore, Dataset from azureml.core.run import Run from sklearn import datasets import pandas as pd import numpy as np from sklearn.ensemble import RandomForestClassifier from sklearn.model_selection import train_test_split, cross_validate from sklearn.metrics import balanced_accuracy_score, f1_score, confusion_matrix #conseguir el contexto run = Run.get_context() #leer de los inputs declarados df = run.input_datasets['train'].to_pandas_dataframe() #separar nuestro dato y = df.pop('Class') X = df clf = RandomForestClassifier(n_estimators = 100) #validación cruzada sobre el dato cv = cross_validate(clf, X, y, scoring='accuracy', cv=5, n_jobs=-1) acc = str(round(np.average(cv['test_score']), 3)) #registrar métricas de rendimiento directamente contra el servicio de Azure ML run.log(name = 'accuracy', value = acc)
Una vez ejecutado, podremos ver la salida en nuestro entorno de desarrollo pero también en el portal de Azure ML Services, donde tendremos todos los logs, los objetos generados (modelos, gráficos, etc.) que hayamos registrado así como las métricas (como “accuracy” que hemos registrado en nuestro script)
El uso de computación remota en Azure ML puede ser mucho más complejo: desde el uso de diferentes recursos de cómputo en pipelines complejas hasta la ejecución de deep learning en paralelo sobre VMs equipadas con GPUs pasando por el uso de clústers Databricks para el entrenamiento paralelo de modelos ML usando Big Data. Todos estos escenarios se salen del ámbito de éste post pero pueden ser tan complejos y fascinantes como casos de uso tengamos.
Desarrollo y no-code
Una buena parte del desarrollo de soluciones de ML se apoya en código por su flexibilidad y escalabilidad, pero a veces otros modos de desarrollo encajan mejor en nuestro escenario. Por ejemplo, usuarios que están aprendiendo sobre ML y quieren hacer experimentos rápidos y entender los conceptos de pipelines, o incluso Data Scientists que quieren, con muy poco esfuerzo, analizar si el modelo es viable con la información disponible y sin preocuparse de implementar pruebas exhaustivas.
Para estos escenarios, Azure ML ofrece dos funcionalidades: AutoML y Designer. Ambas funcionalidades se enmarcan dentro de la versión Enterprise del servicio. La diferencia entre el modo Básico y Enterprise es que para ciertos recursos de computación se nos cobrará un plus por core, además de algunas funcionalidades que sólo están disponibles en Enterprise. Puedes ver las diferencias detalladas aquí
AutoML
AutoML es una implementación de un concepto que se ha hecho bastante popular en los últimos 2-3 años, la automatización de ciertas partes de los flujos de los proyectos de Machine Learning aplicando buenas prácticas. Así, el resultado de un experimento de AutoML nos devolverá una lista de experimentos y modelos con información relacionada a su rendimiento: tiempo de ejecución, precisión en las predicciones, tipo de algoritmo y preprocesado utilizado, etc.
En el mercado ya existen diferentes implementaciones, pero Microsoft añade un punto extra: crea los experimentos automáticos no de manera aleatoria sino probando algoritmos y técnicas de preprocesamiento que han demostrado ser eficaces en otros problemas de ML con conjuntos de datos parecidos en el pasado. Resumiendo: un recomendador de pipelines de ML. Machine Learning aplicado al Machine Learning 🙂
Podemos acceder a AutoML tanto desde la interfaz gráfica como desde el SDK de Python. El SDK permite algunas opciones de configuración extra como el uso de conjuntos de validación específicos (divididos por tiempo, por ejemplo) además del uso de split aleatorio o validación cruzada.
Con AutoML podemos atacar 3 tipos de problemas de ML actualmente:
- Clasificación (y multiclasificación)
- Regresión
- Series temporales
En todos ellos tenemos incluidas funcionalidades de preprocesado de datos, generación de atributos, generación de modelos compuestos (voting y stacking) y más. Para una lista detallada de funcionalidades puedes consultar la documentación aquí
AutoML usa funcionalidades ya citadas en éste post que son los cimientos del servicio: datastores, datasets y cómputo. Para crear un experimento AutoML deberemos seleccionar el dataset previamente registrado o crearlo en el momento
Especificar dónde va a ejecutarse el experimento (en qué recurso de cómputo). Este punto es importante dado que dependiendo del nivel de paralelismo que podamos alcanzar (en nodos de un cluster) podremos ejecutar varias iteraciones de la exploración automática de manera paralela (N nodos = N modelos en paralelo)
Y finalmente especificar la configuración avanzada en el caso de que lo necesitemos. Por ejemplo, limitar el tiempo de ejecución, eliminar algoritmos que sabemos que no nos darán buenos resultados (si procede), configurar el tipo de validación a usar, etc.
Una vez tengamos definidas todas las fases, el experimento empezará a ejecutarse en el contexto de computación que hayamos elegido hasta que se agote el tiempo de ejecución o bien lleguemos al límite de la métrica de rendimiento establecido. Podremos ver como van evolucionando las diferentes ejecuciones y su resultado. Al final AutoML siempre genera dos modelos de ensemble, voting y stacking. En nuestro caso, como se ve en la siguiente captura, es el que mejor rendimiento ha alcanzado
Podemos aplicar automáticamente interpretabilidad sobre éste modelo (a pesar de ser un ensemble de modelo, habitualmente considerado una caja negra) pero también sobre cualquier otra que quisieramos para analizar en profundidad su rendimiento y entender si tenemos algún tipo de sesgo o fallo relativo al entendimiento del dataset.
Finalmente, tenemos el modelo (el pipeline realmente, compuesto por el preprocesado del dato y el modelo entrenado) disponible para descargarlo en formato .pkl y aplicarlo donde necesitemos o para publicarlo directamente sobre un cluster de inferencia (ACI ó AKS)
Designer
Para los más veteranos/as del mundo de ML en Azure recordaréis que durante unos años, además de las VMs y HDInsight teníamos como único recurso el Azure ML Studio. Ésta herramienta gráfica es muy útil para prototipado rápido y explicar los diferentes flujos de información que podemos generar para una solución de ML, pero estaba limitado en lo referente a versionado de soluciones, escalabilidad e integración con otros servicios y plataformas.
Con Designer tenemos una experiencia muy parecida a la de Azure ML Studio (ahora llamado Azure ML Studio Classic) pero con una interfaz renovada y basándonos en computación remota como el resto de experimentos de Azure ML Services. Así, podemos diseñar y ejecutar prototipos hasta que estemos contentos con el resultado y después, con sólo cambiar el recurso de computación que ejecuta cierta fase del pipeline, escalar nuestra potencia de cómputo tanto como necesitemos. Esto lo convierte en una herramienta muy adecuada para usuarios/as que ya conocen los principios de ML y quieren desarrollar soluciones sin meterse a los pormenores del código o para Data Scientists más experimentados pero que quieren crear soluciones visuales rápidas y ser capaces de escalarlas a soluciones de nivel empresarial sin limitaciones de recursos.
Éste servicio está, como casi todos en Azure, en desarrollo constante, y está en el roadmap del equipo de producto seguir añadiendo funcionalidades e integraciones con otras piezas de Azure para hacer las soluciones de Machine Learning parte integral y pervasiva de la plataforma de datos de Azure.
Seguid atentos a más post más detallados sobre soluciones que implementamos en nuestros clientes y mejoras en la plataforma que están por venir durante 2020.
Felices predicciones! 🙂
¿Quieres formarte en Machine Learning? En SolidQ venimos trabajando en proyectos de Machine Learning desde hace algunos años y esta experiencia nos ha servido para adaptar nuestro conocimiento y crear los contenidos formativos objeto de este Módulo de Machine Learning con el que adquirir nuevos conceptos y conocimientos relacionados con analítica avanzada, dar el salto para no quedarte en el BI Tradicional” y seguir creciendo como profesional. Aprovecha la oportunidad y no dejes escapar el descuento que tenemos para ti… ¡antes de que se agote!
¿Quieres poner en marcha tu proyecto de Machine Learning? Conseguir el éxito en proyectos de analítica avanzada y su monetización requiere de datos, un buen modelo… y su interpretación asociada al caso de negocio. Esta combinación es imprescindible para que el proyecto tenga sentido y sea rentable. Por esta razón, durante nuestro Ideation Workshop nos reunimos en una sesión con todas las partes implicadas de tu equipo, para poner en contexto el proyecto y asegurar tanto su viabilidad técnica como los hitos de negocio en términos de rentabilidad. ¡Infórmate! Mira: Machine Learning Ideation Workshop: ¿Cómo empiezo mi proyecto?