İçeriğe geç →

ASP.NET Core Serisi 01: Dapper ile RESTful API Tasarlama ve Azure App Services’e Deploy

Merhaba arkadaşlar.

ASP.NET Core serisine aslında uzun bir süredir giriş yapmayı düşünüyordum fakat, bir türlü fırsat bulamamıştım. 🙂 Son dönemlerde doğan bazı ihtiyaçlarımızdan dolayı (kolayca dockerize edebilmek vb.), bu aralar aktif olarak ASP.NET Core üzerinde development yapmaktayım. Bu sebep ile ara ara seriler halinde ASP.NET Core üzerine irili ufaklı makaleler yazmaya çalışacağım.

Bu makale kapsamında ASP.NET Core ile lightweight bir RESTful API geliştireceğiz. Bunun için data işlemlerinde Dapper ve Repository pattern’ını kullanıp, global exception’ları ise Serilog ile handle edeceğiz. Geliştirmenin ardından ise bir Swagger arayüzü ekleyip, Azure App Services üzerine nasıl deploy edebiliriz gibi işlemleri gerçekleştirmeye çalışacağız.

Proje Structure’ını Oluşturma

Öncelikle PowerShell üzerinden “aspnetcore-rest-api-with-dapper” isminde bir folder oluşturarak, aşağıdaki gibi “dotnet new webapi” komutu ile bir ASP.NET Core Web API projesi oluşturalım. Ardından “code .” komutu ile Visual Studio Code içerisinde projenin açılmasını sağlayalım.

Bu işlemin ardından template, aşağıdaki gibi Visual Studio Code içerisinde açılacaktır.

Artık kodlamaya yavaş yavaş başlayabiliriz.

Model Tanımlama

Bir e-ticaret sitesi geliştirdiğimizi düşünelim ve ürünlerimizi yönetecek bir RESTful API tasarlamak istiyoruz. Öncelikle proje içerisinde “Models” isminde bir folder oluşturalım ve içerisine “Product” class’ını aşağıdaki gibi tanımlayalım.

Sql create script’i ise:

Contract Tanımlama

Request ve Response objelerini tanımlayabilmek için “Contracts” isminde yeni bir folder daha oluşturalım. API üzerinden sisteme yeni bir product eklenmek isteneceği zaman kullanacak olacağımız “ProductRequest” objesini aşağıdaki gibi tanımlı olsun.

Bu işlemin ardından, API üzerinden dışarıya response olarak döneceğimiz “ProductResponse” objesini de aşağıdaki gibi tanımlayalım.

Buradaki “Message” property’sini istenilen product’ın bulunamadığı durumlarda, bulunamadı bilgisini response olarak dönebilmek için kullanacağız. Eğer “Message” property’sine herhangi bir bilgi set etmez isek, eklemiş olduğumuz “[JsonProperty]” attribute’ü ile serialize işlemleri sırasında bu property, ignore edilecektir.

Controller’ı Oluşturma

Gerekli olan common objeleri tanımlamamızın ardından, artık sırasıyla “Controller > Business > Data” şeklinde kodlamaya ve implemente etmeye başlayabiliriz. İlk olarak “Controllers” folder’ı içerisinde, “ProductsController” isminde yeni bir controller oluşturalım ve aşağıdaki gibi kodlayalım.

Constructor üzerinden “IProductBusiness” olarak bir interface inject ettik ve ardından “GetAsync“, “GetAllAsync” ve “AddAsync” method’larının implementasyonunu, sırasıyla gerçekleştirdik. Bu noktadan itibaren daha iyi bir sistem performansı elde edebilmek için, task-based olarak ilerleyeceğiz.

İleride versiyonlama işlemlerini yapabilmek için ise, URL path’i “api/v1/products” şeklinde tanımladık.

Business’ı Oluşturma

Controller’ı kodlarken “IProductBusiness” interface’ini kullanmıştık. Şimdi “Business” isminde bir folder oluşturarak, içerisinde aşağıdaki gibi “IProductBusiness” interface’ini tanımlayalım.

Buradaki Get method’larında response olarak, tanımladığımız “ProductResponse” class’ını kullanacağız. Şimdi “ProductBusiness” isminde bir class oluşturalım ve “IProductBusiness” interface’ini aşağıdaki gibi implemente edelim.

Bu noktada ise constructor üzerinden bir “IProductRepository” inject ediyoruz. Controller içerisinde olduğu gibi bu interface’in de “GetAsync“, “GetAllAsync” ve “AddAsync” method’larını yukarıdaki gibi implemente ediyoruz.

