.NET Core开发实战(第22课:异常处理中间件:区分真异常与逻辑异常)--学习笔记(下)...

接下来介绍使用代理方法的方式,也就是说把 ErrorController 整段逻辑直接定义在注册的地方,使用一个匿名委托来处理,这里的逻辑与之前的逻辑是相同的

app.UseExceptionHandler(errApp =>
{errApp.Run(async context =>{// 在 Features 里面获取异常var exceptionHandlerPathFeature = context.Features.Get<IExceptionHandlerPathFeature>();// 识别异常是否为 IKnownExceptionIKnownException knownException = exceptionHandlerPathFeature.Error as IKnownException;if (knownException == null){// 如果不是则记录并且把错误的响应码响应成 Http 500var logger = context.RequestServices.GetService<ILogger<MyExceptionFilterAttribute>>();logger.LogError(exceptionHandlerPathFeature.Error, exceptionHandlerPathFeature.Error.Message);knownException = KnownException.Unknown;context.Response.StatusCode = StatusCodes.Status500InternalServerError;}else{// 如果捕获到的是一个业务逻辑的异常,Http 响应码应该给是 200knownException = KnownException.FromKnownException(knownException);context.Response.StatusCode = StatusCodes.Status200OK;}// 然后再把响应信息通过 json 的方式输出出去var jsonOptions = context.RequestServices.GetService<IOptions<JsonOptions>>();context.Response.ContentType = "application/json; charset=utf-8";await context.Response.WriteAsync(System.Text.Json.JsonSerializer.Serialize(knownException, jsonOptions.Value.JsonSerializerOptions));});
});

为什么对于未知的异常要输出 Http 500,而对于业务逻辑的异常,建议输出 Http 200?

因为监控系统实际上会对 Http 的响应码进行识别,当监控系统识别到 Http 响应是 500 的比例比较高的情况下,会认为系统的可用性有问题,这个时候告警系统就会发出警告

对于已知的业务逻辑的这种正常的识别的话,用正常的 Http 200 来处理是一个正常的行为,这样就可以让监控系统更好的工作,正确的识别出系统的一些未知的错误信息,错误的告警,让告警系统更加的灵敏,也避免了业务逻辑的异常干扰告警系统

接下来看一下第三种,通过异常过滤器的方式

这种方式实际上是作用在 MVC 的整个框架的体系下面的,它并不是在中间件的最早期发生作用的,它是在 MVC 的整个生命周期里面发生作用,也就是说它只能工作在 MVC Web API 的请求周期里面

首先自定义一个 MyExceptionFilter

namespace ExceptionDemo.Exceptions
{public class MyExceptionFilter : IExceptionFilter{public void OnException(ExceptionContext context){IKnownException knownException = context.Exception as IKnownException;if (knownException == null){var logger = context.HttpContext.RequestServices.GetService<ILogger<MyExceptionFilterAttribute>>();logger.LogError(context.Exception, context.Exception.Message);knownException = KnownException.Unknown;context.HttpContext.Response.StatusCode = StatusCodes.Status500InternalServerError;}else{knownException = KnownException.FromKnownException(knownException);context.HttpContext.Response.StatusCode = StatusCodes.Status200OK;}context.Result = new JsonResult(knownException){ContentType = "application/json; charset=utf-8"};}}
}

处理逻辑与之前的相同

接着注册 Filters

services.AddMvc(mvcOptions =>
{mvcOptions.Filters.Add<MyExceptionFilter>();
}).AddJsonOptions(jsonoptions =>
{jsonoptions.JsonSerializerOptions.Encoder = System.Text.Encodings.Web.JavaScriptEncoder.UnsafeRelaxedJsonEscaping;
});

启动程序,输出如下:

{"message":"未知错误","errorCode":9999,"errorData":null}

输出与之前的一致,因为这是在 Controller 里面输出了错误

如果在 MVC 的中间件之前输出错误的话,它是没办法处理的

这个场景一般情况下是指需要对 Controller 进行特殊的异常处理,而对于中间件整体来讲的话,又要用另一种特殊的逻辑来处理的时候,可以用 ExceptionFilter 的方式处理

这种方式还可以通过 Attribute 的方式

自定义一个 MyExceptionFilterAttribute

namespace ExceptionDemo.Exceptions
{public class MyExceptionFilterAttribute : ExceptionFilterAttribute{public override void OnException(ExceptionContext context){IKnownException knownException = context.Exception as IKnownException;if (knownException == null){var logger = context.HttpContext.RequestServices.GetService<ILogger<MyExceptionFilterAttribute>>();logger.LogError(context.Exception, context.Exception.Message);knownException = KnownException.Unknown;context.HttpContext.Response.StatusCode = StatusCodes.Status500InternalServerError;}else{knownException = KnownException.FromKnownException(knownException);context.HttpContext.Response.StatusCode = StatusCodes.Status200OK;}context.Result = new JsonResult(knownException){ContentType = "application/json; charset=utf-8"};}}
}

在 Controller 上面标注 MyExceptionFilter

[MyExceptionFilter]
public class WeatherForecastController : ControllerBase

启动运行之后效果相同

这两种方式的效果是对等的,区别在于说可以更细粒度的对异常处理进行控制,可以指定部分的 Controller 或者 Exception,来决定我们的异常处理,也可以在全局注册 ExceptionFilter

当然因为 ExceptionFilterAttribute 也实现了 IExceptionFilter,所以它也可以注册到全局,也可以把它当作全局异常处理的过滤器来使用,Controller 上面也就不需要标记了

注册 Filters

services.AddMvc(mvcOptions =>
{//mvcOptions.Filters.Add<MyExceptionFilter>();mvcOptions.Filters.Add<MyExceptionFilterAttribute>();
}).AddJsonOptions(jsonoptions =>
{jsonoptions.JsonSerializerOptions.Encoder = System.Text.Encodings.Web.JavaScriptEncoder.UnsafeRelaxedJsonEscaping;
});

在 Controller 上面取消标注 MyExceptionFilter

//[MyExceptionFilter]
public class WeatherForecastController : ControllerBase

启动程序,输出结果一致

这个场景对于我们定义一些 API,然后对 API 进行定义我们的异常处理的约定是很有帮助的

总结一下

首先我们需要定义特定的异常类或者接口,我们可以定义抽象类,也可以用接口的方式,例子中是通过接口的方式表示业务逻辑的异常

对于业务逻辑的异常,实际上需要定义全局的错误码

对于未知的异常,应该输出特定的输出信息和错误码,然后记录完整的日志,我们不应该把系统内部的一些比如说异常堆栈这些信息输出给用户

对于已知的业务逻辑的异常,用 Http 200 的方式,对于未知的异常,用 Http 500 的方式,这样可以让监控系统更好的工作

另外一个建议就是尽量记录所有的异常的详细信息,以供后续对日志进行分析,也供监控系统做一些特定的监控警告

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/311151.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【朝夕技术专刊】Core3.1WebApi_Filter-Authorize详解

欢迎大家阅读《朝夕Net社区技术专刊》第6期我们致力于.NetCore的推广和落地&#xff0c;为更好的帮助大家学习&#xff0c;方便分享干货&#xff0c;特创此刊&#xff01;很高兴你能成为忠实读者&#xff0c;文末福利不要错过哦&#xff01;前言&#xff1a;本部分文档将详细给…

以正确的方式下载和配置 ASP.NET Core 官方源码

我们可以在Github上面直接查看ASP.NETCore 3.x的源代码&#xff0c;但是我们也可以把源代码下载下来进行查看。而下载源代码进行查看有很多好处&#xff1a;任意的导航源代码内置了一个示例项目直接调试源代码下载源代码想下载并配置好源码&#xff0c;你需要&#xff1a;最新版…

h5应用 vue 钉钉_uniapp开发一个小视频应用(一)

“uni-app 是一个使用 Vue.js 开发所有前端应用的框架&#xff0c;是一种终极的跨平台解决方案&#xff0c;这里的平台&#xff0c;主要指的是App平台(android、ios)、小程序平台、H5平台。开发者编写一套代码&#xff0c;可发布到iOS、Android、H5、以及各种小程序(微信/支付宝…

Blazor入门

&#xff2e;&#xff2f;&#xff37;现在行动&#xff01;Blazor是一个基于C#&#xff0c; Razor和 HTML的新的Web UI框架。它通过WebAssembly运行在浏览器中。有利于使用C#而不是JavaScript构建交互式的Web UI。这篇文章演示了如何使用Blazor构建SPA应用。Blazor简化了可在任…

C#桌面开发的未来WebWindow

WebWindowWebWindow是跨平台的库。Web Window的当前实验实现可在以下平台上运行&#xff1a;Windows – 需要基于Chromium的EdgeLinux – 使用WebKitMac – 需要Safari源码https://github.com/SteveSandersonMS/WebWindow.gitZeje Fork的分支&#xff1a;https://github.com/ze…

C#小游戏—钢铁侠VS太空侵略者

身为漫威迷&#xff0c;最近又把《钢铁侠》和《复仇者联盟》系列又重温了一遍&#xff0c;真的是印证了那句话&#xff1a;“读书百遍&#xff0c;其意自现”。看电影一个道理&#xff0c;每看一遍&#xff0c;都有不懂的感受~ 不知道大伙是不是也有同样的感受&#xff0c;对于…

受检异常 非受检异常_这样设计 Java 异常更优雅,赶紧学

来源&#xff1a;Lrwinlrwinx.github.io/2016/04/28/如何优雅的设计java异常/导语异常处理是程序开发中必不可少操作之一&#xff0c;但如何正确优雅的对异常进行处理确是一门学问&#xff0c;笔者根据自己的开发经验来谈一谈我是如何对异常进行处理的。由于本文只作一些经验之…

.NET Core开发实战(第23课:静态文件中间件:前后端分离开发合并部署骚操作)--学习笔记(上)...

23 | 静态文件中间件&#xff1a;前后端分离开发合并部署骚操作我们先来看一下静态文件中间件有哪些能力1、支持指定相对路径2、支持目录的浏览3、支持设置默认文档4、支持多目录映射源码链接&#xff1a;https://github.com/witskeeper/geektime/tree/master/samples/StaticFi…

src获取同级目录中的图片_一个简单的Python爬虫实例:百度贴吧页面下载图片

本文主要实现一个简单的爬虫&#xff0c;目的是从一个百度贴吧页面下载图片。1. 概述本文主要实现一个简单的爬虫&#xff0c;目的是从一个百度贴吧页面下载图片。下载图片的步骤如下&#xff1a;获取网页html文本内容&#xff1b;分析html中图片的html标签特征&#xff0c;用正…

十问十答 Apache 许可证

Apache 许可证由 Apache Software Foundation&#xff08;ASF&#xff09;发行&#xff0c;是一个由强大社区支持的流行的被广泛部署的许可证。Apache 许可证允许你自由地使用、修改和分发任何 Apache 许可的产品&#xff0c;前提是遵循 Apache 许可的条款。01Apache 许可证的条…

(一)基于企业现金流预测的投资决策-项目介绍

项目背景 某企业想提高现金流的利用率,以便产生更大的投资收益。遇到的问题是:何如在保证更多的资金流向高收益投资的同时,不出现资金短缺的问题。 确定可用于投资的金额 Step1 预测未来的收入、支出和余额 潜在逻辑: 现金流 = 收入 - 支出当月余额(资金存量)= 上月余…

应用程序使用统计信息 – .NET CORE(C#) WPF界面设计

本文首发地址&#xff1a;https://dotnet9.com/10546.html关键功能点抽屉式菜单圆形进度条Demo演示&#xff1a;1. 新建项目使用 VS 2019 的 .NET Core 3.1 WPF 项目模板&#xff0c;创建名为 “MobileAppUsageDashboardCore” 的项目&#xff0c;NuGet 引入 MaterialDesign 的…

iso qemu 安装ubuntu_基于libvirt 和QEMU在macOS安装Ubuntu

在流行的虚拟架构体系中&#xff0c;最重要的技术当然要数libvirt和QEMU了。包括Linux虚拟化技术中KVM和xen都使用了QEMU。关于Xen和KVM进行虚拟化&#xff0c;以及在Window下使用Vmware&#xff0c;VirtualBox和hyper-v构建虚拟机&#xff0c;可能大家都有过很多的尝试。今天我…

在Ocelot中使用自定义的中间件(一)

Ocelot是ASP.NET Core下的API网关的一种实现&#xff0c;在微服务架构领域发挥了非常重要的作用。本文不会从整个微服务架构的角度来介绍Ocelot&#xff0c;而是介绍一下最近在学习过程中遇到的一个问题&#xff0c;以及如何使用中间件&#xff08;Middleware&#xff09;来解决…

多队列 部分队列没有包_记一次TCP全队列溢出问题排查过程

简介&#xff1a;记一次TCP全队列溢出问题排查过程1. 前言本文排查的问题是经典的TCP队列溢出问题&#xff0c;因TCP队列问题在操作系统层面没有明显的指标异常&#xff0c;容易被忽略&#xff0c;故把排查过程分享给大家。2. 问题描述A服务调用B服务接口超时&#xff0c;B服务…

[蓝桥杯2015决赛]完美正方形-dfs

题目描述 如果一些边长互不相同的正方形&#xff0c;可以恰好拼出一个更大的正方形&#xff0c;则称其为完美正方形。 历史上&#xff0c;人们花了很久才找到了若干完美正方形。 比如&#xff1a;如下边长的22个正方形 2 3 4 6 7 8 12 13 14 15 16 17 18 21 22 23 24 26 27 28 …

销量预测设计

目录一、算法计算逻辑举个直观的例子销量预测二、项目背景三、算法与业务的关系四、关于业务人员对未来外部变量“打标签”&#xff1a;五、关于预测颗粒度&#xff1a;六、关于预测准确率和影响准确率的因素&#xff1a;一、算法计算逻辑 销量预测算法建模要用到的数据&#…

.NET Core开发实战(第23课:静态文件中间件:前后端分离开发合并部署骚操作)--学习笔记(下)...

23 | 静态文件中间件&#xff1a;前后端分离开发合并部署骚操作这里还有一个比较特殊的用法一般情况下&#xff0c;我们前后端分离的架构&#xff0c;前端会编译成一个 index.html 文件和若干个 CSS 文件和 JavaScript 和图片文件CSS 文件和 JavaScript 和图片文件一般会部署在…

springboot 历史版本文档_乘风破浪,SpringBoot入门

SpringBoot入门篇前言在普通的java项目中&#xff0c;大量的xml文件配置起来相当繁琐&#xff0c;导致了开发效率非常低下&#xff0c;整合第三方框架的配置可能会存在冲突问题导致部署效率低&#xff0c;打包方式是将项目打成一个war包放入到tomactwebapps目录下执行。简单来说…

简洁直观解释精确率、召回率、F1 值、ROC、AUC

混淆矩阵 当我们在做二分类预测时&#xff0c;把预测情况与实际情况的所有结果两两混合&#xff0c;结果就会出现以下4种情况&#xff0c;就组成了混淆矩阵。 P&#xff08;Positive&#xff09;&#xff1a;代表正样本N&#xff08;Negative&#xff09;&#xff1a;代表负样…