Skip to content
bitzorcas
中EN

Reference

Global Exception Handling and RFC 9457 Problem Details

Explore the BitzOrcas.Modern error management architecture. Learn Result flow control, GlobalExceptionHandler catch-alls, and RFC 9457 Problem Details standards.

Last updated

In production systems, bad error handling manifests in two extremes:

  1. Leaking Raw Stack Traces: Returning NullReferenceException stacks directly to callers, exposing internal SQL schemas and server paths to security exploits;
  2. Returning 200 OK for Errors: Hiding errors behind { code: -1, msg: "Failed" }, breaking HTTP protocol semantics and disabling upstream gateway retries.

BitzOrcas.Modern implements “Layered Error Governance + Standard RFC 9457 Problem Details”:

  • Expected Business Invariants: Handlers return typed Result.Failure(Error) mapped automatically to standard 4xx statuses;
  • Unexpected Infrastructure Crashes: ASP.NET Core IExceptionHandler intercepts crashes, redacting stacks and returning standard 500 Problem Details.

Error Governance and Exception Handling Lifecycle

Result.SuccessResult.Failure (Validation /Conflict)Unexpected Exception

1. Inbound HTTP Request

2. 10-Stage Pipeline and Handler

3. Evaluate Result State

4. HTTP 200 OK (Bare Business Payload)

5. Map to HTTP 400/404/409 (RFC 9457)

6. GlobalExceptionHandler (Catch-All)

7. Structured Alert Log + HTTP 500 Problem Details (Sanitized)


Step 1: Flow Control via Typed Result

Never throw business exceptions! Use typed Result objects for all domain branches:

CancelOrderCommandHandler.cs: Domain Flow Control
using System.Threading;
using System.Threading.Tasks;
using BitzOrcas.Domain.Abstractions;
using BitzOrcas.Domain.Results;
public static class OrderErrors
{
public static readonly Error NotFound =
Error.NotFound("Order.NotFound", "The specified order was not found.");
public static readonly Error CannotCancel =
Error.Conflict("Order.CannotCancel", "Completed or shipped orders cannot be cancelled.");
}
public sealed class CancelOrderCommandHandler(
ICommandRepository<Order, string> orderRepository)
{
public async ValueTask<Result> Handle(CancelOrderCommand command, CancellationToken ct)
{
// 1. Load aggregate root
var orderResult = await orderRepository.FindAsync(command.OrderId, ct);
if (orderResult.IsFailure)
{
// 2. Resource not found: return typed NotFound error without throwing exceptions
return Result.Failure(orderResult.Error);
}
var order = orderResult.GetValueOrThrow();
// 3. Evaluate cancellation invariants
var cancelResult = order.Cancel(command.Reason);
if (cancelResult.IsFailure)
{
// 4. State conflict: return typed Conflict error
return cancelResult;
}
await orderRepository.SaveAsync(order, ct);
return Result.Success();
}
}

Step 2: Global Catch-All (GlobalExceptionHandler)

For unexpected database timeouts or null pointers, the global handler sanitizes responses:

GlobalExceptionHandler.cs: Global Exception Guard
using Microsoft.AspNetCore.Diagnostics;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Logging;
public sealed class GlobalExceptionHandler(ILogger<GlobalExceptionHandler> logger) : IExceptionHandler
{
public async ValueTask<bool> TryHandleAsync(
HttpContext httpContext,
Exception exception,
CancellationToken cancellationToken)
{
var traceId = httpContext.TraceIdentifier;
// 1. Log structured fatal error with full stack trace for engineering alerts
logger.LogError(exception, "Unhandled system exception intercepted, TraceId: {TraceId}", traceId);
// 2. Safely emit RFC 9457 compliant 500 response to client
httpContext.Response.StatusCode = StatusCodes.Status500InternalServerError;
httpContext.Response.ContentType = "application/problem+json";
var problemDetails = new
{
type = "https://errors.bitzorcas.corp/internal-error",
title = "Internal Server Error",
status = 500,
detail = "An unexpected server error occurred. Please contact support with the trace ID.",
traceId
};
await httpContext.Response.WriteAsJsonAsync(problemDetails, cancellationToken);
return true;
}
}

Summary

BitzOrcas error governance guarantees enterprise resilience:

  • Zero Exception Flow Control: Microsecond performance with zero GC allocations;
  • Zero Stack Leaks: Sanitizes physical paths and internal schemas from API consumers;
  • RFC Compliance: Clean Problem Details JSON for robust client handling.

100%

Scroll or use controls to zoom · drag when enlarged · double-click for 100% / 200%