NOT: “GetAllAsync” method’unu implemente ederken, paging işlemini gerçekleştirmedik. Es geçmeyelim. 🙂

Data Kısmının Oluşturulması

Data işlemlerini gerçekleştirebilmek için burada, Repository pattern’ı ve Dapper‘ı kullanacağımızı belirtmiştik. Bunun için öncelikle aşağıdaki gibi Dapper’ı, projemize nuget üzerinden dahil edelim.

Dapper’ın projeye dahil edilmesinden sonra, “Data” isminde yeni bir folder oluşturalım ve içerisinde ilk olarak “IProductRepository” interface’ini aşağıdaki gibi tanımlayalım.

Burada sadece örneğimiz gereği bazı method’ları tanımlayacağız. Bunlar ise “IProductBusiness” içerisinde kullanmış olduğumuz “GetAsync“, “GetAllAsync” ve “AddAsync” method’ları olacak. Implemente edebilmek için “ProductRepository” isminde yeni bir class tanımlayalım ve aşağıdaki gibi kodlayalım.

Kodlama sırasında dikkat ederseniz eğer, Dapper’ın async method’larını kullanmaya çalıştık. Buraya kadar olan noktada, “Controller“, “Business” ve “Data” işlemlerini tamamladık.

Global Exception Handling with Serilog

Bu noktada exception handling konusunda bir kaç farklı alternatifimiz var. İster middleware‘i tercih edebiliriz, istersek de MVC exception filters attribute’ünü. Ben bu noktada, middleware’i kullanmayı tercih edeceğim. Çünkü general case’ler karşısında MVC exception filter’larının, yeterince flexible olmadığı söyleniyor.

Bunun için nuget üzerinden Serilog’un file logger’ını, projemize aşağıdaki gibi dahil edelim.

Implementasyon için “Middlewares” isminde yeni bir folder oluşturalım ve içerisinde aşağıdaki gibi “GlobalExceptionMiddleware” isminde bir class tanımlayalım.

Middleware içerisinden exception’ları, yukarıdaki gibi basit bir şekilde handle ettik. Şimdi tek yapmamız gereken şey “Startup.cs” içerisinden aşağıdaki gibi log file path’ini belirtmek ve middleware içerisine dahil etmek olacaktır.

Swagger Implementasyonu

API’ın consume işlemleri sırasında biz developer’lara çok fazla kolaylık sağlayan Swagger’ın implementasyon işlemini gerçekleştirebilmek için, öncelikle nuget üzerinden projemize aşağıdaki gibi dahil etmemiz gerekmektedir.

Şimdi ise “Startup.cs” içerisinden, Swagger’ı aşağıdaki gibi aktif hale getirelim.

Projeyi çalıştırdıktan sonra tek yapmamız gereken şey artık, “http://localhost:5000/swagger” URL’ı üzerinden erişmek olacaktır.

Application Service’lerin Inject Edilmesi

Hatırlarsak bölümün başında “IProductBusiness” ve “IProductRepository” interface’lerini, constructor’lar üzerinden inject ederek kullanmıştık. Resolve işlemlerinin gerçekleşebilmesi için “Startup.cs” içerisinden, application service’ler arasına ilgili type’ları tanımlamamız gerekmektedir.

Bunun için:

Artık projemiz tamamen hazır durumda.

Terminal üzerinden “dotnet build” yazarak kodu derleyelim ve ardından “dotnet run” komutu ile Kestrel vasıtasıyla projeyi çalıştırabiliriz.

Çalıştırdıktan sonra Swagger’a, “http://localhost:5000/swagger” URI’ı üzerinden erişebiliriz.

Azure App Services’e Deploy İşlemi

Bunun için öncelikle aşağıdaki adımları sırasıyla uygulamamız gerekmektedir.

  1. Azure portal üzerine login olalım.
  2. Sol üst menüden “New” kısmına tıklayalım.
  3. Açılan menüden aşağıdaki gibi “Web + Mobile > Web App” kısmını seçelim.
  4. Eğer subscription yoksa, açılacak ekran üzerinden “Sign up for a new subscription” kısmına gelerek, bir aylık deneme sürümünü elde edelim.
  5. Name” kısmına uygulamamızın adını unique olacak şekilde belirlememiz gerekmektedir. Ben burada aşağıdaki gibi “AspNetCoreRestfulApiSampleGokhanGokalp” olarak ayarlıyorum ve create butonuna basıyorum. (Bu işlem biraz vakit alacaktır.)
  6. Create butonuna bastıktan sonra deployment işlemi bittiğinde, “Deployments succeeded” şeklinde bir bildirim alacağız ve aşağıdaki gibi bir ekran görüyor olmalıyız.
  7. Şimdi sol menüde bulunan “Deployment options” kısmına girelim ve “Local Git Repository” kısmına tıklayalım.
  8. Daha sonra basic authentication işlemi için “Deployment user name” ve “Password” belirleyelim.
  9. Şimdi sol menüden “Settings > Properties” kısmına girelim ve orada yer alan “GIT URL” kısmını kopyalayalım.

