ASP.NET Web API 'sinde kimlik doğrulama ve yetkilendirme

, Mike te son

Bir Web API 'SI oluşturdunuz, ancak şimdi ona erişimi denetlemek istiyorsunuz. Bu makale dizisinde, yetkisiz kullanıcılardan bir Web API 'sinin güvenliğini sağlamaya yönelik bazı seçeneklere bakacağız. Bu seri, hem kimlik doğrulamasını hem de yetkilendirmeyi kapsar.

  • Kimlik doğrulaması , kullanıcının kimliğini öğrenmektir. Örneğin, Gamze Kullanıcı adı ve parolasıyla oturum açar ve sunucu çiğdem kimlik doğrulaması için parolayı kullanır.
  • Yetkilendirme , bir kullanıcının bir eylem gerçekleştirmesine izin verilip verilmediği konusunda karar verebilir. Örneğin, Gamze 'nin bir kaynağı almak için izni vardır ancak kaynağı oluşturmamalıdır.

Serideki ilk makale, ASP.NET Web API 'sinde kimlik doğrulamaya ve yetkilendirmeye genel bir bakış sunar. Diğer konular, Web API 'SI için ortak kimlik doğrulama senaryolarını anlatmaktadır.

Note

Bu seriyi inceleyen ve değerli geri bildirimleri sağlayan kişiler için teşekkürler: Rick Anderson, Levi Broderick, Barry Dorrans, Tom Dykstra, Hongmei Ge, David Matson, Daniel Roth, Tim Teebken.

Kimlik Doğrulaması

Web API 'SI, kimlik doğrulamasının konakta gerçekleştiğini varsayar. Web barındırma için, ana bilgisayar IIS 'dir ve kimlik doğrulaması için HTTP modüllerini kullanır. Projenizi IIS veya ASP.NET 'te yerleşik olarak bulunan kimlik doğrulama modüllerinden birini kullanacak şekilde yapılandırabilir veya özel kimlik doğrulaması gerçekleştirmek için kendi HTTP modülünüzü yazabilirsiniz.

Ana bilgisayar kullanıcının kimliğini doğruladığında, kodun çalıştığı güvenlik bağlamını temsil eden bir IPrincipal nesnesi olan bir sorumluoluşturur. Ana bilgisayar, iş parçacığının. CurrentPrincipalöğesini ayarlayarak sorumluyu geçerli iş parçacığına iliştirir. Asıl öğe, kullanıcıyla ilgili bilgiler içeren ilişkili bir kimlik nesnesi içerir. Kullanıcının kimliği doğrulandıysa, Identity. IsAuthenticated özelliği truedeğerini döndürür. Anonim istekler için, IsAuthenticated , falsedöndürür. Sorumlular hakkında daha fazla bilgi için bkz. rol tabanlı güvenlik.

Kimlik doğrulaması için HTTP Ileti Işleyicileri

Kimlik doğrulaması için konağın kullanılması yerine, kimlik doğrulama mantığını bir http ileti işleyicisinekoyabilirsiniz. Bu durumda, ileti işleyicisi HTTP isteğini inceler ve sorumluyu ayarlar.

Kimlik doğrulaması için ileti işleyicilerini ne zaman kullanmalısınız? Aşağıda bazı dengeler verilmiştir:

  • HTTP modülü, ASP.NET ardışık düzeni üzerinden geçen tüm istekleri görür. İleti işleyicisi yalnızca Web API 'sine yönlendirilen istekleri görür.
  • Belirli bir rotaya bir kimlik doğrulama düzeni uygulamanıza olanak sağlayan yönlendirme başına ileti işleyicileri ayarlayabilirsiniz.
  • HTTP modülleri IIS 'e özeldir. İleti işleyicileri ana bilgisayar belirsiz olduğundan, hem Web barındırma hem de kendiliğinden barındırma ile kullanılabilir.
  • HTTP modülleri, IIS günlüğe kaydetme, denetleme vb. için de yer alır.
  • HTTP modülleri, ardışık düzende daha önce çalışır. Kimlik doğrulamasını bir ileti işleyicisinde işletin, bu, işleyici çalışana kadar küme almaz. Ayrıca, yanıt ileti işleyiciden ayrıldığında, sorumlu önceki sorumluya geri döner.

Genellikle, kendi kendine barındırmayı desteklemeniz gerekmiyorsa, HTTP modülü daha iyi bir seçenektir. Kendi kendine barındırmayı desteklemeniz gerekiyorsa bir ileti işleyicisini düşünün.

Sorumluyu ayarlama

Uygulamanız herhangi bir özel kimlik doğrulama mantığı gerçekleştirirse, sorumluyu iki yerde ayarlamanız gerekir:

  • Thread. CurrentPrincipal. Bu özellik, .NET 'teki iş parçacığının sorumlusunu ayarlamaya yönelik standart bir yoldur.
  • HttpContext. Current. User. Bu özellik ASP.NET 'e özgüdür.

Aşağıdaki kod, sorumlunun nasıl ayarlanacağını göstermektedir:

private void SetPrincipal(IPrincipal principal)
{
    Thread.CurrentPrincipal = principal;
    if (HttpContext.Current != null)
    {
        HttpContext.Current.User = principal;
    }
}

