Strategy pattern ile NetCore 2.0 Multi CDN Azure+AWS+FileSystem


Merhaba arkadaşlar. Bu yazımda size Strategy Pattern ile NetCore içinde Dosya Sistemi, Azure ve AWS için çoktan seçmeli bir CDN mimari örneği sunacağım. Bu projede amaç local dosyalarla çalışmaya başlayıp daha sonra Azure veya AWS ye geçiş yapmayı planlayanlar için bir örnek olmuş olacak. Tabi isterseniz Azure-AWS arasında da geçiş planlayarak çalışmak isteyen olursa kullanabilir. Bu üç örnekteki CDN ler arasında dosyaları fiziksel olarak aktarıp dosya işlemlerinize kaldığınız yerden devam etmenizi sağlayacak bir örnek olacaktır. Özellikle Strategy Pattern kullanımını da daha iyi kavramanız için güzel bir örnektir.

Projemi NetCore 2 üzerinde MVC projesi ile yaptım ancak diğer projeleri de kullanabilirsiniz. İlk olarak projede strategy patterni bize sunacak olan interface i oluşturalım.

2017-11-12 15_10_14-CoreCDNSample - Microsoft Visual Studio

Dosyamı components altına CDN klasöründe oluşturdum. Interface içeriği ise şu şekilde

2017-11-12 15_21_18-CoreCDNSample - Microsoft Visual Studio

Burada iki fonksiyon göreceksiniz. Bu bizim strateji uygulayacağımız iki temel fonksiyon oluyor. CDN lerimiz bu arabirimden oluşmayacak ama bu arabirimi karşılayacak şekilde olmak zorunda. Yani CDN lerimiz farklı fonksiyonlarda içerebilir ancak bu fonksiyonlar şart!

Save fonskiyonu ile içeri göndereceğimiz byte dizisini verdiğimiz ad ile CDN kök dizinine belirteceğimiz klasör içerisine kaydetmesini sağlayacak.

GetPath fonksiyonu online adresini döndüren fonksiyon. Eğer kullanacağınız cdn üzerinde bir şifre ile paylaşım vs yada değişken bir yol durumu söz konusu olacak ise bu fonksiyon bu işi görecek. Biz projemizde bu durumu sabit olarak kabul edeceğiz, o kısmı düz geçeceğiz.

Şimdi ilk CDN imiz olan FileSystemCDN i yazalım.

2017-11-12 16_02_39-CoreCDNSample - Microsoft Visual Studio

Gördüğünüz gibi ICDN den türetilen fonksiyonlar bu şekilde bulunmakta. GetPath başında bahsettiğim gibi düz geçildi. Save fonksiyonu ise dosya kaydetme işlemini temel düzeyde istediğimiz dizine kaydedecek şekilde yapılandırdık. Burada constructor fonksiyon da iki parametre aldık, bunlar local CDN olacağı local path ve bu path in url karşılığı olacak.

Geçelim Azure CDN sınıfımıza. Öncelikle Azure için Nuget yükleme işlemini yapalım.

2017-11-12 16_09_39-CoreCDNSample - Microsoft Visual Studio

WindowsAzure.Storage bileşenini projemize ekledikten sonra artık AzureCDN sınıfımızı oluşturabiliriz.

2017-11-12 17_40_02-CoreCDNSample - Microsoft Visual Studio

Constructor fonksiyonumuzda iki parametre alıyoruz, bunlar azure bağlantısı için connectionstring ve containerimiz.

2017-11-12 17_40_34-CoreCDNSample - Microsoft Visual Studio

Burada bir fonksiyon ile CloudBlobContainer nesnesini döndürüyoruz. Her iki fonksiyonda da lüzum edeceği için bunu tek noktaya taşımak istedim. Fonksiyon içeriği CloudStorageAccount nesnesini connection stringimizden üreterek CloudBlobClient nesnemizi oluşturmaya yarıyor. Client de bize containerimizi verecek. Container aslında Azure içerisinde ki kök dizin mantığında oluşturacağımız ana klasör. Bu container olmadan malesef dosya barındırmamız mümkün değil. Eğer containerimizi oluşturmadıysak CreateIfNotExistsAsync fonksiyonunu çağırarak “oluşturmadıysak bizim yerimize oluştursana” demiş oluyoruz. Bu arada ben fonksiyonları async ile işaretlemedim bu yüzden sonlarında Wait fonksiyonunu kullandım. Siz fonksiyonların dönüş tipini async Task<> şekline yaparsanız hem daha iyi olur hem de Wait e gerek kalmaz (await kullanırsınız). Daha sonraki aşamada ise bu containerin erişimini ayarlıyoruz. Ben herkese açık iznini verdim. Daha fazla bilgi için Azure sitesine bakabilirsiniz.

