Derinlemesine yazılım eğitimleri için kanalımı takip edebilirsiniz...

Asp.NET Core Identity – Identity Altyapısı Kurulumu – II

Merhaba,

Bir önceki Asp.NET Core Identity – Nedir ve Temel Kavramlar? – I başlıklı içeriğimizde Asp.NET Core Identity kütüphanesine dair teorik olarak bir giriş yapmıştık. Bu içeriğimizde ise bir Asp.NET Core uygulamasında Identity alt yapısının nasıl kurulduğunu inceleyeceğiz.

Herşeyden önce Asp.NET Core Identity kütüphanesini bir projeye entegre ederken olayı hem kütüphane hem de veritabanı açısından değerlendirmemiz gerekmektedir. Kütüphane açısından Microsoft.AspNetCore.Identity kütüphanesinin projeye yüklenmiş olması gerektiğini ve Asp.NET Core uygulamalarında ilgili kütüphanenin dahili olarak geldiğini bu yüzden ekstradan işlem yapmamıza gerek kalmadığını yukarıda adresini verdiğimiz önceki makalemizde belirtmiştik.

Veritabanı açısından ise Asp.NET Core Identity kütüphanesi projeye entegre edeceği üyelik sistemiyle alakadar bir veritabanı düzeni getirmektedir. Üye bilgilerini, rolleri, tanımlamaları, token değerlerini, gerekli cross table görevi üstlenen ara tabloları vs. tüm değerleri tutacağı bir yapılanma beklemektedir. Dolayısıyla bu veritabanı karşılığını manuel bir şekilde oluşturmamız mümkün olsa dahi, fıtrat olarak Asp.NET Core Identity yapılanması en güncel ve dinamik veritabanı yaklaşımı olan Code First ile tam bir uyumluluk sergilemekte ve birazdan içeriğimizde ele alacağımız inşa neticesinde yapılan ve modellenen Identity çalışması neticesinde veritabanına uygun tabloları migrate edecek ve bizi manuel yapılanmanın getireceği olası hatalardan net bir şekilde arındırmış olacaktır.

Asp.NET Core Identity, ORM sistemi olan Entity Framework kütüphanesinin Code First yaklaşımıyla %100 uyumlu bir mimaridir.

Proje Alt Yapısı

İlk olarak “Empty” olacak şekilde bir Asp.NET Core uygulaması başlatılarak “Startup.cs” sınıfında aşağıdaki geliştirmeler yapılmalıdır.

    public class Startup
    {
        public IConfiguration Configuration { get; set; }
        public Startup(IConfiguration configuration) => Configuration = configuration;
        public void ConfigureServices(IServiceCollection services)
        {
            services.AddMvc();
        }

        public void Configure(IApplicationBuilder app, IHostingEnvironment env)
        {
            if (env.IsDevelopment())
                app.UseDeveloperExceptionPage();

            app.UseStatusCodePages();
            app.UseStaticFiles();
            app.UseMvc(_ => _.MapRoute("Default", "{controller=Home}/{action=Index}/{id?}"));
        }
    }

Şuanda “Startup.cs” sınıfımız olması gereken en sade şekliyle ayarlanmıştır. Birazdan Identity yapılanması inşa edilecek ve gerekli authenticaion yapılanması tekrar bu sınıf üzerinden modifiye edilecektir.

En Temel Identity Sınıfları

Asp.NET Core Identity kütüphanesinde en temel aktörlerimiz “IdentityUser” ve “IdentityRole” sınıflarıdır. En nihayetinde üyelik sistemi olan Identity mimarisi, bir kullanıcıyı genel geçer modelleyen ve o kullanıcıya dair rolleri tanımlayan bu iki sınıf ile bizlere eşlik edecektir.

