2013-10-29 18 views
12

Ich habe einen CustomApiAuthorizeAttribute:Benutzerdefinierte Api Autorisieren AllowAnonymous ignorieren

public class CustomApiAuthorizeAttribute : AuthorizeAttribute 
{ 
    public override void OnAuthorization(HttpActionContext actionContext) 
    { 
     if (actionContext == null) 
      throw new ArgumentNullException("actionContext"); 

     bool skipAuthorization = actionContext.ActionDescriptor.GetCustomAttributes<AllowAnonymousAttribute>().Any() || 
      actionContext.ActionDescriptor.ControllerDescriptor.GetCustomAttributes<AllowAnonymousAttribute>().Any(); 

     if (skipAuthorization) return; 

     var cookie = HttpContext.Current.Request.Cookies[FormsAuthentication.FormsCookieName]; 

     if (cookie != null) 
     { 
      var decCookie = FormsAuthentication.Decrypt(cookie.Value); 

      if (decCookie != null) 
      { 
       if (!string.IsNullOrEmpty(decCookie.UserData)) 
       { 
        HttpContext.Current.User = new CustomPrinciple(new CustomIdentity(decCookie)); 
        return; 
       } 
      } 
     } 

     HttpContext.Current.Items["RequestWasNotAuthorized"] = true; 

     HttpContext.Current.Response.Cookies.Add(new HttpCookie(FormsAuthentication.FormsCookieName) { Expires = DateTime.Now.AddDays(-1d) }); 

     HandleUnauthorizedRequest(actionContext); 
    } 
} 

Und ich habe einen Controller:

[CustomApiAuthorize] 
public class RacingController : CustomApiController 
{ 
    [HttpGet] 
    [AllowAnonymous] 
    public Venues Venues() 
    { 
     var asr = Services.GetVenues(Token); 
     if(!string.IsNullOrEmpty(Token)) 
      SetAuthTicket(asr.Token); 
     return asr.Payload; 
    } 
} 

ich einen 401 Unauthorized Fehler halte, wenn diese Aktion aufzurufen versuchen. Das Debuggen sagt mir, dass das authorize-Attribut das Vorhandensein von [AllowAnonymous] nicht erkennt, aber ich verstehe nicht warum.

Kann jemand sehen, was ich falsch mache? oder hast du eine Idee, wenn etwas anderes konflikthaft sein könnte?

+2

Es gibt zwei AllowAnonymous-Attribute, eins in System.Web.Mvc und eins in System.Web.Http - haben Sie überprüft, dass die beiden Referenzen in Ihrem Code identisch sind? – stames

Antwort

13

Wenn Sie in der Quelle des System.Web.Http.AuthorizeAttribute aussehen, gibt es die folgende Überprüfung, ob Autorisierung übersprungen werden soll:

public override void OnAuthorization(HttpActionContext actionContext) 
    { 
     if (actionContext == null) 
     { 
      throw Error.ArgumentNull("actionContext"); 
     } 

     if (SkipAuthorization(actionContext)) 
     { 
      return; 
     } 

     if (!IsAuthorized(actionContext)) 
     { 
      HandleUnauthorizedRequest(actionContext); 
     } 
    } 

     private static bool SkipAuthorization(HttpActionContext actionContext) 
    { 
     Contract.Assert(actionContext != null); 

     return actionContext.ActionDescriptor.GetCustomAttributes<AllowAnonymousAttribute>().Any() 
       || actionContext.ControllerContext.ControllerDescriptor.GetCustomAttributes<AllowAnonymousAttribute>().Any(); 
    } 

Also, was ich tat umzusetzen war in einer ähnlichen Kontrolle Meine benutzerdefinierten Autorisierungsattribute.

+1

Diese Problemumgehung funktioniert einwandfrei. Vielen Dank! – Ezequiel

Verwandte Themen