Blazor vs Razor
Blazor vs Razor: guida pratica per sviluppatori .NET
Indice dei contenuti Blazor vs Razor
- Introduzione: Razor e Blazor, due facce dello stesso ecosistema
- Razor Pages: il motore di template server-side
- Blazor: il framework per applicazioni web interattive
- Quando usare Razor da solo
- Quando usare Blazor da solo
- Come e quando usarli insieme: l’approccio ibrido in .NET 10
- Errori comuni nell’uso combinato di Blazor e Razor
- Best practice per un’integrazione efficace
- Tabella comparativa: Blazor vs Razor
- Formazione continua: la chiave per non improvvisare con le nuove tecnologie
1. Introduzione: Razor e Blazor, due facce dello stesso ecosistema
Immagina di dover costruire un edificio. Razor è la cassetta degli attrezzi: martello, livella, pennello. Blazor è invece il progetto architettonico completo, che decide dove vanno i muri, come si collegano i piani e come si comporta l’edificio nel tempo. Spesso confusi tra loro, anche a causa del nome, Razor e Blazor sono due tecnologie distinte ma profondamente legate, entrambe parte dell’ecosistema ASP.NET Core di Microsoft.
Razor è un motore di template server-side che permette di generare HTML dinamico mescolando sintassi C# e markup HTML. Blazor, il cui nome nasce dall’unione di browser e Razor, è invece un framework web completo che consente di costruire applicazioni web interattive usando C# al posto di JavaScript. Capire la differenza tra i due, e soprattutto capire quando usarli separatamente o insieme, è una delle competenze più strategiche per uno sviluppatore .NET moderno. E con l’arrivo di .NET 10, rilasciato ufficialmente l’11 novembre 2025 come versione LTS (Long-Term Support, supportata per tre anni), questo scenario si è ulteriormente evoluto: nuove funzionalità rendono la scelta ancora più ricca — e ancora più importante saper fare bene.
2. Razor Pages: il motore di template server-side
Razor nasce come sintassi di markup all’interno di ASP.NET MVC e si afferma poi come modello a pagine autonomo con Razor Pages. Il suo principio è semplice: ogni file .cshtml mescola codice C# e HTML, dove il simbolo @ indica il passaggio alla logica server.
Un esempio classico di Razor Page:
@page
@model IndexModel
<h1>Benvenuto, @Model.NomeUtente!</h1>
@if (Model.IsAdmin)
{
<p>Sei un amministratore.</p>
}
Il codice viene eseguito sul server: il risultato è HTML puro inviato al browser. Non c’è interattività lato client, nessun aggiornamento dinamico della pagina senza un nuovo round-trip al server. Questo modello è leggero, veloce e ottimo per applicazioni content-driven.
Ogni Razor Page è composta da due file: il .cshtml con la view e il .cshtml.cs con il PageModel, che gestisce i dati e la logica di business. Una separazione pulita, che molti sviluppatori trovano intuitiva soprattutto se provengono da ASP.NET MVC.
3. Blazor: il framework per applicazioni web interattive
Blazor è il salto di paradigma. Anziché generare HTML statico sul server e reinviarlo ad ogni interazione, Blazor costruisce applicazioni a componenti riutilizzabili che possono rispondere agli eventi utente in tempo reale, senza ricaricare la pagina.
I componenti Blazor usano i file .razor e, al loro interno, si trova ancora la sintassi Razor. La differenza fondamentale è che in Blazor il codice non si limita a generare HTML: gestisce lo stato del componente, risponde agli eventi del DOM e aggiorna l’interfaccia in modo reattivo.
@page "/counter"
<h1>Contatore: @count</h1>
<button @onclick="Incrementa">Clicca qui</button>
@code {
private int count = 0;
void Incrementa() => count++;
}
Questo piccolo esempio mostra qualcosa che con Razor puro non sarebbe possibile senza JavaScript: un bottone che aggiorna il valore visualizzato al click, senza ricaricare la pagina.
Blazor offre tre modalità principali di rendering, consolidate in .NET 8/.NET 9 e ulteriormente raffinate in .NET 10:
- Blazor Server: la logica gira sul server, le modifiche all’interfaccia vengono sincronizzate via SignalR. Richiede una connessione costante. Con .NET 10 è ora possibile mettere in pausa e riprendere il circuito (
Blazor.pause()/Blazor.resume()), rendendo le sessioni molto più resilienti anche in scenari enterprise con connessioni instabili. - Blazor WebAssembly (WASM): il runtime .NET e il codice vengono scaricati nel browser ed eseguiti lato client. In .NET 10 il bundle principale
blazor.web.jsè ora un asset statico con compressione automatica e fingerprinting, con una riduzione di dimensione del 76% (da 183 KB a circa 43 KB), migliorando drasticamente i tempi di avvio. - Interactive Auto: parte con Blazor Server per un caricamento rapido, poi scarica WASM in background e subentra automaticamente. Modalità particolarmente strategica per applicazioni che devono bilanciare performance di avvio e funzionamento offline.
Novità rilevante di .NET 10 è anche il supporto nativo a passkey e WebAuthn nei template Blazor Web App, che consente di implementare autenticazione passwordless basata su FIDO2 senza librerie esterne.
4. Quando usare Razor da solo – Blazor vs Razor
Razor Pages brilla in scenari precisi. Se stai costruendo un sito istituzionale, un blog, un e-commerce con pagine prevalentemente statiche o un’applicazione con requisiti SEO importanti, Razor è la scelta giusta. Il payload iniziale è minimo, i tempi di caricamento sono eccellenti e il rendering server-side è nativamente indicizzabile dai motori di ricerca.
Razor è anche la scelta ideale per chi deve gestire flussi che richiedono accesso diretto all’HttpContext, come la lettura e scrittura di cookie, oppure per moduli semplici con validazione lato server. Se il team ha già esperienza con ASP.NET MVC, la curva di apprendimento è quasi nulla.
In sintesi: scegli Razor quando la tua applicazione è prevalentemente informativa, orientata ai contenuti, e dove la semplicità e la velocità di caricamento contano più dell’interattività.
5. Quando usare Blazor da solo – Blazor vs Razor
Blazor diventa la scelta naturale quando devi costruire applicazioni ricche di interazione: dashboard analitiche, CRM, ERP interni, gestori di progetti, applicazioni real-time come chat o monitor live. In questi casi, la component-based architecture di Blazor, simile a React o Angular, permette di costruire interfacce complesse in modo modulare e mantenibile.
Un altro vantaggio competitivo di Blazor è la possibilità di condividere la logica tra client e server interamente in C#, eliminando la necessità di mantenere due codebase separate (backend C#, frontend JavaScript). Per team .NET senza forte expertise frontend in JavaScript, questo è un vantaggio enorme.
Con .NET 10, Blazor WASM supporta anche la precaricamento automatico degli asset del framework tramite il nuovo componente <LinkPreload />, che avvia il download dei file runtime ancora prima che la pagina finisca il rendering, abbattendo ulteriormente i tempi di avvio percepiti dall’utente. È un dettaglio tecnico, ma fa una differenza concreta nell’esperienza utente delle applicazioni enterprise.
6. Come e quando usarli insieme: l’approccio ibrido in .NET 10
Qui si apre lo scenario più interessante — e anche il più delicato. A partire da .NET 8, Microsoft ha introdotto il modello Blazor Web App, che permette di mescolare rendering statico server-side (SSR con Razor) e rendering interattivo Blazor nella stessa applicazione. Con .NET 10, questo modello ibrido raggiunge la sua maturità più solida.
Il caso d’uso tipico: un sito con homepage, pagine di contenuto e blog gestite con Razor SSR (veloci, SEO-friendly), e sezioni come un pannello di controllo utente o un modulo di configurazione avanzata costruite con componenti Blazor interattivi.
La grande novità di .NET 10 per l’approccio ibrido è l’attributo [PersistentState] (precedentemente noto come [SupplyParameterFromPersistentComponentState]), che risolve uno dei problemi più fastidiosi del pre-rendering: il double-render. Ora lo stato del componente viene serializzato durante il pre-render SSR e reso disponibile automaticamente alla fase interattiva, senza boilerplate:
@page "/contacts"
@rendermode InteractiveServer
<h1>Lista Contatti</h1>
@code {
[PersistentState]
public List<Contact>? Contacts { get; set; }
}
I dati vengono caricati una sola volta durante il pre-rendering e incorporati nell’HTML inviato al browser. Blazor li recupera automaticamente nella fase interattiva, senza effettuare una seconda chiamata al server. Zero flash, zero doppia richiesta.
Una pagina statica nello stesso progetto rimane invece in puro SSR Razor, senza alcun render mode:
@page "/privacy"
@attribute [ExcludeFromInteractiveRouting]
<h1>Privacy Policy</h1>
<p>Contenuto statico, indicizzabile, velocissimo.</p>
Con .NET 10 il template Blazor Web App include anche il componente ReconnectModal integrato, che gestisce la UI di riconnessione nel rispetto delle policy CSP (Content Security Policy) più restrittive, risolvendo un problema storico che molti team avevano dovuto aggirare manualmente.
7. Errori comuni nell’uso combinato di Blazor e Razor
L’integrazione ibrida è potente ma insidiosa. Ecco gli errori più frequenti che i team commettono quando iniziano a mescolare Blazor e Razor senza la giusta preparazione.
Confondere i file .razor con i file .cshtml: i componenti Blazor usano .razor con blocco @code, le Razor Pages usano .cshtml con PageModel separato. Mescolare logica Blazor in un file .cshtml o viceversa causa errori di compilazione spesso non intuitivi.
Passare parametri non serializzabili a componenti interattivi: quando si usa InteractiveServer o InteractiveWebAssembly, i parametri devono essere serializzabili. Passare un RenderFragment (child content) a un componente con render mode attivo genera l’errore Cannot pass the parameter 'ChildContent' to component with rendermode, un classico che blocca i team alla prima ora.
Ignorare il ciclo di vita del pre-rendering: Blazor esegue un primo render in SSR prima di diventare interattivo. Codice che accede a servizi disponibili solo lato client durante il pre-rendering causa eccezioni difficili da diagnosticare. Con .NET 10 l’attributo [PersistentState] riduce questo rischio, ma non lo elimina del tutto se il componente non è strutturato correttamente.
Usare HttpContext in un componente Blazor interattivo: HttpContext non è disponibile durante il rendering interattivo. Va gestito in una Razor Page o in un middleware, passando i dati necessari al componente Blazor come parametri.
Mescolare la navigazione: Blazor gestisce la navigazione via NavigationManager, mentre Razor Pages usa redirect HTTP tradizionali. In .NET 10 il NavigationManager gestisce automaticamente il comportamento .NotFound() sia in modalità SSR che interattiva, ma è comunque necessario capire il confine tra i due sistemi per evitare comportamenti inattesi.
Streaming sincrono con HttpClient in WASM: in .NET 10 lo streaming delle risposte HttpClient in Blazor WASM è abilitato per default. Codice che usa operazioni sincrone come Stream.Read() causa una NotSupportedException a runtime. Vanno usate le API asincrone, o disabilitato esplicitamente il comportamento con <WasmEnableStreamingResponse>false</WasmEnableStreamingResponse> nel file di progetto.
8. Best practice per un’integrazione efficace
Lavorare bene con Blazor e Razor insieme richiede una strategia chiara fin dall’inizio del progetto. Queste sono le pratiche che fanno davvero la differenza.
Definisci i confini prima di scrivere codice: stabilisci quali sezioni dell’app sono statiche e quali interattive. Documenta la scelta e comunicala a tutto il team. Un diagramma architetturale che distingue le aree SSR Razor da quelle Blazor interattive evita decine di ore di refactoring.
Usa [PersistentState] per eliminare il double-render: in ogni componente Blazor che carica dati durante il pre-rendering, usa il nuovo attributo di .NET 10 per serializzare lo stato. Meno chiamate, meno flash, meno bug.
Centralizza i componenti in una Razor Class Library (RCL): se l’app ha sia una parte web Blazor che una mobile (MAUI Blazor Hybrid), una RCL permette di riusare i componenti senza duplicazione di codice.
Gestisci lo stato in modo esplicito: in un’app ibrida, lo stato si azzera ad ogni navigazione SSR. Usa servizi scoped o Cascading Parameters per mantenere lo stato tra i componenti Blazor interattivi, e non fare affidamento sullo stato locale nelle pagine Razor.
Sfrutta la validazione con Source Generators in .NET 10: la nuova validazione basata su source generators (anziché reflection) è più veloce, compatibile con AOT compilation e supporta la validazione di oggetti annidati. Aggiungila ai form complessi:
// In Program.cs
builder.Services.AddValidation();
// Nel modello
[ValidatableType]
public class OrdineForm
{
[Required]
public Cliente Cliente { get; set; }
public List<Articolo> Articoli { get; set; }
}
Testa esplicitamente i cicli di vita: scrivi test di integrazione che verificano il comportamento sia in fase di pre-rendering che in fase interattiva. I bug più subdoli si manifestano proprio durante la transizione tra i due stati.
Configura i diagnostics con OpenTelemetry: .NET 10 espone le attività di tracing dei circuit Blazor Server come top-level activities, compatibili con Application Insights e strumenti OpenTelemetry. Attiva il tracing fin dall’inizio del progetto, non dopo.
9. Tabella comparativa: Blazor vs Razor
| Caratteristica | Razor Pages | Blazor |
|---|---|---|
| Tipo | Motore di template / framework pagine | Framework UI a componenti |
| Rendering | Server-side (SSR), HTML statico | Server (SignalR), WebAssembly, Auto, SSR |
| Interattività | Nessuna senza JavaScript | Nativa, gestita da .NET |
| Estensione file | .cshtml | .razor |
| Modello | Page-centric con PageModel | Component-based |
| Stato | Stateless ad ogni richiesta | Stateful (con gestione esplicita) |
| SEO | Ottimo (HTML puro indicizzabile) | Limitato in WASM; ottimo con SSR |
| Caricamento iniziale | Molto rapido (~50 KB HTML) | WASM: ottimizzato in .NET 10 (~43 KB JS); Server: rapido |
| Uso di JavaScript | Necessario per interattività | Opzionale (JS Interop potenziato in .NET 10) |
| Dipendenza da rete | Ogni interazione = round-trip al server | Server: connessione SignalR; WASM: funziona offline |
| Curva di apprendimento | Bassa (simile a MVC) | Media/Alta |
| Caso d’uso ideale | Siti content-driven, SEO, form semplici | SPA, dashboard, app interattive, real-time |
| Validazione form | DataAnnotations standard con reflection | Source Generators in .NET 10, AOT-safe, nested objects |
| Persistenza stato | Non applicabile | [PersistentState] in .NET 10: zero double-render |
| Autenticazione | Identity standard | Passkey / WebAuthn integrato nei template .NET 10 |
| Riuso componenti | Limitato (partial views, layouts) | Elevato (componenti riusabili, RCL, NuGet) |
| Diagnostics | ASP.NET Core standard | OpenTelemetry nativo, circuit tracing in .NET 10 |
10. Formazione continua: la chiave per non improvvisare con le nuove tecnologie
Arrivati a questo punto dell’articolo, è chiaro che Blazor e Razor non sono tecnologie che si imparano leggendo qualche tutorial in un pomeriggio. Con .NET 10 — rilascio LTS che molte aziende adotteranno come versione di riferimento per i prossimi tre anni — il modello ibrido introduce concetti come render modes, [PersistentState], validazione con source generators, circuit resilience, passkey authentication e streaming WASM, tutti argomenti che richiedono comprensione profonda per essere usati correttamente in produzione.
Sbagliare architettura in un progetto Blazor significa ritardi, bug difficili da diagnosticare e codice che diventa rapidamente un debito tecnico. I team che affrontano queste tecnologie senza una formazione strutturata tendono a fare le scelte architetturali sbagliate nelle prime settimane, pagandone il costo per mesi. Il rischio è ancora più alto quando si lavora su un rilascio LTS nuovo come .NET 10: le nuove funzionalità cambiano pattern consolidati, e non aggiornarsi significa vanificare i vantaggi della piattaforma.
La formazione non è un costo: è un investimento che si ripaga nella prima sprint evitata di refactoring.
Innovaformazione propone il Corso Blazor pensato specificamente per sviluppatori .NET e team aziendali che vogliono affrontare Blazor in modo professionale e strutturato, dalle basi fino all’integrazione avanzata con Razor e le nuove funzionalità di .NET 10.
Il corso si svolge in modalità online, classe virtuale, con calendario concordabile in base alle esigenze dell’azienda. È possibile inserire il percorso formativo all’interno del piano Fondimpresa, il fondo interprofessionale che permette alle aziende aderenti di formare i propri dipendenti a costo zero o con finanziamento totale a fondo perduto.
Per sapere se la tua azienda è già aderente a Fondimpresa, richiedere il programma completo del corso o ricevere un preventivo personalizzato:
📧 info@innovaformazione.net 📞 347 101 2275 (Dario Carrassi) 🔗
Non aspettare che un progetto si inceppi per investire nella formazione del team: contatta Innovaformazione oggi stesso e richiedi informazioni senza impegno.
Per altri articoli tecnici consigliamo di navigare sul nostro blog QUI.
Vuoi essere ricontattato? Lasciaci il tuo numero telefonico e la tua email, ti richiameremo nelle 24h:
Articoli correlati
Usare Claude Code con Flutter
Guida Claude Design
Estensioni Flutter per Gemini CLI
Guida Migrazione Negozio eBay
Come integrare Elasticsearch con LLM Ollama
