Exception handling or error handling is one of the crucial aspects of any software development life cycle, if you have worked with earlier version of asp.net framework, you are probably familiar with error handling techniques; let’s learn how exception handling can be implemented in asp.net core application.
Exception handling help us to deal with the unexpected errors which could appear from our coding, server connectivity, bad data, or any other situation, so there are many different ways for handling such exception.
If you have not read our earlier exception handling in asp.net tutorial, please read that, here we discuss different ways of exception handling in asp.net core application only
Exception handling is also type of Middleware in Asp.net Core
In this tutorial we will talk about three different ways of error handling in Asp.net Core
Try catch is common in all most all development practice, very easily can implemented on every function or method you write.
try { // here you write you code } catch (Exception ex) { here you get all exception details in Exception variable, you can either log the error details or display to user } finally { // is optional }
We use Exception handling middleware UseExceptionHandler in Configure method of Startup.Cs
public void Configure(IApplicationBuilder app, IHostingEnvironment env) { // write error handling code here }
To understand if error handling is working properly let’s create some error on PageModel class
public void OnGet() { throw new Exception("this is an exception"); }
The above code will throw error, will see how differently we can catch the exception and log error details and display user friendly error message .
We can implement different type of exception handling mechanism for different environment like for development, staging, production etc.
if(env.IsDevelopment() || env.IsStaging()) { app.UseDeveloperExceptionPage(); } else app.UseExceptionHandler("/error");
Now in above exception handling technique you will be able redirect user to a error page with some messages, but this will not help you to capture actual error details for logging or resolving the issue.
So now let's look at another way of capturing error details
Use of UseExceptionHandler
app.UseExceptionHandler( options => { options.Run( async context => { context.Response.StatusCode = (int)HttpStatusCode.InternalServerError; context.Response.ContentType = "text/html"; var ex = context.Features.Get<IExceptionHandlerFeature>(); if (ex != null) { var err = $"<h1>Error: {ex.Error.Message}</h1>{ex.Error.StackTrace}"; await context.Response.WriteAsync(err).ConfigureAwait(false); } }); } );
Now we see how to write a custom middleware for error handling, and how to access current HttpContext and error details associated with that
using Microsoft.AspNetCore.Builder; using Microsoft.AspNetCore.Http; using System.Threading.Tasks; namespace AspNetCoreWebApplication { public class WTRCustomMiddleware { private readonly RequestDelegate _next; public WTRCustomMiddleware(RequestDelegate next) { _next = next; } public async Task InvokeAsync(HttpContext context) { await context.Response.WriteAsync("- Before Message - \n\r"); await _next(context); var ex = context.Features.Get<IExceptionHandlerFeature>(); await context.Response.WriteAsync("\n\r - After Message - "); } }Now create a Middleware Extensions class
public static class WTRCustomMiddlewareExtensions { public static IApplicationBuilder UseWTRCustomMiddleware(this IApplicationBuilder builder) { return builder.UseMiddleware<WTRCustomMiddleware>(); } } }
In above middleware you have HttpContext, so get the exception details
var ex = context.Features.Get<IExceptionHandlerFeature>();
Now call the above custom middleware in Configure method of Statup.cs
app.UseWTRCustomMiddleware(); app.Run(async context => { await context.Response.WriteAsync("Welcome to WebTrainingRoom!"); });
Now we see how to catch error status code like page not found, internal server error etc.
public void Configure(IApplicationBuilder app, IHostingEnvironment env) { app.UseStatusCodePages(); }
Now if try to access some unknown page on browser, you will get following error message
Above method is good enough to catch error status code and display the error, but in application development sometimes you may want to display the error to a different user friendly page with other page navigation, in such situation you can use UseStatusCodePagesWithRedirects().
public void Configure(IApplicationBuilder app, IHostingEnvironment env) { app.UseStatusCodePagesWithReExecute("/Error", "?statusCode={0}"); }
this method will redirect user to a different error page, where you can show custom error message based on statusCode, alternatively you also can create different error page for each code, and redirect to page based on code.