Skip to content

RequireSystemWebAdapterSession breaks Blazor site when published to remote IIS #577

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
algorexxx opened this issue Jan 31, 2025 · 4 comments
Labels
Needs: Triage 🔍 Label added to new issues which need Triage

Comments

@algorexxx
Copy link

Currently migrating a framework 4.8 solution to .net 8 blazor web app and have run into a strange issue.

I tried following all available documentation for System.Web.Adapters and ended up with a solution that works great on my local development environment. Shared authentication and session both work flawlessly.

However, I ran into an issue I have been unable to resolve when I tried publishing to remote IIS where both sites have their own IIS site on same domain but different subdomains and the cookie works for all domains. Webforms proxy still works great, I can visit all the webforms pages including logging in etc. from the blazor site but the problem appears when I try to visit any of the Blazor pages, regardless if its authenticated or not.

It will load the prerendered blazor page with correct session data from framework site but will stall before rendering interactive components. No error message and browser is not indicating any loading. When I reload the page it will keep loading for 100s until I get a HTTP 500 error and IIS event log shows httpclient timing out when trying to GET ./systemweb-adapters/session.

If I remove RequireSystemWebAdapterSession() from program.cs the issue disappears but that also means session stops working.

I tried running blazor locally (built in release config) and having systemweb-adapters proxy to the remote webforms testsite and that also works flawlessly. If I then try the remote blazor it will stall and trying to refresh the local one in the same browser after that also results in a timeout. If I run the local blazor in a different browser then it will continue to work regardless of if I visit the remote site.

Any idea what I could try?

.NET Framework 4.8 WebForms Application_Start()

                .AddProxySupport(options => options.UseForwardedHeaders = true)
                .AddSessionSerializer(o => o.ThrowOnUnknownSessionKey = false)
                .AddJsonSessionSerializer(options =>
                {
                    options.RegisterKey<Guid?>("LoggedInUser");
                    options.RegisterKey<Guid?>("ActiveAssociation");
                })
                .AddRemoteAppServer(options =>
                {
                    options.ApiKey = ConfigurationManager.AppSettings["RemoteAppApiKey"];
                })
                .AddAuthenticationServer()
                .AddSessionServer();

.NET 8 Blazor Web app program.cs

var builder = WebApplication.CreateBuilder(args);

builder.Services.AddHttpForwarder();

builder.Services.AddSystemWebAdapters()
    .AddSessionSerializer(options => options.ThrowOnUnknownSessionKey = false)
    .AddJsonSessionSerializer(options =>
    {
        options.RegisterKey<Guid?>("LoggedInUser");
        options.RegisterKey<Guid?>("ActiveAssociation");
    })
    .AddRemoteAppClient(option =>
    {
        option.RemoteAppUrl = new(builder.Configuration["RemoteApp:DestinationAddress"]!);
        option.ApiKey = builder.Configuration["RemoteApp:ApiKey"]!;
    })
    .AddAuthenticationClient(true)
    .AddSessionClient();

builder.Services.AddControllers();
builder.Services.AddRazorComponents()
    .AddInteractiveServerComponents();

var app = builder.Build();

app.UseHttpsRedirection();
app.UseStaticFiles();
app.UseRouting();
app.UseAuthentication();
app.UseAntiforgery();
app.UseAuthorization();
app.UseWhen(context => !HttpMethods.IsConnect(context.Request.Method), appBuilder => appBuilder.UseSystemWebAdapters());
app.MapRazorComponents<App>()
    .AddInteractiveServerRenderMode()
    .RequireSystemWebAdapterSession();
app.MapForwarder("/{**catch-all}", builder.Configuration["RemoteApp:DestinationAddress"]!)
    .Add(static builder => ((RouteEndpointBuilder)builder).Order = int.MaxValue);
app.MapControllers();

app.Run();
@dotnet-policy-service dotnet-policy-service bot added the Needs: Triage 🔍 Label added to new issues which need Triage label Jan 31, 2025
@twsouthwick
Copy link
Member

This may be related to #543. Can you try the workaround described there?

@algorexxx
Copy link
Author

Thanks, I appreciate the response!

Should just be this line right?
app.UseWhen(context => !HttpMethods.IsConnect(context.Request.Method), appBuilder => appBuilder.UseSystemWebAdapters());

Because I agree, the symptoms appear identical to the ones I had locally before I added that line. But, since the issue only happens on the remote testsite now, I guess either one of the other requests are staying open aswell or the connect request for some reason isnt caught by !HttpMethods.IsConnect(context.Request.Method).

Not sure how to debug that but I'll keep tinkering with it and will gladly accept any other thoughts or ideas.

@algorexxx
Copy link
Author

Indeed, !HttpMethods.IsConnect(context.Request.Method) somehow didnt catch the signal-r request.

Kept tinkering and since that request was the only one with the path "/_blazor" I ended up trying this:
app.UseWhen(context => context.Request.Path != "/_blazor", appBuilder => appBuilder.UseSystemWebAdapters());
..which worked perfectly.

So for some reason the request type has changed from CONNECT to something else when published to our remote IIS, if it's due to config or something else I couldnt tell you. I dont really have access to the server so I dont know what it's changed to either.

@twsouthwick
Copy link
Member

Interesting. I'm going to close this issue to track in #543.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Needs: Triage 🔍 Label added to new issues which need Triage
Projects
None yet
Development

No branches or pull requests

2 participants