Come abbiamo avuto modo di mostrare in passato, ASP.NET MVC sfrutta l'AntiForgeryToken per evitare attacchi di tipo Cross-Site request forgery sui post dei form. Il principio di funzionamento si basa su una stringa criptata che viene inclusa in un campo hidden del form, il cui valore deve combaciare con quello di un cookie rilasciato dal nostro sito web.
La generazione di queste stringhe si basa su una chiave che, per ovvie ragioni di sicurezza, varia da macchina a macchina, così che non possa essere ricreata artificialmente da un utente malintenzionato.
In ASP.NET classico, questa chiave veniva solitamente generata a partire dalla machine key. In ASP.NET Core il funzionamento alla base è leggermente diverso, come dettagliato in questa pagina (https://docs.microsoft.com/en-us/aspnet/core/security/data-protection/configuration/default-setting), ma il principio di univocità per server è assolutamente preservato.
In uno scenario di web farm, però, quando abbiamo diversi server dietro a un load balancer, normalmente queste chiavi non combaciano. Il risultato è che se la macchina che ha renderizzato originariamente il form è diversa da quella che riceve il POST, quest'ultima solleverà una CryptographicException:

In alcuni casi specifici, per esempio se stiamo utilizzando istanze multiple di Web App su Azure, ASP.NET Core memorizza la chiave di decodifica in una cartella che è condivisa da tutti i server, così da essere sicuro che ognuno abbia la medesima chiave.
In tutti gli altri scenari, per esempio se abbiamo realizzato la nostra web farm presso un provider differente, o stiamo sfruttando i Docker Container e magari abbiamo pubblicato l'applicazione su Kubernetes, dobbiamo configurare questa funzionalità manualmente.
Il sistema più semplice è quello di sfruttare una share di rete raggiungibile da tutti i server, utilizzando il codice seguente allo startup:
public void ConfigureServices(IServiceCollection services) { services.AddMvc(); // .. altro codice qui .. services.AddDataProtection() .SetApplicationName("my-application") .PersistKeysToFileSystem(new DirectoryInfo(@"\\share\mykeys")); }
Il codice in alto richiede innanzi tutto di definire un nome per l'applicazione, così che sia condiviso tra tutti i server che eseguono lo stesso codice. Successivamente, non dobbiamo far altro che invocare PersistKeysToFileSystem indicando il percorso di rete su cui memorizzare le chiavi.
Alternativamente, possiamo sfruttare Azure Blob Storage, tramite il metodo PersistKeysToAzureBlobStorage:
public void ConfigureServices(IServiceCollection services) { services.AddMvc(); // .. altro codice qui .. var account = CloudStorageAccount.Parse("{connectionString}"); var client = account.CreateCloudBlobClient(); var container = client.GetContainerReference("keysContainer"); services.AddDataProtection() .SetApplicationName("my-application") .PersistKeysToAzureBlobStorage(container, "keys"); }
Lo snippet in alto necessita di una connectionString valida per un Azure Storage Account e, dopo aver recuperato il riferimento al Blob Container, lo passa al metodo PersistKeysToAzureBlobStorage unitamente al nome desiderato per il Blob che conterrà le nostre chiavi.
Commenti
Per inserire un commento, devi avere un account.
Fai il login e torna a questa pagina, oppure registrati alla nostra community.
Approfondimenti
Bloccare l'esecuzione di un pod in mancanza di un'artifact attestation di GitHub
Selettore CSS :has() e i suoi casi d'uso avanzati
Fissare una versione dell'agent nelle pipeline di Azure DevOps
Il nuovo controllo Range di Blazor 9
Recuperare App Service cancellati su Azure
Gestione dei nomi con le regole @layer in CSS
Utilizzare una qualunque lista per i parametri di tipo params in C#
Migliorare la scalabilità delle Azure Function con il Flex Consumption
Utilizzare l'espressione if inline in una pipeline di Azure DevOps
Utilizzare Container Queries nominali
Documentare i servizi REST con Swagger e OpenAPI con .NET 9
Utilizzare Locust con Azure Load Testing
I più letti di oggi
- Eseguire query in contemporanea con EF
- Fissare una versione dell'agent nelle pipeline di Azure DevOps
- .NET Aspire per applicazioni distribuite
- Utilizzare Locust con Azure Load Testing
- Autenticazione di git tramite Microsoft Entra ID in Azure DevOps
- Repaint, Reflow e Compositing: Come Funziona il Rendering nel Browser
- ecco tutte le novità pubblicate sui nostri siti questa settimana: https://aspit.co/wkly buon week-end!
- ecco tutte le novità pubblicate sui nostri siti questa settimana: https://aspit.co/wkly buon week-end!