Nei vari snippet precedenti abbiamo usato progetti di tipo Web Role, sia nel codice presentato durante la spiegazione degli strumenti di sviluppo nella Guida Visual Studio 2010. Un Web Role rappresenta un nodo esposto via HTTP verso l'esterno: il sistema operativo configura Internet Information Service per noi durante il deploy delle applicazioni.
Come abbiamo accennato un Web Role può richiedere l'apertura di altri endpoint pubblici tramite la Service Definition:
Nell'immagine, il web role richiede, oltre alla classica porta 80, l'apertura del firewall per l'ingresso TCP/IP sulla porta 23.
Un Web Role è quindi molto aperto, o meglio, usando un termine non troppo italiano "è aperto e apribile" verso l'esterno.
Un Web Role, oltre a rispondere a richieste provenienti dall'esterno, grazie al supporto di IIS, può effettuare operazioni alla partenza del nodo virtuale, come ad esempio operazioni di inizializzazione. Queste operazioni possono essere effettuate nel metodo Application_Start intecettabile dal Global.asax visto che un Web Role è fondamentalmente una applicazione ASP.NET.
È possibile anche effettuare operazioni durante lo startup del nodo virtuale, così come durante lo stop e utilizzare un thread secondario, non dedicato quindi alle richieste in ingresso per compiere operazioni continue.
A tale scopo, la classe base di un role, RoleEntryPoint mette a disposizione dei metodi virtuali, rispettivamente OnStart, OnStop e Run per poter far girare il nostro codice.
Nel caso quindi di una applicazione che non ha bisogno di rispondere a richieste dall'esterno, ma deve operare in modalità schedulata o continua, potremmo usare questi metodi per eseguire queste operazioni, volendo anche diversi thread oppure un nuovo thread pool. Resterebbe in ogni caso IIS a rispondere su un endpoint http.
È infatti impossibile rimuovere tutti gli endpoint da un Web Role, in quanto, come indica la parola stessa, è un ruolo nato per essere esposto sul Web. Questo il messaggio per i curiosi:
Figura 32. impossibile rimuovere tutti gli endpoint
(clic per ingrandire)
Per gestire applicazioni "non aperte" verso l'esterno, ma poter sfruttare le peculiarità di Windows Azure è possibile creare progetti di tipo Worker Role. Come indica la parola Worker, si tratta di applicazioni che "lavorano" e, più precisamente, lavorano dietro le quinte non avendo nessuna porta aperta, per default, verso l'esterno.
Il primo passo del wizard per la creazione di un worker role è identico:
Nel secondo passaggio occorre scegliere Worker Role
Dalla versione di Agosto 2011, un Worker Role appena creato si presenta così:
Il progetto denominato WorkerRole1 si presenta con il classico file di configurazione app.config dove è possibile memorizzare impostazioni applicative e un file WorkerRole.cs che definisce una classe pressochè identica a quella creata dal wizard di creazione di un web role:
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Net;
using System.Threading;
using Microsoft.WindowsAzure;
using Microsoft.WindowsAzure.Diagnostics;
using Microsoft.WindowsAzure.ServiceRuntime;
using Microsoft.WindowsAzure.StorageClient;
namespace WorkerRole1
{
public class WorkerRole : RoleEntryPoint
{
public override void Run()
{
// This is a sample worker implementation. Replace with your logic.
Trace.WriteLine("WorkerRole1 entry point called", "Information");
while (true)
{
Thread.Sleep(10000);
Trace.WriteLine("Working", "Information");
}
}
public override bool OnStart()
{
// Set the maximum number of concurrent connections
ServicePointManager.DefaultConnectionLimit = 12;
// For information on handling configuration changes
// see the MSDN topic at http://go.microsoft.com/fwlink/?LinkId=166357.
return base.OnStart();
}
}
}
La differenza rispetto ad un web role sta solo nel codice di esempio inserito dal wizard che segnala nel trace ogni 10 secondi che il Worker Role è "working".
Per implementare il nostro codice è sufficiente modificare il codice del metodo Run: è possibile eseguire un ciclo come nell'esempio proposto da Visual Studio per operazioni ripetitive come leggere i dati in una tabella a intervalli regolari oppure avviare uno o più thread per eseguire operazioni parallele. Il codice gira all'interno di un application domain .NET quindi è possibile anche accodare operazioni da eseguire all'interno del thread pool nativo così come creare nuovi thread pool.
È sufficiente rispettare queste semplici regole nel metodo Run:
Una ulteriore regola si deve aggiungere nel caso di operazioni di clean-up effettuate nel metodo OnStop: al massimo l'infrastruttura ci concede 30 secondi per queste operazioni dopodichè il ruolo viene "ucciso".
Queste regole valgono anche per un web role quando si implementa il metodo Run.
Un Worker Role può indicare endpoint per aprirsi verso l'esterno, ma, in ogni caso, non viene predisposto IIS sulla macchina virtuale che ospita il ruolo come accade per un web role: occorre quindi ascoltare gli endpoint e predisporre il codice per gestire richieste concorrenti.
Una ultima nota: il file app.config
, così come il file web.config di un web role, viene "impacchettato" nel package di setup e necessita di un publish completo per modificarne le impostazioni. Conviene quindi usare il file ServiceConfiguration.cssfg che può essere modificato a caldo.
Da notare che da Agosto 2011, un worker role si presenta già con 2 configurazioni di default, la prima denominata Cloud e destinata ai settaggi per il deployment in produzione e il secondo, con suffisso Local, per le impostazioni locali di test.