ZetCode

ASP.NET HandleError

最后修改于 2025 年 4 月 3 日

在本文中,我们使用 HandleError 探索 ASP.NET 8 中的错误处理。正确的错误处理对于构建健壮的 Web 应用程序至关重要。

ASP.NET 提供了多种错误处理机制。HandleError 属性提供了一种声明式的方法来管理控制器中的异常。

基本定义

ASP.NET 中的 HandleError 属性允许您指定如何处理控制器操作的异常。它是 MVC 框架的一部分。

当应用于控制器或操作方法时,HandleError 会捕获执行期间未处理的异常。它可以重定向到自定义错误视图。

HandleError 与 ASP.NET 错误处理管道协同工作。它为操作或控制器级别的异常处理提供了精细控制。

ASP.NET HandleError 示例

以下示例演示了在带有 .NET 8 的 ASP.NET MVC 应用程序中使用 HandleError。

Program.cs
var builder = WebApplication.CreateBuilder(args);

builder.Services.AddControllersWithViews(options =>
{
    options.Filters.Add(new HandleErrorAttribute()
    {
        ExceptionType = typeof(Exception),
        View = "Error"
    });
});

var app = builder.Build();

if (!app.Environment.IsDevelopment())
{
    app.UseExceptionHandler("/Home/Error");
    app.UseHsts();
}

app.UseHttpsRedirection();
app.UseStaticFiles();
app.UseRouting();
app.UseAuthorization();

app.MapControllerRoute(
    name: "default",
    pattern: "{controller=Home}/{action=Index}/{id?}");

app.Run();

这会在 ASP.NET 应用程序中设置全局错误处理。HandleErrorAttribute 被注册为全局过滤器。

Controllers/ProductsController.cs
using Microsoft.AspNetCore.Mvc;
using System.Diagnostics;

public class ProductsController : Controller
{
    private readonly List<Product> _products = new()
    {
        new Product(1, "Laptop", 999.99m),
        new Product(2, "Mouse", 19.99m),
        new Product(3, "Keyboard", 49.99m)
    };

    [HandleError(ExceptionType = typeof(KeyNotFoundException), 
                View = "ProductNotFound")]
    public IActionResult Details(int id)
    {
        var product = _products.FirstOrDefault(p => p.Id == id);
        if (product == null)
        {
            throw new KeyNotFoundException($"Product {id} not found");
        }
        return View(product);
    }

    [HandleError(ExceptionType = typeof(DivideByZeroException), 
                View = "MathError")]
    public IActionResult CalculateDiscount(int productId, decimal divisor)
    {
        var product = _products.First(p => p.Id == productId);
        var discountedPrice = product.Price / divisor;
        return View(discountedPrice);
    }
}

public record Product(int Id, string Name, decimal Price);

此控制器演示了两种不同的错误处理场景。Details 操作使用自定义视图处理找不到产品错误。

CalculateDiscount 操作专门捕获 DivideByZeroException。每个 HandleError 属性都指定要捕获的异常类型。

Views/Shared/Error.cshtml
@model ErrorViewModel
@{
    ViewData["Title"] = "Error";
}

<h1 class="text-danger">Error.</h1>
<h2 class="text-danger">An error occurred while processing your request.</h2>

@if (Model.ShowRequestId)
{
    <p>
        <strong>Request ID:</strong> <code>@Model.RequestId</code>
    </p>
}

<h3>Development Mode</h3>
<p>
    Swapping to <strong>Development</strong> environment will display more detailed information about the error that occurred.
</p>

这是将为未处理异常显示的默认错误视图。可以为特定异常创建自定义错误视图。

该示例展示了 HandleError 如何提供对异常处理的精细控制。不同的异常可以路由到不同的视图。

来源

Microsoft ASP.NET MVC Filters 文档

在本文中,我们探索了 ASP.NET 8 中的 HandleError 属性。这个强大的功能简化了 MVC 应用程序中的异常处理。

作者

我的名字是 Jan Bodnar,我是一名充满热情的程序员,拥有丰富的编程经验。我从 2007 年开始撰写编程文章。到目前为止,我已撰写了 1400 多篇文章和 8 本电子书。我在编程教学方面拥有十多年的经验。

列出所有 ASP.NET 教程