Detección de anomalías multivariadas

En este tutorial se muestra cómo entrenar un modelo de detección de anomalías multivariante en un cuaderno de Fabric mediante datos de ejemplo almacenados en un centro de eventos. A continuación, usa el modelo entrenado en un conjunto de consultas de KQL para evaluar nuevos datos y visualizar las anomalías.

Para obtener información general, consulte Detección de anomalías multivariante en Microsoft Fabric: información general.

Requisitos previos

  • Un espacio de trabajo con una capacidad habilitada para Microsoft Fabric.
  • Un rol del área de trabajo de Administrador, Colaborador o Miembro. Necesita este nivel de permiso para crear elementos como un entorno.
  • Una instancia de Eventhouse en el área de trabajo con una base de datos.
  • Archivo de datos de ejemplo.
  • Cuaderno de ejemplo.

Parte 1: Activar la disponibilidad de OneLake

Active la disponibilidad de OneLake antes de cargar los datos en el centro de eventos. Esta configuración hace que los datos ingeridos estén disponibles en OneLake para que pueda acceder a la misma tabla desde un cuaderno más adelante en el tutorial.

  1. En el área de trabajo, abra el centro de eventos que creó en los requisitos previos y, a continuación, seleccione la base de datos donde desea almacenar los datos.

  2. En el panel Detalles de la base de datos , establezca Disponibilidad de OneLake en Activado.

    Captura de pantalla de la habilitación de la disponibilidad de OneLake en el centro de eventos.

Parte 2: Activar el complemento KQL Python

En este paso, activa el complemento de Python en tu eventhouse. Este paso es necesario para ejecutar el código de Python en el conjunto de consultas KQL de la parte 9: Predecir anomalías en un conjunto de consultas KQL. Seleccione la imagen Python que incluye el paquete time-series-anomaly-detector.

  1. En Eventhouse, seleccione Eventhouse>Complementos en la cinta de opciones.

  2. En el panel Complementos, establezca extensión del lenguaje Python en Activado.

  3. Seleccione Python 3.11.7 DL.

  4. Seleccione Listo.

    Captura de pantalla que muestra cómo habilitar el paquete DL de Python 3.11.7 en el centro de eventos.

Parte 3: Creación de un entorno de Spark

En este paso, creará un entorno de Spark para ejecutar el cuaderno que entrena el modelo de detección de anomalías multivariante. Para más información, consulte Creación y administración de entornos.

  1. En el área de trabajo, seleccione + Nuevo elemento y, a continuación, seleccione Entorno.

    Captura de pantalla del icono Entorno en la ventana Nuevo elemento.

  2. Escriba MVAD_ENV para el nombre del entorno y, a continuación, seleccione Crear.

  3. En Bibliotecas, selecciona Bibliotecas públicas.

  4. Selecciona Agregar desde PyPI.

  5. En el cuadro de búsqueda, escriba time-series-anomaly-detector. En el cuadro Versión , escriba 0.3.9.

  6. Seleccione Guardar.

    Captura de pantalla de cómo agregar el paquete PyPI al entorno de Spark.

  7. Selecciona la pestaña Inicios en el entorno.

  8. Selecciona el icono Publicar del desplegable.

  9. Seleccione Publicar todo. Este paso puede tardar varios minutos en completarse.

    Captura de pantalla de la publicación del entorno.

Parte 4: Carga de datos en el centro de eventos

  1. En el centro de eventos, mantenga el puntero sobre la base de datos KQL donde desea almacenar los datos y, a continuación, seleccione El menú Más [...]>Obtención de datos>Archivo local.

    Captura de pantalla de obtención de datos del archivo local.

  2. Seleccione + Nueva tabla y escriba demo_stocks_change como nombre de tabla.

  3. En el cuadro de diálogo de carga, seleccione Examinar archivos y cargue el archivo de datos de ejemplo que descargó en Requisitos previos.

  4. Seleccione Siguiente.

  5. En la sección Inspeccionar los datos, compruebe que Primera fila es el encabezado de columna está establecido en Activado.

  6. Seleccione Finalizar.

  7. Una vez que los datos estén subidos, selecciona Cerrar.

Parte 5: Copiar la ruta de acceso de OneLake

Seleccione la tabla demo_stocks_change. En el panel Detalles de la tabla, seleccione Carpeta OneLake para copiar la ruta de acceso de OneLake en el Portapapeles. Guarde la ruta de acceso en un editor de texto para su uso posterior.

Captura de pantalla de la copia de la ruta de acceso de OneLake.

