2012-10-14 18 views
11

Aktualnie pracuję nad interfejsem Web API, korzystając z projektu MVC 4 web API. Obecnie jestem na etapie, w którym muszę dodać pewne zabezpieczenia do API. Znam atrybut Authorize, jednak klient wolałby inne podejście. W tym celu starałem się przesłonić atrybut Authorize w mojej własnej klasie i jako podstawowy start, po prostu mam AuthorizeCore zawsze zwracając wartość false, co powinno oznaczać, że nie jest uwierzytelniony. Jeśli dodam to do akcji w kontrolerze, akcja zawsze się zakończy i zawsze będę pobierać dane. Wierzę, że przyczyną może być niestandardowy atrybut nie jest zarejestrowany w pliku web.config, jednak nie jestem pewien, jak to zrobić, gdy nie korzystasz z uwierzytelniania formularzy.Używanie niestandardowej autoryzacji w MVC 4

Kod, którego używam do przetestowania, to nowy projekt API sieci MVC 4 z niestandardowym atrybutem pokazanym poniżej.

public class Auth : AuthorizeAttribute 
{ 
    protected override bool AuthorizeCore(HttpContextBase httpContext) 
    { 
     return false; 
    } 
    protected override void HandleUnauthorizedRequest(AuthorizationContext filterContext) 
    { 
     filterContext.Result = new RedirectResult("http://www.google.com"); 
    } 
} 

I dodaje atrybut na metody GET domyślnego ValuesController jako taki

[Auth] 
public IEnumerable<string> Get() 

Jednak, kiedy przejść do domeny/API/wartości Ja zawsze prezentowane z danymi zamiast oczekiwane przekierowanie do google. Każda pomoc jest doceniana.

Edycja: Po rozglądać trochę więcej Znalazłem to tutaj: http://weblogs.asp.net/jgalloway/archive/2012/05/04/asp-net-mvc-authentication-customizing-authentication-and-authorization-the-right-way.aspx Sugeruje to, że wybrałem źle źle klasę AuthorizeAttribute jak ja wybrał jedną z System.Web.MVC zamiast jednego z System.Web.Http . Wygląda na to, że wersja Http nie pozwala na taki sam poziom konfiguracji, jak wersja MVC, ponieważ nie pozwala mi to zastąpić AuthorizeCore. Dozwolona jest dalsza pomoc w tym zakresie.

+0

I nie sądzę, że nie ma nic wspólnego ze złym klasie AuthorizeAttribute. Umieść punkt przerwania na "return false;" instrukcja, uruchom w trybie debugowania i sprawdź, czy trafiłeś w to oświadczenie. – Turnkey

+0

Próbowałem tego, a punkt przerwania w ogóle nie został trafiony. Jest to zgodne z zachowaniem wymienionym w linku, że nic się nie dzieje, gdyby użyto niewłaściwego atrybutu. – bruinbrown

+0

Tak, wygląda na to, że różnica w zachowaniu w WebApi versus MVC. – Turnkey

Odpowiedz

9

Wygląda na to, że przyczyną problemu była niewłaściwa wersja AuthorizeAttribute. Po użyciu wersji znalezionej w System.Web.Http kod zwraca poprawny kod błędu, jeśli użytkownik nie ma wymaganych uprawnień. Jako przykład tutaj jest równoważny kod do tego, co umieścić w oryginalnym pytanie

using System; 
using System.Web.Http; 
using System.Net.Http; 

public class AuthAttribute : AuthorizeAttribute 
{ 
    public override void OnAuthorization(System.Web.Http.Controllers.HttpActionContext actionContext) 
    { 
     HandleUnauthorizedRequest(actionContext); 
    } 

    protected override void HandleUnauthorizedRequest(System.Web.Http.Controllers.HttpActionContext actionContext) 
    { 
     var response = actionContext.Request.CreateResponse(System.Net.HttpStatusCode.Redirect); 
     response.Headers.Add("Location", "http://www.google.com"); 
     actionContext.Response = response; 
    } 
} 
+0

W dalszej części recenzji zalecam, aby nie obsługiwać go z przekierowaniami, ale za pomocą standardowych nagłówków odpowiedzi, jak podano w mojej poprawionej odpowiedzi. Będzie to bardziej zgodne z oczekiwanym zachowaniem klientów korzystających z interfejsu API. Następnie klient może wykonać przekierowanie lub przedstawić odpowiedź użytkownikowi. – Turnkey

3

Dla WebApi możesz wymusić na nim zastąpienie poprawnej klasy AuthorizeAttribute przez określenie jej w override. Również nie ma sensu przekierowanie, to po prostu zwraca nieautoryzowaną odpowiedź sieciową, która jest właściwa dla API.

namespace WebApiTest 
{ 
    public class Auth : System.Web.Http.AuthorizeAttribute 
    { 
     protected override bool IsAuthorized(System.Web.Http.Controllers.HttpActionContext actionContext) 
     { 
      return false; 
     } 

    } 
} 
+0

Powinienem był wspomnieć, że właśnie ustawiłem to dla jakiegoś podstawowego testu obecnie, robię normalnie konwencję. – bruinbrown

Powiązane problemy