ASP.NET Core 2.2 MVC:包装响应 [英] ASP.NET Core 2.2 MVC : wrap responses
问题描述
我有一个用ASP.NET Core MVC开发的应用程序,带有一组用于普通视图响应和Web API的控制器.
I have an application developed in ASP.NET Core MVC with a set of controllers for normal view responses and Web API.
我试图找到一种正确的方法,用一致的类包装所有Web API响应.
I am trying to figure a correct way to wrap all Web API responses with a consistent class.
我的第一个问题是,包装来自Web API控制器的响应的正确方法是什么?由于我有两种控制器类型,因此我需要在它们之间进行区分,因为响应应该只包装给API控制器,而不能包装视图控制器.
My first question is what would be a correct approach to wrap the responses coming from Web API controllers. Since I have two controller types, I would need to distinguish between them as the responses should only be wrapped for API controller, and not view controllers.
据我了解,中间件或动作过滤器有两种选择.
As I understand there are two choices a middleware or an action filter.
起初我以为中间件是最好的选择,但是后来我意识到我仍然需要弄清楚正在处理哪种请求,这会给维护带来更多潜在的麻烦?
At first I thought the middleware would be the best choice, but then I realized that I would still need to figure out what kind of request is being processed which would add more potential headache with maintenance?
然后我看了一个动作过滤器,看来插入包装处理是一个更好的选择.
Then I looked at an action filter and it seems that it would be a better choice to plugin the wrapping handling.
例如,可以将动作过滤器添加到仅用于Web API的基本控制器中,而不是添加到处理视图的控制器中.
For example an action filter can be added to a base controller just for Web API and not controllers handling the views.
所以问题是动作过滤器是否是实现此目标的最佳方法?
So the question is whether the action filters are best approach to achieve this?
推荐答案
I would recommend you to look at result filters for this. Result filters run after a controller action has produced a result, and it allows you to look at that result and then perform some action.
For example, when you return View
in a controller action, then what gets returned is a ViewResult
which makes it easy to identify results that would cause a Razor view to be rendered.
在API控制器中,通常会返回 ObjectResult
.执行动作时,前两个将自动转换为ObjectResult
.因此,您可以只查找ObjectResult
,然后将结果更改为具有一些包装对象.看起来像这样:
Within an API controller, you would usually return a ActionResult<T>
, some model object directly, or an ObjectResult
. The former two will be automatically converted into an ObjectResult
as the action gets executed. So you can just look for ObjectResult
s and then change the result to have some wrapper object instead. This would look something like this:
public class WrapApiResponseResultFilter : IResultFilter
{
public void OnResultExecuting(ResultExecutingContext context)
{
var result = context.Result;
if (result is ObjectResult)
{
// wrap the inner object
var newValue = new WrapperObject(result.Value);
// replace the result
context.Result = new ObjectResult(newValue)
{
// copy the status code
StatusCode = result.StatusCode,
};
}
}
public void OnResultExecuted(ResultExecutedContext context)
{ }
}
这篇关于ASP.NET Core 2.2 MVC:包装响应的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!