IdentityUser IdentityRole
Sistem üzerinde kullanıcıları temsil eden sınıftır.
Asp.NET Core Identity – Alt Yapı Kurulumu - II
Yukarıdaki ekran alıntısında görüldüğü üzere içerisinde UserName, Email vs. gibi bir kullanıcıya dair genel geçer bilgileri barındırmaktadır.
Peki nasıl kullanılır?
Uygulamamızdaki kullanıcıları temsil edecek ve biryandan da modelleyecek olan “AppUser”(istediğiniz ismi verebilirsiniz) ismini verdiğimiz bir sınıf tasarlayacağız. İşte bu sınıf IdentityUser sınıfından türetilecektir. Yazımızın ileriki satırlarında ele alacağımız bu operasyon neticesinde “AppUser” sınıfı IdentityUser sınıfından gerekli propertyleri kalıtım aracılığıyla miras edinecektir. Neticede aldığı kalıtım ile tasarlanmış olan “AppUser” sınıfını Code First ile migrate ettiğimizde mirastan gelen ilgili propertyler kolon olarak oluşturulacaktır. Bu hazır propertyler dışında ihtiyacımıza dönük tüm custom propertyleri “AppUser” sınıfına oluşturarak migrate neticesindeki veritabanına eklenebilecektir.
Kullanıcının rollerini tanımlayan sınıftır. Bir rolle ilişkili tüm verileri barındırmaktadır.
Peki nasıl kullanılır?
İhtiyaç doğrultusunda “AppUserRole”(istediğiniz ismi verebilirsiniz) isminde bir sınıf oluşturacağız. Bu sınıfın IdentityRole sınıfında türetilmesi yeterlidir. Eğer ki özel kolonlara ihtiyacımız olursa, “AppUserRole” sınıfına eklenen propertyler sayesinde o kolonlar oluşturulmuş olacak ve migrate neticesinde veritabanına yansıtılacaktır.

Temel sınıflarımızıda tanıdıktan sonra şimdi sıra Identity mimarisini uygulamada ayağa kaldırmaya geldi…

Adım 1

Projede “Models” isimli klasör oluşturalım ve içerisine “Authentication” isminde bir klasör daha oluşturalım. Bundan sonraki tüm yapılanmalar en son oluşturulan bu “Authentication” isimli klasör içerisinde gerçekleştirilecektir.

Şimdi ilk olarak kullanıcılarımızı temsil edecek olan sınıfımızı tasarlayalım. Bu sınıfımızın adı istediğiniz herhangi bir değerde olabilir. Ben burada örnek amaçlı “AppUser” ismini veriyorum.

    public class AppUser : IdentityUser
    {
    }

Görüldüğü üzere “AppUser” sınıfı oluşturulmuş ve hemen akabinde “IdentityUser” sınıfında türetilmiştir. Böylece bu sınıf uygulamada tüm kullanıcılarımıza model olabilecektir. Şimdilik bu sınıfa herhangi bir custom property girmiyorum. İlerleyen makalelerde custom property girildiği taktirde nasıl bir fark yarattığına dair mukayesede bulunacağız…

Adım 2

Bu içeriğimizdeki esas gayemiz basit bir Identity mekanizmasını ayağa kaldırabilmektir. Bundan dolayı kullanıcıları temsil eden bir sınıfın olması bizim için yeterlidir lakin yukarıda bahsedilen IdentityRole sınıfından türeyen ve sistemdeki rolleri tanımlayan bir sınıf inşa etmemize şimdilik gerek yoktur. Merak etmeyin, ilerleyen makalelerde a’dan z’ye herşeyi, en doğru şekilde incelemiş olacaksınız 🙂

Artık bu noktaya kadar elimizde kullanıcıları modelleyen bir “AppUser” sınıfı mevcuttur. Dolayısıyla şimdi yapmamız gereken Code First yaklaşımıyla üretilecek/migrate edilecek olan veritabanımızın bir karşılığı olan DbContext sınıfını üretmektir. Bunun için “Models” klasörü altında “Context” isimli bir klasör oluşturalım ve içerisinde “AppDbContext” isminde bir sınıf üretelim.

    public class AppDbContext : IdentityDbContext<AppUser>
    {
        public AppDbContext(DbContextOptions<AppDbContext> dbContext) : base(dbContext) { }
    }

Yukarıdaki kod bloğunu incelerseniz eğer oluşturulan context sınıfı normalde “DbContext” sınıfından türetilmesi gerekiyordu. Lakin biz sistemimizde Identity kullandığımızdan dolayı bu identity yapısının karşılığını veritabanında oluşturtmamız gerekmektedir ve bunu “IdentityDbContext” sınıfı ile gerçekleştirebilmekteyiz. Dolayısıyla context sınıfının hangi identity ile birlikte çalışacağını belirtebilmek için “IdentityDbContext” sınıfından türetilmektedir. Ve dikkat edilirse generic olarak bu identity yapılanmasının tarafımızca oluşturulan “AppUser” isimli sınıf ile gerçekleştirildiğini belirtmiş oluyoruz.

