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.
In questo articolo si usa Azure Developer CLI (azd) per creare una funzione trigger di Hub eventi per l'elaborazione di eventi in tempo reale nelle Funzioni di Azure. Dopo aver verificato il codice in locale, lo distribuisci in una nuova app di funzioni serverless in esecuzione su un piano Flex Consumption di Azure.
L'origine del progetto usa azd per creare l'app per le funzioni e le risorse correlate e per distribuire il codice in Azure. Questa distribuzione segue le procedure consigliate correnti per distribuzioni di Funzioni di Azure sicure e scalabili.
Per impostazione predefinita, il piano Flex Consumption segue un modello di fatturazione con pagamento in base al consumo, il che significa che è possibile completare questo articolo e sostenere solo un costo ridotto di pochi centesimi di USD o inferiore nell'account Azure.
Questo articolo supporta la versione 4 del modello di programmazione Node.js per Funzioni di Azure.
Questo articolo supporta la versione 2 del modello di programmazione Python per Funzioni di Azure.
Prerequisiti
-
Java 21 Developer Kit
- Impostare la variabile di ambiente
JAVA_HOMEsul percorso di installazione della versione corretta del Java Development Kit (JDK).
- Impostare la variabile di ambiente
- Apache Maven 3.8.x
- Node.js 22 o versione successiva
- Python 3.11 o versione successiva
Un account Azure con una sottoscrizione attiva. Creare un account gratuito.
Inizializzare il progetto
Usare il azd init comando per creare un progetto di codice di Funzioni di Azure locale da un modello.
Nel terminale locale o nel prompt dei comandi eseguire questo comando azd init in una cartella vuota:
azd init --template functions-quickstart-dotnet-azd-eventhub -e eventhub-dotnet
Questo comando esegue il pull dei file di progetto dal repository template e inizializza il progetto nella cartella corrente. Il flag -e imposta un nome per l'ambiente corrente. In azdl'ambiente mantiene un contesto di distribuzione univoco per l'app ed è possibile definire più di uno. Il nome dell'ambiente viene usato anche nel nome del gruppo di risorse creato in Azure.
Nel terminale locale o nel prompt dei comandi eseguire questo comando azd init in una cartella vuota:
azd init --template functions-quickstart-typescript-azd-eventhub -e eventhub-ts
Questo comando esegue il pull dei file di progetto dal repository template e inizializza il progetto nella cartella corrente. Il flag -e imposta un nome per l'ambiente corrente. In azdl'ambiente mantiene un contesto di distribuzione univoco per l'app ed è possibile definire più di uno. Il nome dell'ambiente viene usato anche nel nome del gruppo di risorse creato in Azure.
Nel terminale locale o nel prompt dei comandi eseguire questo comando azd init in una cartella vuota:
azd init --template functions-quickstart-python-azd-eventhub -e eventhub-py
Questo comando esegue il pull dei file di progetto dal repository template e inizializza il progetto nella cartella corrente. Il flag -e imposta un nome per l'ambiente corrente. In azdl'ambiente mantiene un contesto di distribuzione univoco per l'app ed è possibile definire più di uno. Il nome dell'ambiente viene usato anche nel nome del gruppo di risorse creato in Azure.
Creare e attivare un ambiente virtuale
Nella cartella principale, eseguire questi comandi per creare e attivare un ambiente virtuale denominato .venv:
python3 -m venv .venv
source .venv/bin/activate
Se Python non installa il pacchetto venv nella distribuzione Linux, eseguire il comando seguente:
sudo apt-get install python3-venv
Nel terminale locale o nel prompt dei comandi eseguire questo comando azd init in una cartella vuota:
azd init --template functions-quickstart-java-azd-eventhub -e eventhub-java
Questo comando esegue il pull dei file di progetto dal repository template e inizializza il progetto nella cartella corrente. Il flag -e imposta un nome per l'ambiente corrente. In azdl'ambiente mantiene un contesto di distribuzione univoco per l'app ed è possibile definire più di uno. Il nome dell'ambiente viene usato anche nel nome del gruppo di risorse creato in Azure.
Nel terminale locale o nel prompt dei comandi eseguire questo comando azd init in una cartella vuota:
azd init --template functions-quickstart-javascript-azd-eventhub -e eventhub-js
Questo comando esegue il pull dei file di progetto dal repository template e inizializza il progetto nella cartella corrente. Il flag -e imposta un nome per l'ambiente corrente. In azdl'ambiente mantiene un contesto di distribuzione univoco per l'app ed è possibile definire più di uno. Il nome dell'ambiente viene usato anche nel nome del gruppo di risorse creato in Azure.
Nel terminale locale o nel prompt dei comandi eseguire questo comando azd init in una cartella vuota:
azd init --template functions-quickstart-powershell-azd-eventhub -e eventhub-ps
Questo comando esegue il pull dei file di progetto dal repository template e inizializza il progetto nella cartella corrente. Il flag -e imposta un nome per l'ambiente corrente. In azdl'ambiente mantiene un contesto di distribuzione univoco per l'app ed è possibile definire più di uno. Il nome dell'ambiente viene usato anche nel nome del gruppo di risorse creato in Azure.
Creare risorse di Azure
Prima di poter eseguire localmente la funzione, è necessario creare un namespace e un hub Event Hubs in Azure. Usare azd provision per creare queste risorse e configurare le impostazioni locali aggiungendo il file dilocal.settings.json necessario.
Eseguire questo comando per accedere ad Azure:
azd auth loginSeguire le istruzioni per eseguire l'autenticazione usando l'account Azure.
Dalla cartella radice eseguire il comando seguente per creare le risorse di Azure:
azd provisionQuando richiesto, specificare questi parametri di distribuzione obbligatori:
Parametro Descrizione Sottoscrizione di Azure Sottoscrizione in cui crei le tue risorse. Località di Azure area di Azure in cui creare il gruppo di risorse che contiene le nuove risorse di Azure. Vengono visualizzate solo le aree che attualmente supportano il piano a consumo Flex. vnetEnabled Usare un valore di Falseper evitare il sovraccarico aggiuntivo della creazione di risorse di rete virtuale.Il
azd provisioncomando crea le risorse di Azure necessarie, tra cui uno spazio dei nomi e un hub di Hub eventi, un'app per le funzioni Flex Consumption, Application Insights e un account di archiviazione. Configura anche il file local.settings.json con le informazioni di connessione di Event Hubs.
Eseguire l'ambiente locale
In una finestra del terminale separata avviare l'emulatore di archiviazione Azurite:
azuriteIl processo host locale delle Funzioni usa l'emulatore Azurite per la connessione di archiviazione interna (
AzureWebJobsStorage) richiesta dal runtime.
Per avviare l'app per le funzioni, eseguire questi comandi in un terminale o nel prompt dei comandi per passare alla cartella del
srcprogetto e avviare l'app per le funzioni:cd src func start
Per avviare l'app per le funzioni, eseguire questo comando in un terminale o nel prompt dei comandi:
func start
Per compilare e avviare l'app per le funzioni, eseguire questi comandi in un terminale o nel prompt dei comandi:
mvn clean package mvn azure-functions:run
Per installare le dipendenze e avviare l'app per le funzioni, eseguire questi comandi in un terminale o nel prompt dei comandi:
npm install npm start
Per installare le dipendenze e avviare l'app per le funzioni, eseguire questi comandi in un terminale o nel prompt dei comandi:
cd src npm install npm start
Per avviare l'app per le funzioni, eseguire questo comando in un terminale o nel prompt dei comandi:
func start
Se richiesto, consentire la chiamata di Core Tools (func.exe) tramite il firewall.
Quando l'host delle funzioni viene avviato nella cartella del progetto locale, visualizza sul terminale le informazioni relative alle funzioni.
Questo esempio include una funzione trigger timer che genera automaticamente articoli di notizie ogni 10 secondi e li invia a Hub eventi. La funzione trigger di Hub eventi elabora quindi questi eventi ed esegue l'analisi del sentiment e il rilevamento dell'engagement.
L'output è simile a questo esempio:
[2026-03-02T22:37:30.151Z] Executing 'Functions.EventHubsTrigger' [2026-03-02T22:37:30.159Z] Trigger Details: PartitionId: 24, OffsetString: 0, EnqueueTimeUtc: 2026-03-02T22:37:29.1790000+00:00, SequenceNumber: 0, Count: 1, Offset: 0, PartionId: 24 [2026-03-02T22:37:30.169Z] ⭐ High-engagement article NEWS-20260302-0580CB82 (Views: 6123, Sentiment: 0.57) featured! [2026-03-02T22:37:30.174Z] 🔥 Viral article: NEWS-20260302-0580CB82 - 6,123 views [2026-03-02T22:37:30.181Z] 🌟 Featured article: NEWS-20260302-0580CB82 [2026-03-02T22:37:30.185Z] ✅ Successfully processed article NEWS-20260302-0580CB82 - 'Technology Breakthrough in Renewable Energy Technology' by Sarah Johnson [2026-03-02T22:37:30.191Z] 📰 Processed 1 news articles, 0 failed in batch of 1 [2026-03-02T22:37:30.196Z] 📊 NEWS BATCH SUMMARY: 1 articles | Total Views: 6,123 | Avg Views: 6,123 | Avg Sentiment: 0.57 | Status: [Featured: 1] [2026-03-02T22:37:30.200Z] 📂 Top Categories: [Health: 1] | Top Sources: [Innovation Weekly: 1] [2026-03-02T22:37:30.204Z] 🔥 Viral articles in batch: 1 [2026-03-02T22:37:30.207Z] Executed 'Functions.EventHubsTrigger' (Succeeded, Duration=55ms)
Al termine, premere CTRL+C nella finestra del terminale per arrestare il processo host
func.exe.Chiudere la finestra in cui è in esecuzione Azurite.
- Eseguire
deactivateper arrestare l'ambiente virtuale.
Esaminare il codice (facoltativo)
È possibile esaminare il codice che definisce la funzione trigger di Hub eventi:
using System.Text.Json;
using Azure.Messaging.EventHubs;
using Microsoft.Azure.Functions.Worker;
using Microsoft.Extensions.Logging;
namespace function_app;
public class EventHubsTrigger
{
private readonly ILogger<EventHubsTrigger> _logger;
private readonly NewsProcessingService _newsService;
public EventHubsTrigger(ILogger<EventHubsTrigger> logger, NewsProcessingService newsService)
{
_logger = logger;
_newsService = newsService;
}
[Function(nameof(EventHubsTrigger))]
public async Task Run([EventHubTrigger("news", Connection = "EventHubConnection")] EventData[] input)
{
var processedArticles = new List<NewsArticle>();
var failedEvents = 0;
foreach (var message in input)
{
try
{
var messageBody = message.EventBody.ToString();
// Parse the news article event
var article = ParseNewsArticleEvent(messageBody);
if (article != null)
{
processedArticles.Add(article);
}
else
{
failedEvents++;
}
}
catch (Exception ex)
{
failedEvents++;
_logger.LogWarning($"Error processing message: {ex.Message}");
}
}
// Log summary of this execution
_logger.LogInformation($"📰 Processed {processedArticles.Count} news articles, {failedEvents} failed in batch of {input.Length}");
È possibile esaminare il progetto modello completo here.
package com.function;
import com.microsoft.azure.functions.*;
import com.microsoft.azure.functions.annotation.*;
import java.time.Instant;
import java.util.*;
import java.util.logging.Logger;
/**
* Azure Function that processes messages from an input Event Hub,
* adds metadata, and sends processed messages to an output Event Hub.
*/
public class EventHubsTriggerFunction {
@FunctionName("EventHubsTrigger")
public void run(
@EventHubTrigger(
name = "messages",
eventHubName = "%INPUT_EVENTHUB_NAME%",
connection = "EventHubConnection",
cardinality = Cardinality.MANY)
List<String> messages,
@EventHubOutput(
name = "output",
eventHubName = "%OUTPUT_EVENTHUB_NAME%",
connection = "EventHubConnection")
OutputBinding<List<String>> output,
final ExecutionContext context) {
Logger logger = context.getLogger();
logger.info(String.format("🔄 Event hub function processing %d message(s)", messages.size()));
List<String> processedMessages = new ArrayList<>();
for (String message : messages) {
try {
logger.info("📨 Processing event: " + message);
// Create processed message with additional metadata
String processedMessage = String.format(
"{\"id\":\"%s\",\"message\":%s,\"timestamp\":\"%s\"}",
UUID.randomUUID().toString(),
message,
Instant.now().toString());
processedMessages.add(processedMessage);
logger.info("\u2728 Message processed: " + processedMessage);
} catch (Exception e) {
logger.severe("\u274C Error processing message: " + e.getMessage());
}
}
// Send processed messages to output Event Hub
if (!processedMessages.isEmpty()) {
output.setValue(processedMessages);
logger.info(String.format("📤 Sent %d message(s) to output Event Hub", processedMessages.size()));
}
}
}
È possibile esaminare il progetto modello completo here.
const { app, output } = require("@azure/functions");
const eventHubOutput = output.eventHub({
connection: 'EventHubConnection',
eventHubName: '%OUTPUT_EVENTHUB_NAME%'
});
async function EventHubsTrigger(messages, context) {
context.log(`🔄 Event hub function processing ${messages.length} message(s)`);
const processedMessages = [];
for (const message of messages) {
try {
// Parse the incoming message
const eventData = typeof message === 'string' ? JSON.parse(message) : message;
context.log('📨 Processing event:', eventData);
// Create processed message with additional metadata
const processedMessage = {
id: eventData.id || crypto.randomUUID(),
message: eventData.message || JSON.stringify(eventData),
timestamp: new Date().toISOString()
};
processedMessages.push(processedMessage);
context.log('✨ Message processed:', processedMessage);
} catch (error) {
context.error(`❌ Error processing message: ${error}`);
}
}
// Send processed messages to output Event Hub
if (processedMessages.length > 0) {
context.extraOutputs.set(eventHubOutput, processedMessages);
context.log(`📤 Sent ${processedMessages.length} message(s) to output Event Hub`);
}
}
app.eventHub('EventHubsTrigger', {
connection: 'EventHubConnection',
eventHubName: '%INPUT_EVENTHUB_NAME%',
cardinality: 'many',
extraOutputs: [eventHubOutput],
handler: EventHubsTrigger
});
È possibile esaminare il progetto modello completo here.
import { app, InvocationContext, output } from "@azure/functions";
interface EventMessage {
id: string;
message: string;
timestamp: string;
}
const eventHubOutput = output.eventHub({
connection: 'EventHubConnection',
eventHubName: '%OUTPUT_EVENTHUB_NAME%'
});
export async function EventHubsTrigger(messages: unknown[], context: InvocationContext): Promise<void> {
context.log(`🔄 Event hub function processing ${messages.length} message(s)`);
const processedMessages: EventMessage[] = [];
for (const message of messages) {
try {
// Parse the incoming message
const eventData = typeof message === 'string' ? JSON.parse(message) : message;
context.log('📨 Processing event:', eventData);
// Create processed message with additional metadata
const processedMessage: EventMessage = {
id: eventData.id || crypto.randomUUID(),
message: eventData.message || JSON.stringify(eventData),
timestamp: new Date().toISOString()
};
processedMessages.push(processedMessage);
context.log('✨ Message processed:', processedMessage);
} catch (error) {
context.error(`❌ Error processing message: ${error}`);
}
}
// Send processed messages to output Event Hub
if (processedMessages.length > 0) {
context.extraOutputs.set(eventHubOutput, processedMessages);
context.log(`📤 Sent ${processedMessages.length} message(s) to output Event Hub`);
}
}
app.eventHub('EventHubsTrigger', {
connection: 'EventHubConnection',
eventHubName: '%INPUT_EVENTHUB_NAME%',
cardinality: 'many',
extraOutputs: [eventHubOutput],
handler: EventHubsTrigger
});
È possibile esaminare il progetto modello completo here.
param($InputEvents, $TriggerMetadata)
Write-Host "🔄 Event hub function processing $($InputEvents.Count) message(s)"
$processedMessages = @()
foreach ($message in $InputEvents) {
try {
# Parse the incoming message
$eventData = $message | ConvertFrom-Json -ErrorAction SilentlyContinue
if (-not $eventData) {
$eventData = @{ message = $message }
}
Write-Host "📨 Processing event: $($eventData | ConvertTo-Json -Compress)"
# Create processed message with additional metadata
$processedMessage = @{
id = if ($eventData.id) { $eventData.id } else { [guid]::NewGuid().ToString() }
message = if ($eventData.message) { $eventData.message } else { ($eventData | ConvertTo-Json -Compress) }
timestamp = (Get-Date).ToUniversalTime().ToString('o')
}
$processedMessages += $processedMessage
Write-Host "✨ Message processed: $($processedMessage | ConvertTo-Json -Compress)"
}
catch {
Write-Error "❌ Error processing message: $_"
}
}
# Send processed messages to output Event Hub
if ($processedMessages.Count -gt 0) {
Push-OutputBinding -Name OutputEvents -Value ($processedMessages | ConvertTo-Json -Compress)
Write-Host "📤 Sent $($processedMessages.Count) message(s) to output Event Hub"
}
Il trigger viene definito nel function.json corrispondente.
È possibile esaminare il progetto modello completo here.
import azure.functions as func
import logging
import json
from datetime import datetime, timezone
import random
import uuid
from typing import List
app = func.FunctionApp()
# News article data model
class NewsArticle:
title=random.choice(titles_templates).format(topic=topic),
content=f"Comprehensive coverage of the latest developments in {topic}. " * random.randint(10, 20),
author=random.choice(authors),
source=random.choice(sources),
category=random.choice(categories),
published_date=datetime.now(timezone.utc),
view_count=random.randint(100, 10000),
sentiment_score=round(random.uniform(-1.0, 1.0), 2),
status=random.choice(["Published", "Featured"]),
tags=[random.choice(topics) for _ in range(random.randint(3, 5))]
)
articles.append(article)
# Send articles to Event Hub
events_json = json.dumps([article.to_dict() for article in articles])
event.set(events_json)
logging.info(f'✅ HIGH-THROUGHPUT: Successfully generated {num_articles} news articles in ~10 seconds')
# Event Hub trigger - processes news articles
@app.event_hub_message_trigger(arg_name="events", event_hub_name="news",
connection="EventHubConnection")
def EventHubsTrigger(events: List[func.EventHubEvent]):
"""Process news articles from Event Hub with sentiment analysis and engagement tracking"""
# Handle both single event and list of events
if not isinstance(events, list):
events = [events]
batch_articles = []
failed_count = 0
for event in events:
try:
# Parse the event data
event_data = json.loads(event.get_body().decode('utf-8'))
# Handle both single article and array of articles
articles = event_data if isinstance(event_data, list) else [event_data]
for article_data in articles:
# Process each article
article_id = article_data.get('ArticleId')
title = article_data.get('Title')
author = article_data.get('Author')
È possibile esaminare il progetto modello completo here.
Dopo aver verificato la funzione in locale, è possibile pubblicarla in Azure.
Distribuzione su Azure
Questo progetto è configurato per l'uso del comando azd up al fine di distribuire il codice in una nuova app per le funzioni in un piano a consumo flessibile in Azure. Poiché è già stato effettuato il provisioning delle risorse, questo comando distribuisce il codice nell'app esistente per le funzioni.
Suggerimento
Questo progetto include un set di file Bicep che azd usa per creare una distribuzione sicura in un piano a consumo Flex che segue le procedure consigliate.
Dalla cartella radice del repository eseguire il comando seguente per distribuire il progetto di codice nell'app per le funzioni in Azure:
azd deploy
Il processo di distribuzione crea un pacchetto con il codice e lo distribuisce nell'applicazione per le funzioni. Al termine del comando, vengono visualizzati collegamenti alle risorse create.
Verificare la distribuzione
Al termine della distribuzione, la funzione trigger di Event Hub avvia automaticamente l'elaborazione degli eventi al loro arrivo nell'Hub eventi.
Nel portale di Azure passare alla nuova app per le funzioni.
Selezionare Log stream (Flusso di log ) dal menu a sinistra per monitorare le esecuzioni delle funzioni in tempo reale.
Vengono visualizzate voci di log che indicano che la funzione di trigger di Event Hubs sta elaborando gli eventi generati dal trigger Timer.
Ridistribuire il codice
Eseguire il comando azd up quante volte è necessario per effettuare il provisioning delle risorse di Azure e distribuire gli aggiornamenti del codice nell'app per le funzioni.
Annotazioni
I file di codice distribuiti vengono sempre sovrascritti dal pacchetto di distribuzione più recente.
Le risposte iniziali alle richieste di azd e a tutte le variabili di ambiente generate da azd, vengono archiviate localmente nell'ambiente denominato. Usare il comando azd env get-values per esaminare tutte le variabili nell'ambiente usato durante la creazione di risorse di Azure.
Pulire le risorse
Al termine dell'uso dell'app per le funzioni e delle risorse correlate, usare questo comando per eliminare l'app per le funzioni e le relative risorse da Azure ed evitare di sostenere ulteriori costi:
azd down --no-prompt
Annotazioni
L'opzione --no-prompt indica a azd di eliminare il gruppo di risorse senza conferma.
Questo comando non influisce sul progetto di codice locale.