2017-11-12 17_41_01-CoreCDNSample - Microsoft Visual Studio

Şimdi GetPath ile yüklediğimiz bir dosyanın tam url ini almamız mümkün. Bu fonksiyona örneğin images/laptop.jpg gibi bir adres gönderirsek bize https://user.azurestorage.com/container1/images/laptop.jpg gibi bir adres döndürür. Bu arada baştaki url yi tam hatırlayamadım yanlışta olabilir ama gerek te yok zaten dönmüş olacak. Bu arada bu adresi buradan almak zorunda değilsiniz genel olarak zaten hep bir adres şablonu ile çalıştığı için elle de başına adresler eklemeniz mümkün, tabi özel keyler filan gerekmiyorsa yani containeriniz public değilse.

2017-11-12 17_41_20-CoreCDNSample - Microsoft Visual Studio

Burada da kaydetme aşamasını görüyoruz. Yine containerimizi alıp blobumuza ulaşarak içerisine fiziksel bir dosya yüklemek için block nesnesinin UploadFromByteArrayAsync fonksiyonundan faydalanıyoruz. Bu fonksiyon klasik filestream daki gibi byte dizisi ile çalışmakta. Tabi siz bir path üzerinden de yükletebilirsiniz. Blockumuz içerisinde ki farklı fonksiyonlara bakın.

Artık Azure ile işimiz tamamdır. Şimdi Amazon Servisine geçelim.

2017-11-12 20_57_41-CoreCDNSample - Microsoft Visual Studio

Nuget üzerinden AWSSDK.S3 paketini projemize kuruyoruz. Artık AWS için ICDN içeren bir concrete sınıf oluşturma zamanı geldi.

2017-11-12 21_13_39-CoreCDNSample - Microsoft Visual Studio

Burada Amazon için 3 parametreye ihtiyaç duyuyoruz. AccessKey ve SecretKey bilgilerini AWS hesabınızdan öğrenmeniz mümkün, bucket ise Azure konusunda anlattığım container mevzusuna benzemekte.

2017-11-12 21_16_07-CoreCDNSample - Microsoft Visual Studio

Geldik GetPath fonksiyonuna. Bu yine Azure daki gibi vereceğimiz klasör ve dosya adındaki relative pathimi url olarak geri verecek fonksiyonumuz. Öncelikle AmazonS3Client nesnemizi accessKey ve secretKey ile üretiyoruz. Farklı parametrelerle de başlıyor S3 SDK dökümanlarını okumanızı tavsiye ederim. Ben kendi bildiğim yöntemle yaptım AWS konusunda çok tecrübeli olduğumu söyleyemem. Daha sonra clientin bize elimizde var olan bucketleri vermesini istiyoruz ve bize bucket response listesi döndüyor. Bunun içinde ki Buckets nesnesinde ismi bizim bucketimizle aynı olan bucketi çekiyoruz. Burada anladığım kadarıyla azure daki gibi bucket yoksa oluştur olayı yok. Bunu AWS consolundan önce oluşturmak gerekiyor. Her ne ise bucketimizi aldıktan sonra eğer bucket boş dönmemişse direk cliente (evet tekrar baştaki nesneye dönüp) GetPreSignedURL fonksiyonu ile bir request gönderip adresi alıyoruz. Bu requeste şu üç parametre yeterli oluyor, bucketname bizim verdiğimiz bucket adı, key yani relativ olarak klasör ve dosya adı ve üçüncü olarak son kullanma tarihi. Bu işlemlerin sonucunda bize dosyamızın url i dönmüş oluyor.

2017-11-12 21_38_53-CoreCDNSample - Microsoft Visual Studio