Web barındırma için, sorumluyu her iki yerde de ayarlamanız gerekir; Aksi takdirde güvenlik bağlamı tutarsız hale gelebilir. Ancak, kendi kendine barındırma için HttpContext. Current null. Kodunuzun konağın belirsiz olduğundan emin olmak için, gösterildiği gibi HttpContext. Currentöğesine atamadan önce null değerini denetleyin.

Yetkilendirme

Yetkilendirme, daha sonra işlem hattında denetleyiciye yaklaşarak gerçekleşir. Bu, kaynaklara erişim izni verdiğinizde daha ayrıntılı seçimler yapmanızı sağlar.

  • Yetkilendirme filtreleri , denetleyici eyleminden önce çalışır. İstek yetkilendirilmezse, filtre bir hata yanıtı döndürür ve eylem çağrılmaz.
  • Bir denetleyici eylemi içinde, Apicontroller. User özelliğinden geçerli sorumluyu alabilirsiniz. Örneğin, bir kaynak listesini Kullanıcı adına göre filtreleyerek yalnızca o kullanıcıya ait olan kaynakları geri alabilirsiniz.

[Yetkilendir] özniteliğini kullanma

Web API 'SI, AuthorizeAttributeyerleşik bir yetkilendirme filtresi sağlar. Bu filtre, kullanıcının kimliğinin doğrulandığını denetler. Aksi takdirde, eylemi çağırmadan HTTP durum kodu 401 (yetkilendirilmemiş) döndürür.

Filtreyi denetleyici düzeyinde küresel olarak veya tek tek eylemler düzeyinde uygulayabilirsiniz.

Küresel: her Web API denetleyicisine erişimi kısıtlamak için, genel filtre listesine AuthorizeAttribute filtresini ekleyin:

public static void Register(HttpConfiguration config)
{
    config.Filters.Add(new AuthorizeAttribute());
}

Denetleyici: belirli bir denetleyicinin erişimini kısıtlamak için, filtreyi denetleyiciye bir öznitelik olarak ekleyin:

// Require authorization for all actions on the controller.
[Authorize]
public class ValuesController : ApiController
{
    public HttpResponseMessage Get(int id) { ... }
    public HttpResponseMessage Post() { ... }
}

Eylem: belirli eylemlerin erişimini kısıtlamak için, eylem yöntemine özniteliği ekleyin:

public class ValuesController : ApiController
{
    public HttpResponseMessage Get() { ... }

    // Require authorization for a specific action.
    [Authorize]
    public HttpResponseMessage Post() { ... }
}

Alternatif olarak, denetleyiciyi kısıtlayabilir ve ardından özniteliği kullanarak belirli eylemlere anonim erişime izin verebilirsiniz [AllowAnonymous] . Aşağıdaki örnekte, Post yöntemi kısıtlıdır, ancak Get Yöntem anonim erişime izin verir.

[Authorize]
public class ValuesController : ApiController
{
    [AllowAnonymous]
    public HttpResponseMessage Get() { ... }

    public HttpResponseMessage Post() { ... }
}

Önceki örneklerde, filtre tüm kimliği doğrulanmış kullanıcıların kısıtlı yöntemlere erişmesine izin verir; yalnızca anonim kullanıcılar tutulur. Ayrıca, erişimi belirli kullanıcılara veya belirli rollerdeki kullanıcılara sınırlayabilirsiniz:

// Restrict by user:
[Authorize(Users="Alice,Bob")]
public class ValuesController : ApiController
{
}
   
// Restrict by role:
[Authorize(Roles="Administrators")]
public class ValuesController : ApiController
{
}

Note

Web API denetleyicileri için AuthorizeAttribute filtresi System. Web. http ad alanında bulunur. System. Web. Mvc ad alanında, Web API denetleyicileriyle uyumlu olmayan MVC denetleyicileri için benzer bir filtre vardır.

Özel Yetkilendirme filtreleri

Özel bir yetkilendirme filtresi yazmak için, bu türlerden birini türetebilirsiniz:

  • AuthorizeAttribute. Geçerli kullanıcıya ve kullanıcının rollerine göre yetkilendirme mantığını gerçekleştirmek için bu sınıfı genişletin.
  • Authorizationfilterattribute. Geçerli Kullanıcı veya role dayalı olması gereken zaman uyumlu yetkilendirme mantığını gerçekleştirmek için bu sınıfı genişletin.
  • IAuthorizationFilter. Zaman uyumsuz yetkilendirme mantığını gerçekleştirmek için bu arabirimi uygulayın; Örneğin, yetkilendirme mantığınızın zaman uyumsuz g/ç veya ağ çağrıları yapıyorsa. (Yetkilendirme mantığınızın CPU ile sınırlı olması durumunda, bir zaman uyumsuz yöntem yazmanıza gerek olmadığından Authorizationfilterattribute'tan türemek daha basittir.)

Aşağıdaki diyagramda AuthorizeAttribute sınıfının sınıf hiyerarşisi gösterilmektedir.

Denetleyici eylemi Içinde yetkilendirme

Bazı durumlarda, bir isteğin devam etmesini sağlayabilir, ancak durumu sorumlu temelinde değiştirebilirsiniz. Örneğin, döndürülen bilgiler kullanıcının rolüne bağlı olarak değişebilir. Bir denetleyici yöntemi içinde, Apicontroller. User özelliğinden geçerli sorumluyu alabilirsiniz.

public HttpResponseMessage Get()
{
    if (User.IsInRole("Administrators"))
    {
        // ...
    }
}