Last post Mar 05, 2021 01:08 AM by eroque74
Mar 05, 2021 01:08 AM|eroque74|LINK
I have an intranet Blazor Server application created using the Visual Studio template with the Work or School Accounts authentication option. Everything was working beautifully when running on my local machine and when the app was published to our development
environment. However, once I moved the app to our staging environment, the application would sometimes crash after authenticating the user in Azure.
After troubleshooting the issue, I believe the problem to be that our on-premises staging environment is load balanced (mimicking production). Our dev environment is not load balanced. I think what was occurring was that once authenticated in Azure and redirected
back to the application, the user doesn't always land on the same server due to the load balancer. This breaks the Signal-R circuit and caused the application to crash. This also explains why the error was random; happening maybe 2 out of every 10 logon attempts.
To test this, I removed Azure AD authentication from the application and allowed anonymous access to every page. The crashes stopped.
My question is if anyone knows of any workaround to get Blazor Server with Azure AD authentication working with an on-premises load balancer. I searched all over the web and the only workaround I found was to use sticky sessions with Azure Signal R service.
We are not hosting apps on the cloud yet. Is switching to Blazor Webassembly the only option if I want to use Blazor with authentication in my environment? Someone at work suggested switching the application to use our on premises ADFS server. However, wouldn't
that encounter the same issue?
For reference, here is the code in startup.cs ConfigureServices method that sets up the Azure authentication in the application:
.AddAzureAD(options => Configuration.Bind("AzureAd", options));
var policy = new AuthorizationPolicyBuilder().RequireAuthenticatedUser().Build();
Mar 19, 2021 12:59 PM|eroque74|LINK
I found the solution to this and am posting it here in case anyone else is facing a similar issue.
It turns out the problem wasn't SignalR or anything specific to Blazor Server. After enabling the developer exception page on the load balanced environment, I saw that the error was "Unable to unprotect the message.State". The application state is encrypted
by middleware before the user is authenticated by Azure AD. When Azure AD posts back, it includes that encrypted state which is then in turn decrypted on the client side by the middleware.
The key needed to decrypt is by stored on the web server. When in a load balanced environment, if you land on a different server than where you started, the middleware will then be attempting to decrypt state with the wrong key. This of course results in
To fix this you have to store the keys on a central location like a file share instead of on the server itself. Implementing the fix is actually simple. Include the following line in ConfigureServices in startup.cs:
There are also options to store keys on Azure if that is preferred.
This post by Kevin Dockx is what finally gave me the answer: