Create an wrapper class based on IFilterProvider that returns the global FilterProviders.Providers.GetFilters() result, like this:
public class FilterProvider
: IFilterProvider
{
#region IFilterProvider Members
public IEnumerable<Filter> GetFilters(ControllerContext controllerContext, ActionDescriptor actionDescriptor)
{
return FilterProviders.Providers.GetFilters(controllerContext, actionDescriptor);
}
#endregion
}
Then, adjust the constructor in your classes that require the dependency.
public class MyBusinessClass
: IMyBusinessClass
{
public MyBusinessClass(
IFilterProvider filterProvider
)
{
if (filterProvider == null)
throw new ArgumentNullException("filterProvider");
this.filterProvider = filterProvider;
}
protected readonly IFilterProvider filterProvider;
public IEnumerable<AuthorizeAttribute> GetAuthorizeAttributes(ControllerContext controllerContext, ActionDescriptor actionDescriptor)
{
var filters = filterProvider.GetFilters(controllerContext, actionDescriptor);
return filters
.Where(f => typeof(AuthorizeAttribute).IsAssignableFrom(f.Instance.GetType()))
.Select(f => f.Instance as AuthorizeAttribute);
}
}
Next, configure your DI container to use FilterProvider concrete type as the default.
container.Configure(x => x
.For<IFilterProvider>()
.Use<FilterProvider>()
);
If you need to override the default and provide your own IFilterProvider, now it is just a matter of creating a new concrete type based on IFilterProvider and swapping what is registered in the DI container.
//container.Configure(x => x
// .For<IFilterProvider>()
// .Use<FilterProvider>()
//);
container.Configure(x => x
.For<IFilterProvider>()
.Use<NewFilterProvider>()
);
Most importantly, there is no service locator anywhere in this pattern.