

Best Practices for Error Handling in .Net 6
source link: https://dzone.com/articles/best-practices-for-error-handling-in-net-6
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

Quick Microsoft .NET 6 Overview
Microsoft .NET 6 is a cross-platform framework that merges the .NET Core, .NET Framework, and Xamarin/Mono technologies into a single framework. Continuing the unification that started with .NET 5 by unifying the runtime and SDK for desktop, web, mobile, and cloud applications.
Alongside C# 10 and Visual Studio 2022, Microsoft made .NET 6 generally available on November 9, 2021. There are many new enhancements to .NET 6, including:
- Improved performance
- Profile - guided optimizing
- Security improvements
- C# 10 and F# 6 improvements
Error Handling Using Try-Catch Blocks
Try-catch blocks are the most basic way of handling exceptions and are most widely used and generally used to gracefully handle code statements that might generate an exception.
Consider the following ProcessFile class as a code example:
using System;
using System.IO;
public class ProcessFile
{
public static void Main()
{
try
{
using (StreamReader sr = File.OpenText("data.txt"))
{
Console.WriteLine($"The first line of this file is {sr.ReadLine()}");
}
}
catch (FileNotFoundException e)
{
Console.WriteLine($"The file was not found: '{e}'");
}
catch (DirectoryNotFoundException e)
{
Console.WriteLine($"The directory was not found: '{e}'");
}
catch (IOException e)
{
Console.WriteLine($"The file could not be opened: '{e}'");
}
catch (Exception e)
{
Console.WriteLine($"General exception: '{e}'");
}
}
}
The above code example is a typical case where we use try-catch to handle the exception. Any exception thrown by the code enclosed within the try block will be caught and handled by the catch block. Also illustrated is the use of catching multiple exception types, which is useful for handling different exceptions uniquely for the same block of code.
Try-catch blocks are best used within methods in which an error might occur, and you would like to handle it appropriately and uniquely for the end user or service. Every developer should be aware of try-catch blocks as it is a useful tools to develop robust applications. However, adding a try-catch block to every method is not desirable and can get messy quickly. It's best to use global exception handling and try-catch block where uniquely needed.
Global Exception Handling
Global exception handling enables an application with a much broader ability to handle all exceptions. This is usually done through custom middleware for ASP.NET core applications, AppDomain unhandled exception events for .NET core console and service applications, or .NET 3rd party exception handling libraries.
ASP.NET Core Global Exception Handling With Custom Middleware
Using custom middleware to handle global exceptions provides a better development and application experience.
Consider the following CustomExceptionHandlingMiddleware class as a Custom Middleware example:
using System.Net;
using System.Text.Json;
using ExceptionHandling.Models.Responses;
namespace Middleware;
public class CustomExceptionHandlingMiddleware
{
private readonly RequestDelegate _next;
private readonly ILogger<CustomExceptionHandlingMiddleware> _logger;
public ExceptionHandlingMiddleware(RequestDelegate next, ILogger<CustomExceptionHandlingMiddleware> logger)
{
_next = next;
_logger = logger;
}
public async Task InvokeAsync(HttpContext httpContext)
{
try
{
await _next(httpContext);
}
catch (Exception ex)
{
await HandleExceptionAsync(httpContext, ex);
}
}
private async Task HandleExceptionAsync(HttpContext context, Exception exception)
{
context.Response.ContentType = "application/json";
var response = context.Response;
var errorResponse = new ErrorResponse
{
Success = false
};
switch (exception)
{
case ApplicationException ex:
if (ex.Message.Contains("Unauthorized"))
{
response.StatusCode = (int) HttpStatusCode.Forbidden;
errorResponse.Message = ex.Message;
break;
}
response.StatusCode = (int) HttpStatusCode.BadRequest;
errorResponse.Message = ex.Message;
break;
default:
response.StatusCode = (int) HttpStatusCode.InternalServerError;
errorResponse.Message = "Internal server error!";
break;
}
_logger.LogError(exception.Message);
var result = JsonSerializer.Serialize(errorResponse);
await context.Response.WriteAsync(result);
}
}
Next, you must register your middleware in your Program class.
app.UseMiddleware<ExceptionHandlingMiddleware>();
.NET Core Console Global Exception Handling
Global exception handling in console apps is done through the AppDomain unhandled exception event. Here you can add custom logic around what happens when an unhandled exception occurs.
Consider the following code from a sample Program class that catches and logs exceptions:
var logger = host.Services.GetRequiredService<ILogger<Program>>();
System.AppDomain.CurrentDomain.UnhandledException += CurrentDomain_UnhandledException;
void CurrentDomain_UnhandledException(object sender, UnhandledExceptionEventArgs e)
{
var exception = e.ExceptionObject as Exception;
logger.LogError(exception, exception.Message);
}
3rd Party Logging and Exception Handling
There are many .NET exception handling and logging tools that help developers integrate global error handling and logging into their applications. This removes a lot of the heavy lifting from the developer with easier implementation and management.
Consider this example of ClearInsights Logging for global exception handling:
ASP.NET Core
using ClearInsights.Logging;
using System.Net;
var builder = WebApplication.CreateBuilder(args);
//Add to capture logs with ClearInsights Logging
builder.Logging.AddClearInsightsLogger(configuration =>
{
configuration.ApiKey = "{ApiKey}";
configuration.Secret = "{Environment Client Secret}";
configuration.ApplicationName = "{Application Name}";
});
var app = builder.Build();
//Add to use ClearInsights global error handling.
//This will automatically catch and log any unhandled exceptions
app.UseClearInsightsExceptionHandling(options =>
{
//Add to extend the error handler and add additional logic.
//Add logic like custom HTTP response, etc...
options.OnError += (sender, arg) =>
{
var response = "Oops something went wrong";
arg.HttpContext.Response.ContentType = "text/html";
arg.HttpContext.Response.StatusCode = (int)HttpStatusCode.NotFound;
arg.HttpContext.Response.WriteAsync(response);
};
});
.NET Core
using ClearInsights.Logging;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using IHost host = Host.CreateDefaultBuilder(args)
.ConfigureLogging(builder =>
builder.ClearProviders()
//Add to capture logs with ClearInsights Logging
.AddClearInsightsLogger(configuration =>
{
configuration.ApiKey = "{ApiKey}";
configuration.Secret = "{Environment Client Secret}";
configuration.ApplicationName = "{Application Name}";
}))
.Build();
//Add to use ClearInsights global error handling.
//This will automatically catch and log any unhandled exceptions
System.AppDomain.CurrentDomain.UseClearInsightsExceptionHandling(host.Services.GetRequiredService<ILogger<Program>>());
Recommend
-
11
Error handling best practice yourbasic.org/golang Go has two different error-handling mechanisms: most functions return
-
16
React Error Handling and Logging Best PracticesHow to handle errors and properly log them using the right tools
-
9
5 Best Practices for Handling State Structure in ReactFive best practices that can help to structure the state wellWhen we write a component in React that holds some state, we will have to make choices...
-
9
<?xml encoding="utf-8" ??>Introduction This guide explains error handling in Go and the best practices for handling API errors in Go. You should have a working knowledge of Go and understand how...
-
7
Blog Post Learn best practices for debugging and error handling in an enterprise-grade blockchain application Identify where failures take place and resolve them ...
-
9
Blazor Best Practices: Handling Errors
-
4
Introduction One of the challenges of working with any graphics API is that under the hood they tend to be very asynchronous in nature. The work you send to the GPU isn’t completed the moment you call draw or dispatch,...
-
9
5 Best Practices in Handling HTTP Errors in JavaScript Errors are an everyday obstacle that all developers and clients face. A typical error is when applications or a particular fun...
-
9
General Tip "The trick is to catch exceptions at the proper layer, where your program can either meaningfully recover from the exception and continue without causing further errors, or provide the user with specific information,...
-
11
Avoiding Silent Failures in Python: Best Practices for Error Handling By Bob Belderbos on 7 August 2023 ...
About Joyk
Aggregate valuable and interesting links.
Joyk means Joy of geeK