Nota
L'accesso a questa pagina richiede l'autorizzazione. È possibile provare ad accedere o modificare le directory.
L'accesso a questa pagina richiede l'autorizzazione. È possibile provare a modificare le directory.
A volte il messaggio in arrivo non contiene tutto ciò di cui hai bisogno. Una lettura della temperatura potrebbe arrivare con un ID dispositivo, ma il nome visualizzato, la posizione e l'offset di calibrazione sono memorizzati in una tabella di ricerca separata. L'arricchimento consente di integrare i dati esterni all'interno delle regole di trasformazione.
Per una panoramica dei grafici del flusso di dati, vedere Panoramica dei grafici del flusso di dati.
Le trasformazioni utilizzano un linguaggio di espressione per calcolare valori, condizioni di test e campi di riferimento. Le espressioni si riferiscono agli input per posizione, non per nome: il primo input nella inputs lista è $1, il secondo è $2, e così via. Funzioni integrate come cToF convertono e manipolano tali valori.
Per l'elenco completo di operatori, funzioni, tipi di dati e campi di metadati, consulta il riferimento Expressions.
L'arricchimento è opzionale, ed è una caratteristica separata dai dataset che potresti definire su un asset. Nei grafici di flusso di dati, un dataset significa sempre un dataset di contestualizzazione letto dallo store di stati. Se i tuoi messaggi contengono già i campi necessari, non è necessario configurare i dataset.
L'arricchimento funziona con le trasformazioni map, filter e branch e con le regole trigger nelle trasformazioni window per la versione 1.1 o successive.
Prerequisiti
- Istanza di Operazioni di Azure IoT distribuita in un cluster Kubernetes. Per altre informazioni, vedere Deploy Operazioni di Azure IoT.
- La distribuzione crea automaticamente un endpoint di registro predefinito chiamato
defaultche punta amcr.microsoft.com.
Gli esempi interfaccia della riga di comando di Azure in questo articolo usano variabili di ambiente così puoi impostare ogni valore una volta e poi copiare e incollare i comandi as-is. Se stai usando l'ambiente Operazioni di Azure IoT Codespaces dal quickstart, queste variabili sono già impostate per te e puoi saltare questo passaggio. Altrimenti, imposta le seguenti variabili di ambiente nella tua shell prima di eseguire i comandi.
I seguenti script impostano le variabili di ambiente più comunemente utilizzate:
| Variabile di ambiente | Descrizione |
|---|---|
SUBSCRIPTION_ID |
L'ID dell'abbonamento che contiene la tua istanza Operazioni di Azure IoT. |
RESOURCE_GROUP |
Il nome del gruppo di risorse che contiene la tua istanza Operazioni di Azure IoT. |
AIO_INSTANCE_NAME |
Il nome della tua istanza Operazioni di Azure IoT. Per elencare le tue istanze, esegui az iot ops list -o table. |
CLUSTER_NAME |
Il nome del cluster Kubernetes abilitato Azure Arc che ospita la tua istanza. |
LOCATION |
La regione Azure da utilizzare per nuove risorse, ad esempio eastus. |
SUBSCRIPTION_ID=<subscription-id>
RESOURCE_GROUP=<resource-group-name>
AIO_INSTANCE_NAME=<instance-name>
CLUSTER_NAME=<cluster-name>
LOCATION=<region>
Devi solo impostare le variabili utilizzate in questo articolo. Questo articolo potrebbe utilizzare variabili ambientali aggiuntive per i nomi delle risorse che scegli. L'articolo spiega come posizionarli dove vengono introdotti.
Configurare l'archivio di stato
Il runtime legge i record del set di dati dall'archivio stati distribuito di Operazioni IoT di Azure. Ogni chiave del set di dati esegue il mapping a uno o più record in formato NDJSON (un oggetto JSON per riga). Il runtime memorizza i record e riceve notifiche di modifica, quindi gli aggiornamenti dello state store entrano in vigore durante l'elaborazione.
Per informazioni sulla configurazione dell'archivio stati distribuito, vedere Panoramica dell'archivio stati.
Popola la chiave dell'archivio di stato
Il negozio statale non è pre-popolato. Scrivi i record del dataset su di essa tramite MQTT usando il comando dello SET state store. Per il dataset device-metadata as device configurato più avanti in questo articolo, pubblica la seguente richiesta per inizializzare due record NDJSON (uno per riga) con la chiave device-metadata. Includere ogni campo citato dalle regole che utilizzano questo dataset, inclusi location. L'esempio Deploy a data flow graph with enrichment viene utilizzato location più avanti in questo articolo. Altrimenti, il campo si risolve in null per ogni messaggio:
mosquitto_pub -h <BROKER_HOST> -p <BROKER_PORT> -V mqttv5 -q 1 \
-t 'statestore/v1/FA9AE35F-2F64-47CD-9BFF-08E2B32A0FE8/command/invoke' \
-D publish response-topic 'clients/dataflow-docs-client/services/statestore/_any_/command/invoke/response' \
-D publish correlation-data '1' \
-D publish user-property __ts "$(date +%s%3N):0:dataflow-docs-client" \
-m $'*3\r\n$3\r\nSET\r\n$15\r\ndevice-metadata\r\n$153\r\n{"deviceId":"dev-001","displayName":"Line 1 Sensor","location":"Building A"}\n{"deviceId":"dev-002","displayName":"Line 2 Sensor","location":"Building B"}\r\n'
I valori $15 e $153 sono le lunghezze in byte della chiave (device-metadata) e del valore successivi. Una risposta vincente SET con +OK l'argomento della risposta. Per il formato completo della richiesta, le proprietà MQTT v5 richieste e i codici di risposta, si veda il riferimento al protocollo state store.
Configurare un set di dati
Definisci i dataset nell'array datasets al livello principale della configurazione delle regole per le trasformazioni map, filter e branch.
Per le trasformazioni delle finestre (versione 1.1 o successiva), configurare i dataset all'interno della triggers configurazione. Per ulteriori dettagli, vedi Aggregare i dati con trasformazioni a finestra nei grafi del flusso di dati.
Nella configurazione della trasformazione aggiungere un set di dati. Configurare:
| Impostazione | Descrizione |
|---|---|
| Chiave dello State Store | Chiave in cui vengono archiviati i record del set di dati. Usare as per assegnare un alias , ad esempio device-metadata as device. |
| Corrispondenze di input | Campi da confrontare: uno dal messaggio di origine ($source.<field>) e uno dal set di dati ($context.<field>). |
| Espressione di corrispondenza | Espressione booleana , ad esempio $1 == $2. |
Ogni voce del set di dati ha queste proprietà:
| Proprietà | Obbligatorio | Descrizione |
|---|---|---|
key |
Sì | Chiave dell'archivio stati in cui vengono archiviati i record del set di dati. Supporta un alias facoltativo con la as parola chiave . Per popolare questa chiave, pubblica una SET richiesta su MQTT (vedi Popolare la chiave dello stato del store). |
dynamicValues |
No | Elenco dei percorsi dei campi del messaggio sostituito nei $N segnaposto in key, permettendo al runtime di derivare la chiave di stato per ogni messaggio.
Vedi Tasti dinamiche. |
inputs |
Sì | Elenco dei riferimenti di campo utilizzati nell'espressione di corrispondenza. Ogni voce utilizza un prefisso $source. o $context.. |
expression |
Sì | Espressione booleana che determina quale record del set di dati corrisponde al messaggio in arrivo. |
Chiave e alias
Il key valore è la chiave dell'archivio stati che il runtime legge. Assegna un alias più breve usando la as parola chiave. Ad esempio, datasets.parag10.rule42 as position consente di fare riferimento ai campi come $context(position).WorkingHours.
Una chiave può anche essere un template che il runtime risolve separatamente per ogni messaggio. Per maggiori informazioni, vedi Chiavi dinamiche.
Chiavi dinamiche
Un disturbo statico key funziona bene quando arricchisci ogni messaggio dallo stesso record dello store statale. Ma a volte ogni messaggio ha bisogno di un record diverso. Ad esempio, con i dati di calibrazione per dispositivo, il record da consultare dipende da un campo nel messaggio in arrivo.
Invece di distribuire un set di dati separato (e un grafo separato) per ogni possibile valore di ricerca, usa key come modello con $1, $2 e così via come segnaposto. Aggiungi una dynamicValuesproprietà che elenchi il campo del messaggio da sostituire a ciascun segnaposto. L'runtime risolve il template per ogni messaggio prima di interrogare lo state store.
Suggerimento
Abbina una dinamica key a un alias usando as. L'alias, non la chiave risolta, è il nome fisso che fai riferimento nelle regole come $context(<alias>).<field>. Mantieni l'alias come identificatore stabile anche se la chiave sottostante cambia per ogni messaggio.
Prerequisito: Compilare una chiave di stato dinamica
Poiché la chiave risolta è guidata dai dati, devi riempire lo store di stato con un record per ogni valore risolto che ti aspetti di cercare. Nell'esempio della sezione seguente, per un messaggio con sensorId: "TEMP-42", il runtime cerca calibration:TEMP-42, quindi pubblica una SET richiesta per quella chiave esatta. Il record deve includere ogni campo utilizzato dalla corrispondenza inputs del dataset (qui, sensorId, confrontato con quello $source.sensorIddel messaggio in arrivo ), oltre a qualsiasi campo con cui le regole arricchiscono, come offset. Altrimenti, la corrispondenza non riesce mai e i campi di arricchimento restano non disponibili:
mosquitto_pub -h <BROKER_HOST> -p <BROKER_PORT> -V mqttv5 -q 1 \
-t 'statestore/v1/FA9AE35F-2F64-47CD-9BFF-08E2B32A0FE8/command/invoke' \
-D publish response-topic 'clients/dataflow-docs-client/services/statestore/_any_/command/invoke/response' \
-D publish correlation-data '1' \
-D publish user-property __ts "$(date +%s%3N):0:dataflow-docs-client" \
-m $'*3\r\n$3\r\nSET\r\n$19\r\ncalibration:TEMP-42\r\n$33\r\n{"sensorId":"TEMP-42","offset":5}\r\n'
I valori $19 e $33 sono le lunghezze in byte della chiave (calibration:TEMP-42) e del valore successivi. Una risposta vincente SET con +OK l'argomento della risposta. Per il formato completo della richiesta, le proprietà MQTT v5 richieste e i codici di risposta, si veda il riferimento al protocollo state store.
Configura un dataset con valori dinamici
Nella configurazione di trasformazione, aggiungi un dataset e configura:
| Impostazione | Descrizione |
|---|---|
| Chiave dello State Store | Un template come calibration:$1 as calibration, dove un campo di messaggio sostituisce $1 al momento dell'elaborazione. Per popolare la chiave risolta, pubblica una SET richiesta su MQTT (vedi Popolare una chiave di stato dinamico). |
| Valori dinamici | Il campo messaggio da sostituire per ogni segnaposto, in ordine (ad esempio, sensorId). |
| Input corrispondenti / Espressione corrispondente | Configura allo stesso modo di un dataset a chiave statica. |
Per un messaggio con sensorId: "TEMP-42", il runtime risolve il template a calibration:TEMP-42 prima di interrogare lo status store. Il campo del offset record abbinato diventa disponibile come $context(calibration).offset.
Valori predefiniti per i campi mancanti
Ogni voce in dynamicValues può includere un valore predefinito ??, utilizzato quando il campo del messaggio è mancante o null. Senza un valore predefinito, un campo mancante o null causa il fallimento dell'elaborazione di quel messaggio.
{
"key": "calibration:$1 as calibration",
"dynamicValues": ["sensorId ?? \"unknown\""]
}
Sfuggire a un letterale $
Se le chiavi dell'archivio di stato nel sistema contengono già un carattere letterale $, esegui l'escape come $$ nel template. Solo $N (a $ seguita da cifre) viene trattata come segnaposto.
$$ produce sempre un singolo valore letterale $.
{
"key": "rate:$$USD:$1",
"dynamicValues": ["region ?? \"us\""]
}
Per un messaggio con region: "eu", questo si risolve in rate:$USD:eu.
Chiavi composte
Un template può fare riferimento a più di un campo di messaggio. Ogni $N corrisponde alla voce corrispondente in dynamicValues, nell'ordine:
{
"key": "line:$1:station:$2 as lineStatus",
"dynamicValues": ["lineId ?? \"unknown\"", "stationId ?? \"0\""]
}
Per un messaggio con lineId: "L-3" e stationId: "7", questo si risolve in line:L-3:station:7.
Note
Solo i campi di messaggio stringa, numero e booleani possono essere sostituiti in una chiave. I campi oggetto e array non sono supportati come valori chiave dinamici. Usarne uno comporta un errore quando il messaggio viene elaborato.
Importante
I seguenti errori vengono convalidati quando viene applicato il grafo, non quando vengono elaborati i messaggi:
- Un segnaposto
$Nil cui indice è maggiore del numero di voci indynamicValues. - Una lista
dynamicValuesconfigurata su unkeyche non contiene alcun segnaposto$Nsenza caratteri di escape. - Un segnaposto malformato, come
$0o un$non seguito da una cifra.
Correggi questi errori prima di applicare il grafico. Non emergono dopo come fallimenti nell'elaborazione dei messaggi.
Poiché la chiave risolta è guidata dai dati, può essere diversa per ogni messaggio. Se si abilita la registrazione diagnostica o la traccia per le ricerche di arricchimento, verrà visualizzata la chiave resolved (ad esempio, calibration:TEMP-42), non il modello configurato.
Input di set di dati
Ogni voce nella inputs matrice usa un prefisso per indicare da dove proviene il valore:
-
$source.<field>: legge dal messaggio in arrivo. -
$context.<field>: legge dal record del set di dati in fase di valutazione.
Gli input possono apparire in qualsiasi ordine ed è possibile combinare liberamente i riferimenti $source e $context. Gli input con caratteri jolly non sono supportati nelle definizioni dei set di dati.
Espressione di corrispondenza
expression viene valutato come un booleano. Il runtime carica il set di dati dall'archivio di stato come NDJSON (un oggetto JSON per riga), scorre i record e restituisce il primo record in cui l'espressione restituisce true.
Se nessun record corrisponde, i campi di arricchimento non sono disponibili. Le regole che dipendono da queste continuano a essere eseguite, ma scrivono il valore null nel campo di output invece di contrassegnare il messaggio come non riuscito. La regola non viene rimossa dall'output, solo il suo valore risolto è null.
Usare i dati arricchiti nelle regole
Fai riferimento ai campi di record abbinati in un array di qualsiasi regola inputs usando $context(<alias>).<fieldPath>.
Esempio di mappa
Aggiungere regole mappa che fanno riferimento a campi arricchiti:
| Inserimento | Risultato |
|---|---|
$context(position).WorkingHours |
WorkingHours |
rawValue e $context(product).multiplier |
adjustedValue (espressione: $1 * $2) |
Esempio di filtro
Aggiungere una regola di filtro con input rawValue, $context(limits).multipliere $context(limits).baseLimite l'espressione $1 * $2 > $3.
Esempio di filiale
Configurare una regola di ramo con input quantity, $context(mult).factore $context(mult).thresholde l'espressione $1 * $2 > $3.
Caratteri jolly con set di dati
Nelle regole della mappa usare $context(<alias>).* per copiare tutti i campi di primo livello dal record del set di dati corrispondente:
Aggiungere una regola della mappa con input $context(device).* e output *.
I jolly possono anche colpire un oggetto annidato all'interno del record del dataset. Ad esempio, $context(device).configuration.* copia solo i campi in configuration.
Solo le regole della mappa supportano input di arricchimento wildcard. Le regole di filtro e di ramo non supportano gli input con caratteri jolly.
Distribuire un grafico del flusso di dati con arricchimento
Nell'esperienza Operazioni creare un grafico del flusso di dati con arricchimento:
- Aggiungere un'origine che esegue la lettura dall'argomento MQTT.
- Aggiungere una trasformazione mappa . Nella configurazione del set di dati aggiungere un set di dati con la chiave dell'archivio stati e la condizione di corrispondenza.
- Nelle regole della mappa, si fanno riferimento ai campi arricchiti usando
$context(<alias>).<field>la sintassi. - Aggiungere una destinazione che invia all'argomento di output.
Limitazioni dell'arricchimento
- Il supporto delle finestre funziona solo tramite trigger. Nelle trasformazioni di finestra, l'arricchimento del set di dati è disponibile per le regole di attivazione (
triggers.datasets) inazureiotoperations/graph-dataflow-window:1.1.0o versioni successive, non per le regole di accumulo. - La prima partita vince. Il runtime usa il primo record in cui l'espressione restituisce
true. - I match mancanti non falliscono il messaggio. Se nessun record del dataset corrisponde, le regole che fanno riferimento
$context(<alias>)ai campi continuano a eseguirsi ma risolvono innull. Il campo di output è presente con unnullvalore, non omesso. La trasformazione non fallisce. - Gli errori dell'archivio stati vengono propagati. Se l'archivio di stato non è raggiungibile, la trasformazione non riesce per il messaggio.
- Nessun input con caratteri jolly nelle definizioni del set di dati. Ogni input deve essere un riferimento specifico
$source.<field>o$context.<field>.