开始编写一个简单的过滤器,在每个动作加载时从请求中提取一些东西,从其他类似的堆栈流中复制一些代码:
public class TestKeyAttribute : ActionFilterAttribute
{
public override void OnActionExecuting(HttpActionContext context)
{
if (context.Request.Properties.ContainsKey("test"))
{
// do stuff
}
}
}
然后使用其余部分添加属性:
public static void RegisterGlobalFilters(GlobalFilterCollection filters)
{
GlobalConfiguration.Configuration.Filters.Add(new ElmahHandledErrorLoggerFilter());
filters.Add(new HandleErrorAttribute());
filters.Add(new TestKeyAttribute());
}
运行时,会导致此错误:
The given filter instance must implement one or more of the following filter
interfaces: IAuthorizationFilter, IActionFilter, IResultFilter, IExceptionFilter.
我发现的大多数链接都与MVC 3有关,这似乎有效;然而,我正在使用MVC 4并使用Web API - 我现在需要注册属性吗?
请注意:我不希望附加到Web API控制器的过滤器(将其添加到GlobalConfiguration.Configuration.Filters确实有效),而是普通的Web控制器。
编辑:我知道我可以通过继承IActionFilter并使用OnActionExecuting来实现这一点,我只是好奇为什么这种方法不起作用,因为一堆教程似乎在说应该。
答案 0 :(得分:7)
我遇到了同样的错误,并且在ElmahHandledErrorLoggerFilter
实施IExceptionFilter
时感到困惑。
经过调查,我踢了自己,我将filters.Add(new ElmahHandledErrorLoggerFilter());
添加到FilterConfig类下的MVC站点配置中。将config.Filters.Add(new ElmahHandleErrorApiAttribute());
添加到WebApiConfig类可以正常工作。
注意:我在这里使用的是WebAPi v1,但我以同样的方式配置了v2项目。
答案 1 :(得分:2)
这不起作用的原因是您的过滤器是WebAPI过滤器,它不能与Mvc过滤器互换。 Mvc和WebAPI FilterAttribute以及相关的类和接口有许多相同的名称(这就是为什么教程似乎说这应该有效),但它们存在于不同的命名空间中。 Mvc过滤器类位于System.Web.Mvc
,WebAPI类位于System.Web.Http
。
答案 2 :(得分:1)
使用MVC4时,自定义属性所在的项目必须包含对System.Web.Http.Common库的引用。我使用NuGet将它添加到我的项目中,嘿presto!错误消失了。