Parte 6: Preparar el cuaderno

  1. Seleccione su área de trabajo.

  2. Seleccione Importar>Notebook>desde este equipo.

  3. Seleccione Cargar y elija el cuaderno que descargó en Requisitos previos.

  4. Una vez cargado el cuaderno, puede encontrar y abrir el cuaderno desde el área de trabajo.

  5. En la cinta de opciones superior, seleccione la lista desplegable Predeterminado del área de trabajo y, a continuación, seleccione el entorno que creó en el paso anterior.

    Captura de pantalla de la selección del entorno en el bloc de notas.

Parte 7: Ejecutar el cuaderno

  1. Importar paquetes estándar.

    import numpy as np
    import pandas as pd
    
  2. Spark necesita un URI de ABFSS para conectarse de forma segura al almacenamiento de OneLake, por lo que define una función auxiliar que convierte el URI de OneLake en un URI de ABFSS.

    def convert_onelake_to_abfss(onelake_uri):
        if not onelake_uri.startswith('https://'):
            raise ValueError("Invalid OneLake URI. It should start with 'https://'.")
        uri_without_scheme = onelake_uri[8:]
        parts = uri_without_scheme.split('/')
        if len(parts) < 3:
            raise ValueError("Invalid OneLake URI format.")
        container_name = parts[1]
        path = '/'.join(parts[2:])
        abfss_uri = f"abfss://{container_name}@{parts[0]}/{path}"
        return abfss_uri
    
  3. Sustituya OneLakeTableURI por el URI de OneLake que copió en Parte 5: Copiar la ruta de OneLake y, a continuación, cargue la tabla demo_stocks_change en un marco de datos de pandas.

    onelake_uri = "OneLakeTableURI"  # Replace with your OneLake table URI.
    abfss_uri = convert_onelake_to_abfss(onelake_uri)
    print(abfss_uri)
    
    df = spark.read.format('delta').load(abfss_uri)
    df = df.toPandas()
    df['Date'] = pd.to_datetime(df['Date'])
    df = df.set_index('Date').sort_index()
    print(df.shape)
    df.head(3)
    
  4. Ejecuta las celdas siguientes para preparar los marcos de datos (dataframes) de entrenamiento y pronóstico.

    Nota:

    Las predicciones reales se ejecutan en el eventhouse en Parte 9: Predecir anomalías en un conjunto de consultas KQL. En un escenario de producción, normalmente puntua los nuevos datos de streaming. En este tutorial, el conjunto de datos se divide por fecha en intervalos de entrenamiento y predicción para simular datos históricos y entrantes.

    features_cols = ['AAPL', 'AMZN', 'GOOG', 'MSFT', 'SPY']
    cutoff_date = pd.Timestamp('2023-01-01')
    
    train_df = df.loc[df.index < cutoff_date, features_cols]
    print(train_df.shape)
    train_df.head(3)
    
    train_len = len(train_df)
    predict_len = len(df) - train_len
    print(f'Total samples: {len(df)}. Split to {train_len} for training, {predict_len} for testing')
    
  5. Ejecute las celdas para entrenar el modelo y guárdela en el registro de modelos de MLflow de Fabric.

    from anomaly_detector import MultivariateAnomalyDetector
    model = MultivariateAnomalyDetector()
    
    sliding_window = 200
    params = {"sliding_window": sliding_window}
    
    model.fit(train_df, params=params)
    
    model_name = "mvad_5_stocks_model"
    
    import mlflow
    
    with mlflow.start_run():
        mlflow.log_params(params)
        mlflow.set_tag("Training Info", "MVAD on 5 Stocks Dataset")
    
        model_info = mlflow.pyfunc.log_model(
            python_model=model,
            artifact_path="mvad_artifacts",
            registered_model_name=model_name,
        )
    
  6. Ejecuta la siguiente celda para obtener la ruta de acceso del modelo registrado que usarás más adelante para la predicción en el entorno de pruebas de Python de KQL.

    from mlflow.tracking import MlflowClient
    
    client = MlflowClient()
    mvs = client.search_model_versions(f"name='{model_name}'")
    latest = max(mvs, key=lambda v: v.creation_timestamp)
    model_abfss = latest.source
    print(model_abfss)
    
  7. Copie el URI del modelo de la salida de la última celda. Se usa en la parte 9.

Parte 8: Crear un conjunto de consultas KQL

Para obtener información general, consulta Creación de un conjunto de consultas KQL.

  1. En el área de trabajo, seleccione + Nuevo elemento>KQL Queryset.
  2. Escriba MultivariateAnomalyDetectionTutorialy, a continuación, seleccione Crear.
  3. En la ventana del catálogo de OneLake , seleccione la base de datos KQL donde almacenó los datos.
  4. Seleccione Conectar.