Geldik save olayına. Yine dosya byte dizisi, adı ve konacağı klasörü geçiriyoruz. Bu arada farklı şekillerde dosyayı iletmeniz mümkün ancak bu projede kullandığımız ICDN her üç yöntem içinde ortak olmalı, farklı bir şey yapacaksanız elbette farklı yöntemlere başvurabilirsiniz. Her ne ise bu aşamada yine clientimizi oluşturup gelen diziyi stream e çevirmek adına memorystream kullandık. Yükleme işlemi için ise TransferUtility objesini kullanacaksınız. Bu obje bize dosya transferlerini yapmamızı sağlayan ana nesne. Hemen bir request oluşturuyoruz. Requestte yüklenecek bucket, storageclass tipimizi (niye reducedredundancy olduğunu bilmiyorum ama kelime anlamı gereksiz şeyleri kısıtlama anlamına geliyor ne işe yarıyorsa artık, sanırım sıkıştırma filandır bilen varsa yazsın 🙂 böyle şeyler için AWS dökümanını bir yalamanız da gerekebilir.) belirtiyoruz. Farklı tiplerde de belirtmemiz mümkün ince ayar için dökümanları incelemenizi tavsiye ederim. Sonra CannedACL ile herkese okuma izni veriyoruz. Key muhabbeti yine dosyanın klasör ve adı oluyor. Ardından yüklenecek dosyanın stream hali. Bu şekilde yükleme işlemi yapabiliriz. Ardından transferutility e upload komutu verip requesti geçiriyoruz. Bir hata olmamışsa dosya yüklendi demektir.

Artık strategy uygulama vakti geldi. Hemen Components altındaki CDN dizinine bir Context sınıfı oluşturalım.

2017-11-12 22_02_51-CoreCDNSample - Microsoft Visual Studio

Context sınıfımız oluşurken strateji örneğini aldığına dikkatinizi çekerim. Eğer enum gibi bir şey kullansaydık ve bunun sonucunda oluştursaydık (bunu tavsiye ederim CDN sınıfı içeride oluşur ve parametrelerini veritabanı veya config dosyasından okuyabilir) bu strateji + fabrika yöntemine girerdi. Bu yüzden fabrika yöntemini burada oluşturmuyoruz. Daha sonra aldığımız bu CDN arabirimini private olarak saklayarak ICDN arabirimini context sınıfımıza da uyarlıyoruz. Artık context sınıfımızı yarattıktan sonra direk bu sınıf üzerinden GetPath ve Save fonksiyonlarını kullanacağız.

Evet geldik test aşamasına. Bu aşamada Azure Local Storage şeysini kullanarak lokal test yapacağım. Siz online çalışmak için normal işlemleri yapmanız gerek. Hemen bir controller oluşturup dosya yükleyelim.

2017-11-12 23_12_43-CoreCDNSample - Microsoft Visual Studio

2017-11-12 23_23_33-CoreCDNSample - Microsoft Visual Studio

 

Yukarıda dosya yapısını gösterdikten sonra controlleri de göstereyim dedim. Index action içinde bir file input var. Buradan yükle dediğimizde Upload actionına dosyamız gelecek. Burada context nesnesinden örnekleme yaptım ancak bu çok mantıklı bir yaklaşım olmadı. Yapılması gereken bence ya bu contexti dependency ile üretmek yada fabrika ile birleştirmek. Yoksa direk azurecdn yi burada da kullanabilirdik 🙂 Neyse olayın o kısmı şu an ki konumuz dışı inşallah vakit olursa o konulara da gireriz. Bu aşamadan sonra işlem basit save yapacaz tabiki. Hadi yapalım.

2017-11-12 23_26_31-Microsoft Azure Storage Explorer

Evet resimde de görüldüğü gibi sol tarafta blob containers altına corecdn containerini oluşturup içerisine images klasörünü oluşturmuş ve içine de technics… şekline bir adla dosyayı kaydetmiş.

Evet olay bu kadar, projeyi indirip üzerinde incelemek veya kendi projenizde bir şekilde kullanmak isterseniz git adresi aşağıdadır.

https://github.com/halityurttas/NetCore2-MultipleCDN-StrategyPattern

Tekrar görüşünceye dek esenlikle…

Bu yazı 698 defa görüntülendi

Bir cevap yazın

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

This site uses Akismet to reduce spam. Learn how your comment data is processed.

Yazar Hakkında

15 yıllık çalışma hayatında birçok proje geliştirmiş binlerce projeyi inceleme fırsatı bulmuş yazılım aşığıdır. İşini hobi olarak gören yazarımız iş hayatını profesyonelce zevkle sürdürmektedir.

Son Eklenenler