开发者

Do ASP.Net MVC Controller Attributes Execute Before or After the Action?

Consider the following code:

    [Authenticate(Order = 1)]
    public ActionResult SomeActionThatRequiresAuthentication()
    { 
        var model = new SomeViewModel(); 
        // Do something with an authenticated session/user...
        return View(model);
    }

Does the Authenticate attribute happen before or after the code inside the SomeActionThatRequiresAuthentication method is executed?

I am asking this because I have a Attribute that does something like this:

    public class Authenticate : CustomAuthorizeAttribute
{
 开发者_如何学Python   public override void OnAuthorization(AuthorizationContext filterContext)
    {
        if (!UserService.IsAuthenticated && !HttpContext.Current.Response.IsRequestBeingRedirected)
            HttpContext.Current.Response.Redirect(ViewUtil.Actions.User.LogOnUrl());
    }
}

As you can see the attribute will redirect a user if the user is not authenticated. However it appears that the redirect only happens after the action executes. This is causing problems because I made the assumption the user is authenticated when executing the action. First I need to understand if the attributes are supposed to happen before or after the action is executed, or am I thinking of the workflow completely wrong?

Thanks, Paul


After researching this some more it is clear that the filterContext.Result has to be set for this to work. After making a small change in my Authorize attribute, it is now working:

    public class Authenticate : CustomAuthorizeAttribute
{
    public override void OnAuthorization(AuthorizationContext filterContext)
    {
        if (!UserService.IsAuthenticated && !HttpContext.Current.Response.IsRequestBeingRedirected)
            filterContext.Result = new RedirectResult(ViewUtil.Actions.User.LogOnUrl());
    }
}


You're correct, Attributes execute before the action in question, so [Authenticate] should most certainly execute first and, if the user is not authenticated, the Action code never executes until after the user is redirected, authenticates and is redirected back to this action.

Edit based on comment: the MVC Framework OnAuthorizatrion method (source here) doesn't redirect, but sets the filterContext.Result to a `HttpUnauthorizedResult()' (which just sets a 401 status code). That result causes the authentication module to redirect the user to the login page. Assuming that the rest of your custom implementation is standard (not overriden or calling the base methods) changing this

HttpContext.Current.Response.Redirect(ViewUtil.Actions.User.LogOnUrl()); 

to this (or something similar, as long as you set the Result)

filterContext.Result = new HttpUnauthorizedResult();

should do the trick, at at least get your further down the road.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