Context sınıfını inşa ettikten sonra migrate işlemi neticesinde hedef sunucu providerını “appsettings.json” dosyasında aşağıdaki şekilde belirleyelim;

{
  "ConnectionStrings": {
    "SqlServerConnectionString": "Server=.;Database=IdentityExampleDb;Trusted_Connection=True;"
  },
  "Logging": {
    "LogLevel": {
      "Default": "Warning"
    }
  },
  "AllowedHosts": "*"
}

Adım 3

Artık uygulamada inşa edilen bu identity yapılanması “Startup.cs” sınıfı üzerinden uygulamaya dahil edilmelidir. Bunun için aşağıdaki çalışma yeterlidir…

    public class Startup
    {
        public IConfiguration Configuration { get; set; }
        public Startup(IConfiguration configuration) => Configuration = configuration;
        public void ConfigureServices(IServiceCollection services)
        {
            services.AddDbContext<AppDbContext>(_ => _.UseSqlServer(Configuration["ConnectionStrings:SqlServerConnectionString"]));
            services.AddIdentity<AppUser, IdentityRole>().AddEntityFrameworkStores<AppDbContext>();
            services.AddMvc();
        }

        public void Configure(IApplicationBuilder app, IHostingEnvironment env)
        {
            if (env.IsDevelopment())
                app.UseDeveloperExceptionPage();

            app.UseStatusCodePages();
            app.UseStaticFiles();
            app.UseAuthentication();
            app.UseMvc(_ => _.MapRoute("Default", "{controller=Home}/{action=Index}/{id?}"));
        }
    }

7. satır‘da görüldüğü üzere uygulamaya geliştirdiğimiz context nesnesi DbContext olarak tanıtılmaktadır.

8. satır‘da görüldüğü üzere ise uygulamaya identity yapılanmasına dair gerekli entegrasyonu “AddIdentity” metodu ile gerçekleştirmekteyiz. Dikkat ederseniz generic olarak birinci parametreye bu identity yapılanmasının kullanacağı IdentityUser yapılanmasını istemektedir. Bunun için tarafımızdan “AppUser” sınıfı verilmiştir. Lakin ikinci parametreye ise tarafımızca herhangi bir IdentityRole sınıfından türeyen sınıf inşa edilmediğinden dolayı direkt olarak “IdentityRole” sınıfı verilmiştir. Yani anlayacağınız temelde biz sadece IdentityUser sınıfından türeyen “AppUser” sınıfını inşa ederek en temel üyelik yönetimi yapılanmasını gerçekleştirmiş bulunmaktayız. Buradaki işlem neticesinde “AddEntityFrameworkStores” generic metodu sayesinde “AppDbContext” isminde oluşturduğumuz contexte özel depolama gerçekleştirmiş bulunmaktayız.

Ayrıca 19. satır‘da “UseAuthentication” metodu sayesinde uygulamanın identity ile kimlik doğrulaması gerçekleştireceğini belirtmiş bulunmaktayız.

Evet…

Bu işlemler neticesinde artık uygulamamızda bir Identity altyapısı mevcut hale getirilmiştir. Şimdi Code First yaklaşımı ile migrationları oluşturup veritabanımızı sunucuya migrate edelim. Asp.NET Core uygulamalarında migration işlemlerini tam teferruatlı inceleyebilmek için Asp.NET Core 2 MVC’de Migrations İle Veritabanı İşlemleri başlıklı makaleye göz atabilirsiniz.

dotnet ef migrations add mig_1
dotnet ef database update

Asp.NET Core Identity – Alt Yapı Kurulumu - II
Bu işlem neticesinde migrate edilen veritabanı ve oluşturulan tabloları aşağıdaki görselde olduğu gibidir;
Asp.NET Core Identity – Alt Yapı Kurulumu - II

