欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

.net core异常中间件的使用

程序员文章站 2022-08-12 08:10:22
正文这样写入中间件哈,那么在env环境下就会去执行usedeveloperexceptionpage。那么我们应该去看developerexceptionpagemiddleware中间件哈。那么这里...

正文

if (env.isdevelopment())
{
	app.usedeveloperexceptionpage();
}

这样写入中间件哈,那么在env环境下就会去执行usedeveloperexceptionpage。

public static iapplicationbuilder usedeveloperexceptionpage(this iapplicationbuilder app)
{
	if (app == null)
	{
		throw new argumentnullexception(nameof(app));
	}

	return app.usemiddleware<developerexceptionpagemiddleware>();
}

那么我们应该去看developerexceptionpagemiddleware中间件哈。

那么这里介绍它是如何能够捕获其他中间件的异常的哈。

里面的invoke:

其实它的操作是很简单的,直接在外面套了try catch。

里面的异常处理怎么处理的可以直接去看developerexceptionpagemiddleware 中间件,里面的操作也比较简单处理。

测试:

[httpget]
public int getservice([fromservices]iselfservice selfservice)
{
	throw new system.exception("错误");
	return 1;
}

结果:

.net core异常中间件的使用

因为上面说了,这个是dev环境下,那么生产环境不能直接给用户看到错误信息。

正式环境:

app.useexceptionhandler("/error");

将错误转移到/error 处理。具体useexceptionhandler细节篇里面介绍,有许多可以借鉴的地方。

[apicontroller]
[route("[controller]")]
public class errorcontroller : controller
{
	public ilogger<errorcontroller> _logger;
	public errorcontroller(ilogger<errorcontroller> logger)
	{
		this._logger = logger;
	}

	public iactionresult index()
	{
		var exceptionhandlerpathfeature = httpcontext.features.get<iexceptionhandlerpathfeature>();

		var ex = exceptionhandlerpathfeature?.error;

		var knownexception = ex as iknownexception;

		if (knownexception == null)
		{
			_logger.logerror(ex, ex.message);
			knownexception = knownexception.unknow;
		}
		else
		{
			knownexception = knownexception.fromknowexception(knowexception);
		}

		return view(knownexception);
	}
}

视图:

<html>
<head>

</head>
<body>
<div>
    错误码: @model.errorcode
</div>
<div>
    错误信息: @model.message
</div>
</body>
</html>

iknownexception:

public interface iknownexception
{
	public string message { get; }

	public int errorcode { get; }

	public object[] errordata { get; }
}

knownexception:

public class knownexception : iknownexception
{
	public string message
	{
		get; private set;
	}

	public int errorcode
	{
		get; private set;
	}

	public object[] errordata
	{
		get;
		private set;
	}

	public readonly static iknownexception unknow = new knownexception { message = "未知错误", errorcode = 99 };

	public static iknownexception fromknowexception(iknownexception exception)
	{
		return new knownexception{message = exception.message, errorcode = exception.errorcode, errordata = exception.errordata};
	}
}

测试1:

[httpget]
public int getservice([fromservices]iselfservice selfservice)
{
	throw new system.exception("错误");
	return 1;
}

这种属于未知异常,结果:

.net core异常中间件的使用

现在弄一个支付异常:

public class payerrorexception : exception, iknownexception
{
	public payerrorexception(string message, int errorcode, params object[] errordata): base(message)
	{
		this.errorcode = errorcode;
		this.errordata = errordata;
	}

	public int errorcode { get;private set; }

	public object[] errordata { get;private set; }
}

测试2:

[httpget]
public int getservice([fromservices]iselfservice selfservice)
{

	throw new payerrorexception("支付错误",405,null);
	return 1;
}

.net core异常中间件的使用

将异常处理放入到中间件分支中。

app.useexceptionhandler(errapp =>
{
	errapp.run(async context =>
	{
		var exceptionhandlerpathfeature = context.features.get<iexceptionhandlerpathfeature>();
		iknownexception knownexception = exceptionhandlerpathfeature.error as iknownexception;
		if (knownexception == null)
		{
			var logger = context.requestservices.getservice<ilogger<myexceptionfilterattribute>>();
			logger.logerror(exceptionhandlerpathfeature.error, exceptionhandlerpathfeature.error.message);
			knownexception = knownexception.unknown;
			context.response.statuscode = statuscodes.status500internalservererror;
		}
		else
		{
			knownexception = knownexception.fromknownexception(knownexception);
			context.response.statuscode = statuscodes.status200ok;
		}
		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));
	});
});

效果一样就不演示了。如果是已知异常错误码应该为200,一个是500异常是系统无法处理,系统错误,但是已知错误是属于系统正常处理。另一个是监控系统,认为报500错误,是会持续放出系统警告。

还有一种局部异常,只在mvc中生效,而不是全局生效:

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"
		};
	}
}

在mvc 中注册:

services.addmvc(mvcoptions =>
{
	mvcoptions.filters.add<myexceptionfilter>();
}).addjsonoptions(jsonoptions =>
{
	jsonoptions.jsonserializeroptions.encoder = system.text.encodings.web.javascriptencoder.unsaferelaxedjsonescaping;
});

最后介绍一种,只作用于某个控制器,或者action:

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"
		};
	}
}

查看一下exceptionfilterattribute头部:

[attributeusage(attributetargets.class | attributetargets.method, allowmultiple = true, inherited = true)]
public abstract class exceptionfilterattribute : attribute, iasyncexceptionfilter, iexceptionfilter, iorderedfilter

上面标志了可以放于类上也可以放于方法上。所以可以放至在controller上,也可以action上,看需求了。


以上就是.net core异常中间件的使用的详细内容,更多关于.net core异常中间件的资料请关注其它相关文章!