Artık projeyi Azure App Service üzerine publish etmek için hazırız.

Öncelikle bunun için Visual Studio Code üzerinden bir local Git repository oluşturmamız gerekiyor.

Sol menüden “Source Control” menüsüne geldikten sonra, “Initialize git repository” kısmına tıklayalım ve ardından “Commit All” butonuna basalım.

Daha sonra aşağıdaki komutu terminal üzerinden çalıştıralım.

Şimdide credential bilgilerinin push işlemlerinde otomatik eklenebilmesi için, aşağıdaki komutu çalıştıralım.

Artık push işlemini gerçekleştirebiliriz. Bunun için aşağıdaki komutu kullanabiliriz:

Tüm işlemlerin bitiminin ardından ise, aşağıdaki gibi bir kaç satır görüyor olacağız.

İşte bu kadar. Azure App Services üzerinde host etmiş olduğumuz projeye artık, buradan erişim sağlayabilirsiniz: http://aspnetcorerestfulapisamplegokhangokalp.azurewebsites.net/swagger/

Umarım herkes için keyifli bir makale olmuştur. ASP.NET Core, gün geçtikçe dahada harika bir hal alarak ilerlemeye devam ediyor. Bir sonraki ASP.NET Core makale serisinde, görüşmek üzere.

https://github.com/GokGokalp/aspnetcore-rest-api-with-dapper

Bazı referanslar:

https://github.com/Microsoft/azure-docs/blob/master/articles/app-service-web/web-sites-create-web-app-using-vscode.md

https://docs.microsoft.com/en-us/aspnet/core/tutorials/web-api-help-pages-using-swagger

Bu makale toplam (9904) kez okunmuştur.

40
1



Kategori: ASP.NET Core Azure

11 Yorum

  1. ahmet ahmet

    Hocam şu ProdcutResponse oluşturulurken
    public ProductResponse()
    {
    Products = new List();
    }

    ve

    public List Products { get; set; }

    kısımlarında List’ler kızarıyor sebebi nedir?

    • Merhaba, kodları şekillendirmek için kullandığım plugin den kaynaklı sanırım type’lar gitmiş. 🙁 Farketmemiştim. Düzelteceğim, teşekkürler.

      “public List Products” şeklinde olacaktı.

  2. ahmet ahmet

    Hocam peki dapper referance nasıl ekleyeceğiz arama kısmına yazdığımda bulamadım

    • Merhaba, “dotnet add package Dapper” komutunu çalıştırıp, ardından “dotnet restore” yapmanız gerekmektedir.

  3. ahmet ahmet

    her şey iyi hoş lakin neyi neden yaptığımızı hiç anlamadım keşke yeni başlayanların da anlayabileceği bir dilden anlatsaydınız

    • Yazdığım bazı makaleler, genelde bu teknolojileri .NET Framework’de kullanan kitleye hitap etmektedir. Amacı ise başlığında olduğu gibidir aslında. Dapper kullanarak RESTful bir API tasarlama ve biraz da Azure App Servis’i göstermek. Yorumun için teşekkürler.

  4. ahmet ahmet

    Hocam merhaba,
    Since ‘ProductsController.Get()’ is an async method that returns ‘Task’, a return keyword must not be followed by an object expression. Did you intend to return ‘Task’? [aspnetcore-rest-api-with-dapper]
    şeklinde bir hata alıyorum çözümü nedir acaba?

  5. ahmet ahmet

    Hocam biraz çaba sarfettikten sonra daha da iyi oturdu her şey. Teşekkürler ekstradan verdiğiniz cevaplar için 🙂

  6. son son

    DI için Autofac imi tercih edersiniz yoksa .net core la gelen DI yımı.

    • Merhaba, genelde benim tercihim .NET Core içerisinde build-in olarak gelen DI’ı kullanmak. Bazı makalelerde ise autofac gibi library’lerin dependency load işlemlerinin bir tık daha hızlı olduğu söyleniyor, ama ne derecede ne farkeder bilemiyorum. 🙂

Bir cevap yazın

E-posta hesabınız yayımlanmayacak. Gerekli alanlar * ile işaretlenmişlerdir

*