Netice olarak; bu içeriğimizde sadece üyeleri temsil edecek olan sınıfı inşa ederek IdentityDbContext nesnesi oluşturmayı, Startup sınıfına Identity mimarisini entegre ederek projeye tüm bu yapılanmayla ayağa kaldırmayı incelemiş olduk. Yani uzun lafın kısası bir projede en sade haliyle Identity mimarisinin nasıl kurulduğunu görmüş olduk.

Sonraki makalemizde ise neticede oluşturulan veritabanında Identity mimarisine özel tabloları inceleyeceğiz. O halde şimdilik görüşmek üzere…

İlgilenenlerin faydalanması dileğiyle…
İyi çalışmalar…

Not : Örnek projeyi indirmek için buraya tıklayınız.

Bunlar da hoşunuza gidebilir...

28 Cevaplar

  1. Ali dedi ki:

    Merhaba hocam makaleniz için çok teşekkür ederim bu konuyla ilgili bir soru soracaktım Asp .net Core Identity mimarisini bir tek MVC de mi kullanabiliyoruz ? Web Api ile bu mimariyi kullanabiliyor muyuz? Kullanabiliyorsak aynı yapılandırmalar Web Api içinde geçerli mi?

  2. Fisun dedi ki:

    Uygulamayı Asp.Net Core 3.1 ile oluşturabilmek için ne yapmamız gerekiyor.

    • Gençay dedi ki:

      Uygulamayı 3.1 ile oluşturabilmek için Visual Studio’da .NET Core 3.1 seçili bir web uygulaması oluşturmanız gerekiyor.

      • Fisun dedi ki:

        Evet öyle yaptım ama siz projenizde AspNetCore.App 2.2.0 paketini kullanmışsınız. Bu paket Net Core 3.1 de oluşturduğum projeye eklediğimde paket üzerinde sarı üçgen bir uyarı oluşuyor ve AppDBContext de IdentityDbContext context inden inherit edemiyorum. Ama projeyi .Net Core 2.2 ye dönüştürdüğümde hiç sıkıntısız çalışıyor. Acaba başka bir kütüphanemi kullanmam lazım.

  3. Kutlu GÜNGÖR dedi ki:

    Merhaba, yukarıda Fisun Hanım’da size sormuş fakat aynı sorunu bende yaşıyorum. Core 3.1 ‘ de sizin bahsettiğiniz adımları takip ettiğim zaman AppContex’te DbContext option’a AppContext’i verdiğimde entityframeworkcore için context tipi uyumlu değil hatası alıyorum.

    • Gençay dedi ki:

      Muhtemelen ya uygulamaniz 3.1 değil ya da kullandığınız Entity Framework Core kütüphaneniz. Nuget’ten ilgili kütüphaneyi kontrol edebilir misiniz?

      • Gökhan dedi ki:

        Nuget paket olarak aşağıdakini yüklerseniz sorun çözümleniyor.
        Microsoft.AspNetCore.Identity.EntityFrameworkCore

  4. Murat dedi ki:

    Elinize sağlık şöyle bir not düşmek istiyorum.
    .net core 3.0 ve sonraki sürümlerde startup dosyasına

    app.UseAuthentication();

    app.UseAuthorization();

    bu sıra ile yazmak gerekiyor

  5. murat dedi ki:

    Şöyle bir sorum vardı hocam. Giriş yapan kullanıcının yetkisi bulunduğu sayfalarda giriş bilgilerinin veri tabanı sorgusu yapılarak o kullanıcıya ait bilgileri nasıl kullanabiliriz?

    • Gençay dedi ki:

      Direkt olarak ‘User’ property’si size kullanıcıya dair bilgileri getirecektir. O bilgiler üzerinden ‘UserManager’ ile aşağıdaki sorgulamayı yapabilirsiniz.

                  AppUser appUser = await _userManager.FindByNameAsync(User.Identity.Name);
      

      Serimizin ileriki makalelerinde ilgili konuya değinildiğini ve detaylı bir şekilde sindirerek okumanızı öneririm.

      Kolay gelsin…

  6. Busra dedi ki:

    Merhaba bi sorum olacaktı umarım en kısa sürede görürsünüz.
    Uygulamada iki tip kullanıcı olacaktır. (Yönetici, Kullanıcı) Yönetici tanımı manuel oluşturulabilir, ancak uygulama girişi tek olacaktır.

    Kullanıcı kayıt işlemi.(Register) (e-posta, şifre, ad soyad ve cep telefonu – validasyonlar yapılacaktır)

    Yönetici ve Kullanıcı için giriş işlemi. (Login)

    Uygulama menüsü yönetici için ve kullanıcı için farklılık gösterecektir.
    bu işlemler için nasıl bi yol izlemem gerekiyor. Identity ve rol yetkilendrme mi kullanacagım?

    • Gençay dedi ki:

      Evet, identity mimarisini kullanabilir, rol tabanlı yetkilendirme yapabilirsiniz.

      • Busra dedi ki:

        Öncelikle cevabınız için çok teşekkür ederim. Peki nasıl başlamam gerekiyor bu işleme. Ben yöneticiyi manuel oluşturmayıp kayıt işlemi yapayım diyorum. Yani hem kullanıcı için hem de yönetici icin hem login hem de kayıt yaptırıcam fakat rol kısmını burda nasıl kulanıcam?
        Yada sizce nasıl bi yol izlemeliyim?

        • Gençay dedi ki:

          Bu yazı serisinde, bu işin nasıl yapıldığını detaylıca anlatmaya çalıştığım. Dolayısıyla size bu seriyi uygulayarak okumanızı tavsiye ediyorum.

  7. Burak dedi ki:

    Emeğinize sağlık. Çok teşekkürler.

  8. Şahin dedi ki:

    Öncelikle bu serideki makalelerinizin tamamını okudum. Hepsi de çok özenle hazırlanmış, çok teşekkür ederim.
    Ancak sizlere bir sorum olacak. Şu an bir MVC projesi hazırlamaya başladım. Projedeki veritabanım AppDb adında ve AppDbContext nesnesini kullanıyor. IdentityDbContext nesnesiyle oluşturacağım kullanıcılar için de aynı veritabanını kullanabilir miyim? Yoksa farklı bir veritabanı mı oluşturmam gerekiyor.
    Bir de uygulamayı ve kullanıcıları aynı veritabanında tutmak mı daha verimli ve kullanışlı olur, farklı veritabanlarında tutmak mı?
    İlginiz için şimdiden teşekkür ederim.

    • Gençay dedi ki:

      Merhaba,

      1. Aynı veritabanını kullanabilirsiniz.
      2. Bu konuya dair yorum yapabilmek için projenin kapsamı doğrultusunda değerlendirme yapılması daha doğru olacaktır.
      Sevgilerimle…

  9. Baran dedi ki:

    Merhaba, makale çok güzel elinize sağlık. Sormak istediğim soru şu;
    Biz yazdığınız gibi entitylerimiz için DbContext sınıfı türetiyoruz ve bütün entitylerimizi oraya belirtiyoruz. Burada ise IdentityDbContext tanımlıyoruz. Bunları birleştirme şansımız var mı? Doğrusu nasıldır.
    Yoksa User roller vs. için IdentityDbContext ayrı mı tutulmalıdır bu mu doğrusudur?
    Tam sorabildim mi bilmiyorum ama umarım anlatabildim.
    Teşekkürler

    • Onurcan Oğul dedi ki:

      IdentityDbContext zaten DbContext i miras alan bir class. Bu yüzden DbContext de yapacağın işlemleri IdentityDbContextde yapabilirsin.

  10. FARUK dedi ki:

    Canım hocam, bal hocam, vaktiniz olursa bu makaleleri EntityFramework 7.0 için de günceller misiniz

    Teşekkürler bal hocam, can hocam.

  11. Erkan dedi ki:

    Makale için teşekkürler. Emeğine sağlık

  1. 10 Ağustos 2019

    […] Asp.NET Core Identity – Identity Alt Yapısı Kurulumu – II […]

  2. 11 Ağustos 2019

    […] önceki Asp.NET Core Identity – Identity Altyapısı Kurulumu – II başlıklı makalede Asp.NET Core uygulamalarında Identity altyapısının nasıl kurulduğunu […]

  3. 14 Temmuz 2020

Ali için bir yanıt yazın Yanıtı iptal et

E-posta adresiniz yayınlanmayacak. Gerekli alanlar * ile işaretlenmişlerdir