I have ASP .NET Core 3.1 web site that uses razor pages, but also has single controller that inherits from ASP .NET Core Controller class. The controller handles payload and then redirects to one of the razor pages when successful. I'm noticing that when there is unhandled exception in the controller, browser displays HTTP 400 - Bad Request error, but I want the controller to simply use the exception handler I already defined, which looks like this:
if (env.IsDevelopment())
app.UseDeveloperExceptionPage();
else
app.UseExceptionHandler("/Error");
In the above, the "/Error" path is razor page. In non-development mode, controller doesn't use my exception handler and just displays HTTP 400 - Bad Request browser error.
I managed to get it to work with exception filter class where inside OnException() method, I log the error and manually redirect to "/Error" page. The exception filter looks like this:
private class CustomExceptionFilter : IExceptionFilter
{
private readonly IWebHostEnvironment hostingEnvironment;
private readonly ILogger<CustomExceptionFilter> logger;
public CustomExceptionFilter(IWebHostEnvironment hostingEnvironment, ILogger<CustomExceptionFilter> logger)
{
this.hostingEnvironment = hostingEnvironment;
this.logger = logger;
}
public void OnException(ExceptionContext context)
{
if (this.hostingEnvironment.IsDevelopment())
{
return;
}
this.logger.LogError(context.Exception, string.Empty);
context.Result = new RedirectToPageResult("/Error");
}
Then, I defined [TypeFilter(typeof(CustomExceptionFilter))] on the controller itself. Everything appears to be working, but it seems like a lot of moving parts. Is this the only way to do it or maybe I'm missing something?
Here is Startup code:
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
app.UseForwardedHeaders();
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
else
{
app.UseExceptionHandler("/Error");
app.UseHsts(options => options.MaxAge(365).IncludeSubdomains());
}
app.UseStaticFiles();
app.UseCookiePolicy();
app.UseXRobotsTag(options => options.NoIndex().NoFollow());
app.UseXfo(options => options.SameOrigin());
app.UseXXssProtection(options => options.EnabledWithBlockMode());
app.UseXContentTypeOptions();
app.UseNoCacheHttpHeaders();
app.UseRedirectValidation();
app.UseRouting();
app.UseAuthentication();
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapControllers();
endpoints.MapRazorPages();
});
}
Thanks in advance!