2011-07-18 57 views
12

我有以下签名用asp.net mvc的动作奇怪的行为过滤AttributeUsage

[AttributeUsage(AttributeTargets.Method, AllowMultiple = true)] 
public class UnitOfWorkAttribute : ActionFilterAttribute 

根据MSDN的行为过滤器:

该物业的AllowMultiple指示是否的 你的属性的多个实例可以存在于一个元素上。如果设置为true,则允许多个 实例;如果设置为false(默认值),则只允许有一个 实例。

在MVC中,行为似乎有点奇怪。当我用这个属性修饰动作时,我发现过滤器的OnActionExecuting方法执行了两次。

该过滤器仅在操作上声明,而不是在控制器上声明,并且我清除了任何全局过滤器。有人可以解释这种行为吗?

+0

只是_AllowMultiple_这会导致_OnActionExecuting_被调用两次,或者你真的用两个属性实例来修饰你的动作吗? – Codo

+0

@Codo,不,我不需要多个实例,因此将AllowMultiple设置为false可以解决问题,但它不能解释它。可能是asp.net mvc中的错误? –

+0

这个动作确实没有发射两次?只有属性? – dknaack

回答

29

我遇到了同样的问题。 (我安装了一个全球性的过滤器(只有一次),并发现其IActionFilterIResultFilter方法被调用两次,每次请求。在传递给这些方法的filterContext.HttpContext对象正是为这两个调用相同)。

这横空出世这是由于在视图中使用Html.Action所致。它看起来(从查看调用堆栈)调用Html.Action reentrantly处理子操作方法(在处理初始操作方法期间)并且为两者调用过滤器。

您可以通过检查filterContext.IsChildAction属性来检测此情况。

+0

您节省了我的一天:-) –

+0

非常感谢soo!正是我需要的。 – Vindberg

+0

这很有用,但它为什么这样做。我回想起所有使用自定义操作过滤器的应用程序,并且很担心。 –

0

我从我的自定义操作筛选器类执行了两次也有OnActionExecuting方法。

在某一点上我在的global.asax.cs文件添加到了我的Application_Start方法:

GlobalConfiguration.Configuration.Filters.Add(new MyCustomActionFilter()); 

很显然,我的行为过滤器已经加入到Filters收集这是导致双呼叫OnActionExecutingOnActionExecuted。因此applicaton_start中的那一行是不需要的。