Dependency Injection, Object Oriented Programing kodlama yapmak için class, interface, constructor, property, access modifiers, generic type v.b. bunun gibi birçok kavramı okunabilir, geliştirilebilir, tekrar kullanılabilir, güvenli ve performanslı çalışan uygulamalar yapmak için kullanıyoruz. Bu makalede bunlardan biri olan Dependency Injection nedir ve neden kullanmalıyız konularını örnekler ile işleyeceğiz.
Dependency Injection(DI) Nedir? Neden Kullanırız?
Makale Devamında Kullanılacak Kısatmalar | |
Kısaltma | Açılımı |
DI | Dependency Injection |
OOP | Object Oriented Programing |
OOP kodlama yaparken girişte bahsettiğim 5-10 tane terim kullanmıyoruz bu yazdıklarım üzerine onlarca yeni terim daha eklenebilir ama biz bu makalemizde DI’i ele alacağız. DI’yı 3 farklı şekilde kullanabiliyoruz. Bu kullanım alanları ise şöyle;
- Constructor Injection
- Method Injection
- Property Injection
Bu 3 kullanımıda örnekler ile ele alacağız ama örnekleri ele almadan önce başlıktaki Nedir ve Neden sorularına cevap verelim.
Nedir ve Neden sorularına birden cevap vereceğim: bağımlıkları en aza indirmek ve bu bağımlıkları yönetmek konusunu daha sağlıklı hale getirmek için DI kullanacağız. Açıklamanın bu şekilde pek anlaşılır olmadığı yazarkende fark ettim ama örnekler üzerinden çok daha anlaşılır olacağını düşünüyorum.
Şimdi 3 farklı kullanım türü olduğunu söylemiştir bunlara sırasıyla örnek verelim ama örneğimizin kurgusunu öncelikle anlatalım örneğimiz Araba üzerine olacak bildiğiniz gibi araçların özellikleri standart olabiliyor. Bunlar Teker sayısı, renk, model, marka gibi özellikler aynı ama değerleri farklı olabiliyor bildiğiniz gibi. Şimdi biz olayı çok fazla karmaşık hale getirmeden bu saydığım özellikler üzerinden gideceğiz.
Uygulamayı kodlamaya geçmeden önce bu örnekte Console Application projesini ve .NET Framework 4.5.2 sürümü kullanacağımı belirtmek istiyorum böylelik yazacağınız bazı kısımların neden bende hata verdi gibi durumların önüne geçmek adına.
IAraba adında bir interface oluşturuyoruz ve bu interface içeriğini şu şekilde dolduruyoruz.
1 2 3 4 5 6 7 | interface IAraba { byte TekerSayisi { get; set; } Color Renk { get; set; } string Model { get; set; } string Marka { get; set; } } |
Şimdi bu IAraba arayüzünden türetilmiş 2 araç markası sınıfı oluşturacağız oluşturduğumuz 2 araç markası sınıfları şu şekilde.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 | class Renault : IAraba { public Renault(string marka, string model, Color renk, byte tekerSayisi) { Marka = marka; Model = model; Renk = renk; TekerSayisi = tekerSayisi; } public string Marka { get; set; } public string Model { get; set; } public Color Renk { get; set; } public byte TekerSayisi { get; set; } } class Fiat : IAraba { public Fiat(string marka, string model, Color renk, byte tekerSayisi) { Marka = marka; Model = model; Renk = renk; TekerSayisi = tekerSayisi; } public string Marka { get; set; } public string Model { get; set; } public Color Renk { get; set; } public byte TekerSayisi { get; set; } } |
Gördüğünüz gibi IAraba arayüzünden türetilmiş 2 farklı Renault ve Fiat araç sınıfı olduğunu görüyoruz.
Constructor Injection
Şimdi DI’i anlayacağımız kısma geçiyoruz ilk önce kodu yazıp sonra yorumlayalım. AracYonetimi adında bir sınıf oluşturuyoruz ve bu sınıfın constructor’indan IAraba arayüzünden türetilmiş sınıfı inject ediyoruz.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | class AracYonetimi { readonly IAraba _araba; public AracYonetimi(IAraba araba) { _araba = araba; } public void RenkDegistir(Color renk) => _araba.Renk = renk; public void ModelDegistir(string model) => _araba.Model = model; public void TekerSayisiDegistir(byte tekerSayisi) => _araba.TekerSayisi = tekerSayisi; public string TumOzellikler() { var arry = new string[4]; arry[0] = $"{nameof(_araba.TekerSayisi)}:{_araba.TekerSayisi}"; arry[1] = $"{nameof(_araba.Renk)}:{_araba.Renk}"; arry[3] = $"{nameof(_araba.Marka)}:{_araba.Marka}"; arry[2] = $"{nameof(_araba.Model)}:{_araba.Model}"; return string.Join(Environment.NewLine, arry); } } |
Buraya kadar yazdığımız kodları kullanmaya başlayalım. AracYonetimi adlı sınıftan bir örnek alacağız ve bu aldığımız örneğin constructor metodunu kullanarak tüm özelliklerine değerini vermiş oluyoruz. Sonrasında TumOzellikler adındaki metodu kullanıp console ekranına vermiş olduğumuz özelliklerin değerlerinin basıldığını görüyoruz.
1 2 3 | var aracYonetimi = new AracYonetimi(new Fiat("Fiat", "500L", Color.Red, 2)); WriteLine(aracYonetimi.TumOzellikler()); ReadLine(); |
Çıktı
AracYonetimi içinde tanımladığımız _araba field’ındaki IAraba arayüzünden türetilmiş sınıf üzerinde değişiklikleri yapmak için TekerSayisiDegistir, ModelDegistir ve RenkDegistir metodlarını kullanacağız ve bu değişikiği console’a bastırarak göreceğiz.
1 2 3 4 5 6 7 8 | var aracYonetimi = new AracYonetimi(new Fiat("Fiat", "500L", Color.Red, 2)); aracYonetimi.TekerSayisiDegistir(4); aracYonetimi.ModelDegistir("500X"); aracYonetimi.RenkDegistir(Color.Blue); WriteLine(aracYonetimi.TumOzellikler()); ReadLine(); |
Çıktı
Görüldüğü üzere metodlar sayesinde AracYonetimi constructor’ina geçtiğimiz IAraba arayüzünden türetilmiş sınıfın özelliklerinde değişikliği yapabiliyoruz new Fiat… yerine new Renault… yazarak başka değişiklik yapmadan Method Dependency Injection’i kullanabiliyoruz.
Property Injection
Property injection’da tek değişen üst örneğimizde yer alan _araba adlı field’i bir özelliğe çeviriyoruz ve constructor’ı kaldırıyoruz(isterseniz constructor aracılığı ile Araba adlı özelliğe değer atayabilirsiniz) AracYonetiminin son haline gözatalım.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 | class AracYonetimi { public IAraba Araba { get; set ; } public void RenkDegistir(Color renk) => Araba.Renk = renk; public void ModelDegistir(string model) => Araba.Model = model; public void TekerSayisiDegistir(byte tekerSayisi) => Araba.TekerSayisi = tekerSayisi; public string TumOzellikler() { var arry = new string[4]; arry[0] = $"{nameof(Araba.TekerSayisi)}:{Araba.TekerSayisi}"; arry[1] = $"{nameof(Araba.Renk)}:{Araba.Renk}"; arry[3] = $"{nameof(Araba.Marka)}:{Araba.Marka}"; arry[2] = $"{nameof(Araba.Model)}:{Araba.Model}"; return string.Join(Environment.NewLine, arry); } } |
AracYonetimi adlı sınıfta yaptığımız değişiklik sonrası şu şekilde kullanıyoruz.
1 2 3 4 5 6 7 8 9 | var aracYonetimi = new AracYonetimi { Araba = new Fiat("Fiat", "500L", Color.Red, 2) }; aracYonetimi.TekerSayisiDegistir(4); aracYonetimi.ModelDegistir("500X"); aracYonetimi.RenkDegistir(Color.Blue); WriteLine(aracYonetimi.TumOzellikler()); |
Çıktı önceki constructor injection’daki gibi olduğundan bir daha çıktıyı verip konuyu uzatmak istemiyorum.
Method Injection
Method injection’da consturtor yada özellik tanımlayıp IAraba arayüzünden türemiş sınıfı almayacağız bu defa metodların ilk parametresine IAraba arayüzünü ekleyeceğiz ve bu şekilde IAraba arayüzünden türemiş sınıfları parametre ile elde edeceğiz.
Öncelikle AracYonetimi adlı sınıfı alttaki şekilde değiştiriyoruz.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 | class AracYonetimi { public void RenkDegistir(IAraba araba, Color renk) => araba.Renk = renk; public void ModelDegistir(IAraba araba, string model) => araba.Model = model; public void TekerSayisiDegistir(IAraba araba, byte tekerSayisi) => araba.TekerSayisi = tekerSayisi; public string TumOzellikler(IAraba araba) { var arry = new string[4]; arry[0] = $"{nameof(araba.TekerSayisi)}:{araba.TekerSayisi}"; arry[1] = $"{nameof(araba.Renk)}:{araba.Renk}"; arry[3] = $"{nameof(araba.Marka)}:{araba.Marka}"; arry[2] = $"{nameof(araba.Model)}:{araba.Model}"; return string.Join(Environment.NewLine, arry); } } |
Gördüğünüz gibi Method Injection yöntemini kullandığımız için tüm metodların ilk parametresine IAraba arayüzünü ekliyoruz.
Method Injection adlı yöntemi uyguladığımız AracYonetimi adlı sınıfın kullanımı ise şu şekilde olacak.
1 2 3 4 5 6 7 8 | var aracYonetimi = new AracYonetimi(); var araba = new Fiat("Fiat", "500L", Color.Red, 2); aracYonetimi.TekerSayisiDegistir(araba, 4); aracYonetimi.ModelDegistir(araba, "500X"); aracYonetimi.RenkDegistir(araba, Color.Blue); WriteLine(aracYonetimi.TumOzellikler(araba)); |
Bu makale ile ilgili olumlu-olumsuz tüm görüşeriniz için bana yorum yada mail yolu ile ulaşabilirsiniz.
Makalede kullanılan tüm örneklere ve C# ile ilgili diğer tüm örneklere github hesabımdan erişebilirsiniz buraya tıklayıp github hesabıma erişebilirsiniz.
Video
.Net Core ve Blazor’da Dependency Injection yönetimi nasıl yapılıyor diye merak ediyorsanız altta gördüğünüz videoyu izleyebilirsiniz.
Çok güzel anlatım olmuş, 3 tür injection olayından bahseden nadirTürkçe kaynaklardansınız, tebrikler.
Ek olarak kullandığınız tema bu mudur, yoksa özel bir yapıda c+p yapıyorsunuz
Teşekkür ederim düşünceniz için. “tema” ve “c+p” ile ne demek istediğiniz anlayamadım biraz açabilir misiniz bu başlıkları?
anlamayaa çalışıyorum yaazı için teşekkürler
Solid prensiplerini ve Dependency Injection olayını bayadır inceliyorum. Bu kadar güzel anlatım görmedim. Tebrikler gerçekten…
Değerlendirmeniz için teşekkür ederim.