NCIOCPL / NCI.OCPL.Api.Shared

Common code shared between APIs
0 stars 1 forks source link

Only log application errors #50

Open blairlearn opened 2 years ago

blairlearn commented 2 years ago

Issue description

Both application and user errors are being indiscriminately written to the Windows Application log.

This is because our controllers throw APIErrorException for errors and use a global exception handler to return a suitable HTTP status code. Despite the exception handler in the startup, these exceptions are considered unhandled exceptions and logged in the Windows event log, regardless of whether the user was due to application logic or something the user did.

ESTIMATE TBD

What's the expected change?

What's the current functionality?

What's the updated acceptance criteria?

Additional details / screenshot

image

Related Tickets

blairlearn commented 1 year ago

Part of the solution is to create an Exception Filter. The filter should behave as:

// Partial implemenation of the exception filter

using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.Filters;

using NCI.OCPL.Api.Common;

public class NCIResponseExceptionFilter : IActionFilter, IOrderedFilter
{
    public int Order => int.MaxValue - 10;

    public void OnActionExecuting(ActionExecutingContext context) { }

    public void OnActionExecuted(ActionExecutedContext context)
    {
        if (context.Exception is APIErrorException httpResponseException)
        {
            context.Result = new ObjectResult(new { Message = httpResponseException.Message })
            {
                StatusCode = httpResponseException.HttpStatusCode
            };

            context.ExceptionHandled = true;
        }
    }
}

// Register the filter in NciStartupBase
services.AddControllers(options => {
    options.Filters.Add<NCIResponseExceptionFilter>();
});
blairlearn commented 1 year ago

Set up logging to the Windows event viewer with code along the lines of this in NciProgramBase.cs, but use the appropriate log type for the OS (e.g. RuntimeInformation.IsOSPlatform(OSPlatform.Windows))

public static IHostBuilder CreateHostBuilder (string[] args) =>
    Host.CreateDefaultBuilder(args)
        .ConfigureLogging (logging =>
        {
            logging.AddEventLog (new EventLogSettings
            {
                SourceName = "YourSourceName",
                LogName = "Application"
            }):
        })
        .ConfigureWebHostDefaults (webBuilder =>
        {
            webBuilder. UseStartup<Startup> ( ) :
        }):