Merhaba,
Günümüz uygulamaları yapısal olarak kendi bünyelerinde bir bütün teşkil etselerde kullanıcılara daha farklı hitap şekilleriyle piyasada fark yaratmaya çalışmaktadırlar ve bu hitap şekilleri yer yer uygulama üzerinde belirli noktaları dünyaya açacak kadar ileri derece fikirlerle zenginleştirilmektedir. Bu konuya örnek olarak dünya devlerinden Google’ı verebiliriz. Google maps özelliğini sadece son kullanıcılara hizmet veren bir navigasyon uygulaması olarak tasarlamış olsaydı muhtemelen çoktan bu hizmette olan desteğini sonlandırmış olacaktı. Bilhassa kullanıcılarada kendi ihtiyaçları doğrultusunda maps uygulaması üzerinden geliştirmeler yapabilme olanağı tanıyarak ürünün detaylı gelişimini dünyaya bırakmış oldu. Benzer şekilde Facebook’u ele alırsak eğer, en basitinden Facebook ile Login uygulaması yapılmasına müsaade ederek, kitlelere hitap eden siteler üzerinde kendi varlığını hissetirirken biryandan da toplumsal bir nüfuz sağlamış oldu.
Peki bu dünya devlerine erişim nasıl sağlandı diye sorarsanız eğer arada sadece API diye nitelendirilen ve uygulama geliştiren firma/şahıs tarafından yapıya özel tasarlanmış ve belirli veri yahut işlemlere kontrollü bir şekilde erişim izni verilmiş yapılar ortaya kondu.
İnsanlar bu API denen yapılar aracılığıyla uygulama geliştiricisinin çizdiği sınırlarda o uygulamanın belli başlı nimetlerinden faydalanabilir oldu. İşte bu içeriğimizde Asp.NET MVC uygulamalarımızda istediğimiz nimetleri diğer insanlarla paylaşabileceğimiz API uygulamalarının nasıl oluşturulacağını teknik boyutta detaylıca ele alacağız.
İlk olarak API’yi tanımlayarak işe başlayalım.
API Nedir?
API, Türkçe manası “Uygulama Geliştirme Arayüzü” olan “Application Programming Interface” kelimelerinin baş harflerinden meydana gelen bir sözcüktür. API sayesinde yazılım geliştiricileri, ellerindeki verileri yahut işlevsellikleri istedikleri sınırlılıkta dış dünyayla paylaşabilmekte ve bu paylaşım sürecinde tüm kontrolleri ellerinde tutabilmektedirler.
Dolayısıyla bu paylaşım neticesinde farklı uygulamalar yahut platformlar herşeyden(dil, platform, alt yapı vs.) bağımsız bir şekilde verilerden yahut işlevselliklerden istifade edebilir.
Neden Web API Kullanmalıyız?
Son yıllarda internete erişim olanağı çok farklı platformlar tarafından sağlandığı için dolayısıyla kullanıcıların ihtiyaçlarını sadece web siteleri karşılayamaz olmuştur. Bu platformlar bilgisayarlarla birlikte tabletler ve özellikle biribirinden farklı yetenekler sergileyen mobil telefonlardır. Haliyle uygulama geliştiricileri platformdan bağımsız bir şekilde kullanıcılara ulaşabilmek için uygulamadan da bağımsız API geliştirmeye yönelmektedirler. Geliştirilen bu API’ler tüm platform ve uygulamaların okuyup, anlamlandırabileceği XML veya JSON gibi veri tiplerini kullanarak hizmet sunmakta ve bu şekilde tüm bağımlılıklardan kendilerini arındırarak geliştiricilerin amaçları doğrultusunda son kullanıcılara hizmet verebilmektedirler.
Asp.NET MVC İle Web API Nasıl Oluşturulur?
Şimdi geldik makalemizin esas konusuna. Asp.NET MVC ile Web API konusunu detaylıca ele alabilmek için öncelikle boş bir Web API projesini oluşturalım. Ardından makalemizde örneklendirme yapabilmemiz için North Wind veritabanını Entity Framework ile projeye entegre edelim.
Web API konusunda üç farklı duruma hakim olmamız gerekmektedir. Bu durumlar;
- Route yapılanması,
- GET – POST durumları
- ve yapılacak işe göre isimlendirme yöntemi.
İlk olarak Route yapılanmasını inceleyelim.
“App_Start” klasörü altındaki “WebApiConfig.cs” dosyasının içeriğine göz atarsak eğer;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.Http;
namespace WebApiApplication
{
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
// Web API configuration and services
// Web API routes
config.MapHttpAttributeRoutes();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{id}",
defaults: new { id = RouteParameter.Optional }
);
}
}
}
şeklinde bir route tasarımı mevcuttur. Öncelikle Web API’nin kullanacağı route şablonunu oluşturmamız gerekmektedir. Bizler bu örneğimizde; veri getirme, post etme ve bir yandan da güncelleme üzerine örneklendirme yapacağımızdan dolayı ona göre bir route tasarlayacağız.
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional }
);
Evet… Route şablonumuzu hazırlamış olduk. Şimdi sıra API’mizi oluşturmaya geldi.
Tabi bir yandan API’mizi oluştururken bir yandan da API sınıflarının detaylarından bahserek GET – POST durumlarını inceleyelim.
public class PersonelController : ApiController
{
}
Yukarıdaki kod bloğunu incelerseniz eğer “Personel(Controller).cs” isminde bir API oluşturmuş olduk. Bir sınıfın API olabilmesi için “ApiController” sınıfından türemesi gerektiğini anladığınızı düşünüyorum…
Velhasıl şimdi bu API ile uygulamanın dışına açmak istediğimiz nimetleri tasarlayacağımız metotları oluşturalım. Tabi burada dikkat edilmesi gereken nokta oluşturulacak ilgili metodun GET’mi POST’mu olduğudur.
public class PersonelController : ApiController
{
NorthwindEntities db = new NorthwindEntities();
public IEnumerable<Personeller> GetPersoneller() => db.Personeller.ToList();
}
Yukarıdaki metoda bakarsanız eğer bir GET metodudur. Nereden mi anlıyoruz? Bakınca görülüyor işte 🙂 Doğrusu bizim anlayıp anlamamız şu durum için çok önemli değil. Web API bunun bir GET metodu olduğunu nereden anlayacak? asıl soru bu! Bu sorunun iki cevabı vardır. Öncelikle compiler ilgili metodun ismine bakacaktır. GET ile mi POST ile mi başlıyor. Ona göre ilgili metodun GET ya da POST olduğunu anlıyor. Yani buarada “(Get)Personeller” metodu GET ile başladığı için API tarafından GET metodu olarak algılanmaktadır.
Eğer ki metot ismi GET ya da POST ile başlamıyorsa compiler ilgili metodun “HttpGet” ya da “HttpPost” attributelarından hangisiyle işaretlendiğine bakacaktır.
public class PersonelController : ApiController
{
NorthwindEntities db = new NorthwindEntities();
[HttpGet]
public IEnumerable<Personeller> TumPersonelleriGetir() => db.Personeller.ToList();
}
Yukarıdaki örnekte olduğu gibi…
Dolayısıyla API içerisindeki metotları isimlendirirken dikkat etmemiz gerektiğini anlamış olsa gerek.
Birazdan API metotlarımızı oluşturacağız. Lakin herşeyden önce bize engel teşkil edecek bir olası hata durumunu öncelikle değerlendirip konumuza devam etmek istiyorum.
API metotlarını route yapılanmasında olduğu gibi tetiklemekteyiz. Örneğin;
public class PersonelController : ApiController
{
NorthwindEntities db = new NorthwindEntities();
//GET Metodu
public IEnumerable<Personeller> GetPersoneller() => db.Personeller.ToList();
}
yukarıdaki “GetPersoneller” isimli metoda talep göndermek için aşağıdaki gibi linki tetiklememiz gerekmektedir.
localhost:*****/api/personel/GetPersoneller
Bu şekilde metoda talep gönderildiği vakit aşağıdaki gibi hatayla karşılaşılacaktır.
Bu hatanın sebebi, veritabanının ilgili tablosunun tüm özelliklerinin dışarıya açılmasından kaynaklanmaktadır. Bizler Web API’ler de lüzumsuz yere tüm tablo bilgilerimizin erişilebilir olmasını istemeyiz. Haliyle bunu API’de istememekte. İşte bu yüzden direkt olarak Entity Framework tarafından oluşturulan entity dışarıya açılmamaktadır. Yerine istediğimiz verileri sunacağımız bir entity oluşturarak kontrollü bir yapı sunmamız bu hatadan bizleri kurtaracaktır.
public class Personel
{
public int PersonelId { get; set; }
public string Adi { get; set; }
public string Soyadi { get; set; }
public string Unvan { get; set; }
}
Evet… Gördüğünüz üzere yukarıda oluşturmuş olduğum “Personel” sınıfı ile veritabanımdaki tablomun dışarı açacağım alanlarını temsil etmekteyim. Bu şekilde hem veritabanımdaki tablomun güvenliğini sağlamış bulunuyorum hem de dışarıya lüzumsuz alan çıkartarak oluşacak performans kaybını önlemiş oluyorum.
public class PersonelController : ApiController
{
NorthwindEntities db = new NorthwindEntities();
//GET Metodu
public IEnumerable<Personel> GetPersoneller() => db.Personeller.Select(p => new Personel
{
Adi = p.Adi,
Soyadi = p.SoyAdi,
PersonelId = p.PersonelID,
Unvan = p.Unvan
}).ToList();
}
Haliyle tüm metot yapımı oluşturduğum ve dış dünya ile temas kuracak entity tipinde şekillendiriyorum.
Görüldüğü üzere olası hatamıza nasıl çözüm bulacağımızı yerinde görmüş olduk.
Hazır yeri gelmişken önemli bir hususuda belirtmek istiyorum ki; response neticesinde gelen veriyi JSON olarak görmek isterseniz gelen XML datasını Clear etmeniz yeterli olacaktır. Bu işlemide
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
GlobalConfiguration.Configuration.Formatters.XmlFormatter.SupportedMediaTypes.Clear();
config.MapHttpAttributeRoutes();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional }
);
}
}
şeklinde “WebApiConfig.cs” dosyasına “GlobalConfiguration.Configuration.Formatters.XmlFormatter.SupportedMediaTypes.Clear();” komutunu ekleyerek gerçekleştirebilir ve bundan böyle gelecek tüm sonuçları JSON veri formatında elde edebiliriz.
Şimdi konumuza devam ederek gönül rahatlığıyla API metotlarımızı oluşturabiliriz.
public class PersonelController : ApiController
{
NorthwindEntities db = new NorthwindEntities();
//GET Metodu
public IEnumerable<Personel> GetPersoneller() => db.Personeller.Select(p => new Personel
{
Adi = p.Adi,
Soyadi = p.SoyAdi,
PersonelId = p.PersonelID,
Unvan = p.Unvan
}).ToList();
//GET Metodu
[HttpGet]
public Personel PersonelGetir(int id)
{
Personeller p1 = db.Personeller.FirstOrDefault(p => p.PersonelID == id);
return new Personel
{
Adi = p1.Adi,
Soyadi = p1.SoyAdi,
PersonelId = p1.PersonelID,
Unvan = p1.Unvan
};
}
//POST Metodu
public IHttpActionResult PostPersonel(Personel personel)
{
db.Personeller.Add(new Personeller
{
Adi = personel.Adi,
SoyAdi = personel.Soyadi,
Unvan = personel.Unvan
});
db.SaveChanges();
return Ok<string>("Personel kaydedildi...");
}
//PUT Metodu
public IHttpActionResult PutKategori(int id)
{
Kategoriler kategori = db.Kategoriler.FirstOrDefault(k => k.KategoriID == id);
kategori.KategoriAdi = " - Güncel";
db.SaveChanges();
return Ok<string>("Kategori güncellenmiştir...");
}
//PUT Metodu
[HttpPut]
public IHttpActionResult KategoriGuncelle(int id)
{
Kategoriler kategori = db.Kategoriler.FirstOrDefault(k => k.KategoriID == id);
kategori.KategoriAdi = " - Güncel";
db.SaveChanges();
return Ok<string>("Kategori güncellenmiştir...");
}
}
Gördüğünüz üzere Web API’mizi her cins metodu örneklendirecek şekilde oluşturmuş olduk. Şu ana kadar GET metotlarının link üzerinden basitçe tetiklendiğini gördük. Lakin POST metotlarının tetiklenme mekanizması biraz farklı olduğu için bu yazımızda ek bir uygulama kullanarak gerçekleştireceğiz.
Google amcaya gidip “PostMan” yazdığınız vakit karşınıza gelen uygulamayı indirip, yükleyiniz.
Ekran alıntısında olduğu üzere POST metotlarını görüldüğü gibi tetikleyebilmekte ve çalışıp çalışmadığını denetlemekteyiz.
Evet arkadaşlar… Asp.NET MVC’de Web API’lerin nasıl oluşturulduğunu görmüş olduk. Bu içeriğimizde yapmış olduğumuz tüm işlemleri güvenlik doğrulaması yapmaksızın gerçekleştirmiş olduk. Dolayısıyla bir başka yazımızda bu içeriğimizin devamı niteliğinde Token Authentication ile Web API üzerine istişare ediyor olacağız.
O halde sonraki yazımda görüşmek üzere diyelim…
İyi çalışmalar dilerim…
