public ControllerActionInvokerState GetState(ControllerContext controllerContext) { // Filter instances from statically defined filter descriptors + from filter providers IFilterMetadata[] filters; var cache = CurrentCache; var actionDescriptor = controllerContext.ActionDescriptor; Entry cacheEntry; if (cache.Entries.TryGetValue(actionDescriptor, out cacheEntry)) { // Deep copy the cached filter items as filter providers could modify them var filterItems = new List<FilterItem>(cacheEntry.FilterItems.Count); for (var i = 0; i < cacheEntry.FilterItems.Count; i++) { var filterItem = cacheEntry.FilterItems[i]; filterItems.Add( new FilterItem(filterItem.Descriptor) { Filter = filterItem.Filter, IsReusable = filterItem.IsReusable }); } filters = GetFilters(controllerContext, filterItems); return new ControllerActionInvokerState(filters, cacheEntry.ActionMethodExecutor); } var executor = ObjectMethodExecutor.Create( actionDescriptor.MethodInfo, actionDescriptor.ControllerTypeInfo); var staticFilterItems = new List<FilterItem>(actionDescriptor.FilterDescriptors.Count); for (var i = 0; i < actionDescriptor.FilterDescriptors.Count; i++) { staticFilterItems.Add(new FilterItem(actionDescriptor.FilterDescriptors[i])); } // Create a separate collection as we want to hold onto the statically defined filter items // in order to cache them var allFilterItems = new List<FilterItem>(staticFilterItems); filters = GetFilters(controllerContext, allFilterItems); // Cache the filter items based on the following criteria // 1. Are created statically (ex: via filter attributes, added to global filter list etc.) // 2. Are re-usable for (var i = 0; i < staticFilterItems.Count; i++) { var item = staticFilterItems[i]; if (!item.IsReusable) { item.Filter = null; } } cacheEntry = new Entry(staticFilterItems, executor); cache.Entries.TryAdd(actionDescriptor, cacheEntry); return new ControllerActionInvokerState(filters, cacheEntry.ActionMethodExecutor); }
private static ObjectMethodExecutor CreateExecutor(ControllerActionDescriptor actionDescriptor) { return(ObjectMethodExecutor.Create(actionDescriptor.MethodInfo, actionDescriptor.ControllerTypeInfo)); }