跨所有应用程序的 MVC Action 过滤器
我正在尝试创建授权操作过滤器,它将在每个请求上触发以检查用户是否允许执行某些操作。
所以,我创建了以下类/接口:
public interface IGlobalAuthorizationFilter : IGlobalFilter, IAuthorizationFilter
{
}
public interface IGlobalFilter
{
bool ShouldBeInvoked(ControllerContext controllerContext);
}
public class GlobalFilterActionInvoker : ControllerActionInvoker
{
protected FilterInfo GlobalFilters;
public GlobalFilterActionInvoker()
{
GlobalFilters = new FilterInfo();
}
public GlobalFilterActionInvoker(FilterInfo filters)
{
GlobalFilters = filters;
}
public GlobalFilterActionInvoker(IEnumerable<IGlobalFilter> filters)
: this(new FilterInfo())
{
foreach (IGlobalFilter filter in filters)
RegisterGlobalFilter(filter);
}
public FilterInfo Filters
{
get { return GlobalFilters; }
}
public void RegisterGlobalFilter(IGlobalFilter filter)
{
if (filter is IGlobalAuthorizationFilter)
GlobalFilters.AuthorizationFilters.Add((IGlobalAuthorizationFilter) filter);
}
protected override FilterInfo GetFilters(ControllerContext controllerContext, ActionDescriptor actionDescriptor)
{
FilterInfo definedFilters = base.GetFilters(controllerContext, actionDescriptor);
foreach (IAuthorizationFilter filter in Filters.AuthorizationFilters)
{
var globalFilter = filter as IGlobalFilter;
if (globalFilter == null ||
(globalFilter.ShouldBeInvoked(controllerContext)))
{
definedFilters.AuthorizationFilters.Add(filter);
}
}
return definedFilters;
}
}
public class ApplicationControllerFactory : DefaultControllerFactory
{
private readonly IUnityContainer _container;
public ApplicationControllerFactory(IUnityContainer container)
{
this._container = container;
}
protected override IController GetControllerInstance(RequestContext requestContext, Type controllerType)
{
if ( controllerType == null )
{
throw new HttpException(404, "The file " + requestContext.HttpContext.Request.FilePath + " not found.");
}
IController icontroller = _container.Resolve(controllerType) as IController;
if (typeof(Controller).IsAssignableFrom(controllerType))
{
Controller controller = icontroller as Controller;
if (controller != null)
controller.ActionInvoker = _container.Resolve<IActionInvoker>();
return icontroller;
}
return icontroller;
}
}
以及具有需要调用的函数的类,但它不是..
public class AuthenticationActionFilter : IGlobalAuthorizationFilter
{
public bool ShouldBeInvoked(System.Web.Mvc.ControllerContext controllerContext)
{
return true;
}
public void OnAuthorization(System.Web.Mvc.AuthorizationContext filterContext)
{
}
}
并且,Global.asax注册内容:
IUnityContainer unityContainer = new UnityContainer();
unityContainer.RegisterType<IUserService, UserManager>();
unityContainer.RegisterType<IAppSettings, AppSettingsHelper>();
unityContainer.RegisterType<ICheckAccessHelper, CheckAccessHelper>().Configure<InjectedMembers>().ConfigureInjectionFor<CheckAccessHelper>(new InjectionConstructor());
unityContainer.RegisterType<IActionInvoker, GlobalFilterActionInvoker>().Configure<InjectedMembers>().ConfigureInjectionFor<GlobalFilterActionInvoker>(new InjectionConstructor());
unityContainer.RegisterType<IGlobalAuthorizationFilter, AuthenticationActionFilter>();
IControllerFactory unityControllerFactory = new ApplicationControllerFactory(unityContainer);
ControllerBuilder.Current.SetControllerFactory(unityControllerFactory);
所以,正如我所说,我的问题是函数:“ShouldBeInvoked “从来没有打电话过。
有什么帮助吗?
I am trying to create authorization action filter the will fire on each request to check if the user is allow to do some stuff.
So, i created the following classes/interfaces:
public interface IGlobalAuthorizationFilter : IGlobalFilter, IAuthorizationFilter
{
}
public interface IGlobalFilter
{
bool ShouldBeInvoked(ControllerContext controllerContext);
}
public class GlobalFilterActionInvoker : ControllerActionInvoker
{
protected FilterInfo GlobalFilters;
public GlobalFilterActionInvoker()
{
GlobalFilters = new FilterInfo();
}
public GlobalFilterActionInvoker(FilterInfo filters)
{
GlobalFilters = filters;
}
public GlobalFilterActionInvoker(IEnumerable<IGlobalFilter> filters)
: this(new FilterInfo())
{
foreach (IGlobalFilter filter in filters)
RegisterGlobalFilter(filter);
}
public FilterInfo Filters
{
get { return GlobalFilters; }
}
public void RegisterGlobalFilter(IGlobalFilter filter)
{
if (filter is IGlobalAuthorizationFilter)
GlobalFilters.AuthorizationFilters.Add((IGlobalAuthorizationFilter) filter);
}
protected override FilterInfo GetFilters(ControllerContext controllerContext, ActionDescriptor actionDescriptor)
{
FilterInfo definedFilters = base.GetFilters(controllerContext, actionDescriptor);
foreach (IAuthorizationFilter filter in Filters.AuthorizationFilters)
{
var globalFilter = filter as IGlobalFilter;
if (globalFilter == null ||
(globalFilter.ShouldBeInvoked(controllerContext)))
{
definedFilters.AuthorizationFilters.Add(filter);
}
}
return definedFilters;
}
}
public class ApplicationControllerFactory : DefaultControllerFactory
{
private readonly IUnityContainer _container;
public ApplicationControllerFactory(IUnityContainer container)
{
this._container = container;
}
protected override IController GetControllerInstance(RequestContext requestContext, Type controllerType)
{
if ( controllerType == null )
{
throw new HttpException(404, "The file " + requestContext.HttpContext.Request.FilePath + " not found.");
}
IController icontroller = _container.Resolve(controllerType) as IController;
if (typeof(Controller).IsAssignableFrom(controllerType))
{
Controller controller = icontroller as Controller;
if (controller != null)
controller.ActionInvoker = _container.Resolve<IActionInvoker>();
return icontroller;
}
return icontroller;
}
}
And the class with the function that need to be called, but its not..
public class AuthenticationActionFilter : IGlobalAuthorizationFilter
{
public bool ShouldBeInvoked(System.Web.Mvc.ControllerContext controllerContext)
{
return true;
}
public void OnAuthorization(System.Web.Mvc.AuthorizationContext filterContext)
{
}
}
And, the Global.asax registration stuff:
IUnityContainer unityContainer = new UnityContainer();
unityContainer.RegisterType<IUserService, UserManager>();
unityContainer.RegisterType<IAppSettings, AppSettingsHelper>();
unityContainer.RegisterType<ICheckAccessHelper, CheckAccessHelper>().Configure<InjectedMembers>().ConfigureInjectionFor<CheckAccessHelper>(new InjectionConstructor());
unityContainer.RegisterType<IActionInvoker, GlobalFilterActionInvoker>().Configure<InjectedMembers>().ConfigureInjectionFor<GlobalFilterActionInvoker>(new InjectionConstructor());
unityContainer.RegisterType<IGlobalAuthorizationFilter, AuthenticationActionFilter>();
IControllerFactory unityControllerFactory = new ApplicationControllerFactory(unityContainer);
ControllerBuilder.Current.SetControllerFactory(unityControllerFactory);
So, as i said, my problem is the function: "ShouldBeInvoked" never called.
Any help?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
我相信这个过滤器只会在用 [Authorize] 修饰的操作上调用,您希望这个过滤器运行的方法上有这个吗?
I believe this filter would only be invoked on actions decorated with [Authorize] do you have that on the methods you want this filter to run?