Parte 9: Predicción de anomalías en un conjunto de consultas KQL

  1. Ejecute la consulta siguiente .create-or-alter function para definir la predict_fabric_mvad_fl() función almacenada:

    .create-or-alter function with (folder = "Packages\\ML", docstring = "Predict MVAD model in Microsoft Fabric")
    predict_fabric_mvad_fl(samples:(*), features_cols:dynamic, artifacts_uri:string, trim_result:bool=false)
    {
        let s = artifacts_uri;
        let artifacts = bag_pack('MLmodel', strcat(s, '/MLmodel;impersonate'), 'conda.yaml', strcat(s, '/conda.yaml;impersonate'),
                                 'requirements.txt', strcat(s, '/requirements.txt;impersonate'), 'python_env.yaml', strcat(s, '/python_env.yaml;impersonate'),
                                 'python_model.pkl', strcat(s, '/python_model.pkl;impersonate'));
        let kwargs = bag_pack('features_cols', features_cols, 'trim_result', trim_result);
        let code = ```if 1:
            import os
            import shutil
            import mlflow
            work_dir = os.environ.get("UPLOAD_PATH")
            model_dir = work_dir + '/mvad_model'
            model_data_dir = model_dir + '/data'
            os.mkdir(model_dir)
            shutil.move(work_dir + '/MLmodel', model_dir)
            shutil.move(work_dir + '/conda.yaml', model_dir)
            shutil.move(work_dir + '/requirements.txt', model_dir)
            shutil.move(work_dir + '/python_env.yaml', model_dir)
            shutil.move(work_dir + '/python_model.pkl', model_dir)
            features_cols = kargs["features_cols"]
            trim_result = kargs["trim_result"]
            test_data = df[features_cols]
            model = mlflow.pyfunc.load_model(model_dir)
            predictions = model.predict(test_data)
            predict_result = pd.DataFrame(predictions)
            samples_offset = len(df) - len(predict_result)        # this model doesn't output predictions for the first sliding_window-1 samples
            if trim_result:                                       # trim the prefix samples
                result = df[samples_offset:]
                result.iloc[:,-4:] = predict_result.iloc[:, 1:]   # no need to copy 1st column which is the timestamp index
            else:
                result = df                                       # output all samples
                result.iloc[samples_offset:,-4:] = predict_result.iloc[:, 1:]
            ```;
        samples
        | evaluate python(typeof(*), code, kwargs, external_artifacts=artifacts)
    }
    
  2. Ejecute la siguiente consulta de predicción. Reemplace enter your model URI here por el URI que copió al final de la parte 7: Ejecute el cuaderno.

    La consulta detecta anomalías multivariantes en las cinco acciones mediante el modelo entrenado y, a continuación, muestra los resultados como un anomalychart. Los puntos anómalos se muestran en el primer stock (AAPL), pero representan anomalías en el comportamiento conjunto de las cinco acciones en una fecha determinada.

    let cutoff_date=datetime(2023-01-01);
    let num_predictions=toscalar(demo_stocks_change | where Date >= cutoff_date | count);   //  number of latest points to predict
    let sliding_window=200;                                                                 //  should match the window that was set for model training
    let prefix_score_len = sliding_window/2+min_of(sliding_window/2, 200)-1;
    let num_samples = prefix_score_len + num_predictions;
    demo_stocks_change
    | top num_samples by Date desc
    | order by Date asc
    | extend is_anomaly=bool(false), score=real(null), severity=real(null), interpretation=dynamic(null)
    | invoke predict_fabric_mvad_fl(pack_array('AAPL', 'AMZN', 'GOOG', 'MSFT', 'SPY'),
                // NOTE: Update artifacts_uri to model path
                artifacts_uri='enter your model URI here',
                trim_result=true)
    | summarize Date=make_list(Date), AAPL=make_list(AAPL), AMZN=make_list(AMZN), GOOG=make_list(GOOG), MSFT=make_list(MSFT), SPY=make_list(SPY), anomaly=make_list(toint(is_anomaly))
    | render anomalychart with(anomalycolumns=anomaly, title='Stock price changes in % with anomalies')
    

El gráfico de anomalías resultante es similar a la siguiente imagen:

Captura de pantalla de la salida de anomalías multivariantes.

Limpieza de recursos

Cuando termine el tutorial, elimine los recursos que creó para evitar costos innecesarios:

  1. Navegue a la página principal del área de trabajo.
  2. Elimina el entorno que hayas creado en este tutorial.
  3. Elimine el cuaderno que haya creado en este tutorial.
  4. Elimine el centro de eventos o la base de datos que se usa en este tutorial.
  5. Elimina el conjunto de consultas KQL que hayas creado en este tutorial.