KnockoutJs,
Stavev Sanderson tarafından geliştirilmeye başlanmış bir JavaScript kütüphanesidir. Bu kütüphane ile amaçlanan sayfa
oluşturulurken hem veri hem de html kod aynı anda oluşturulurken hem verinin
hem de html kodlarının aynı anda oluşturulması performansı etkilediği için
alternatif olarak şöyle düşünmüşler biz önce html kodunu sayfaya basalım daha
sonra arka tarafta json ve javascript ile veriyi gerekli yere bind edelim
mantığı vardır. Peki bunu nasıl anlayabiliriz biraz bunu inceleyelim. Öncelikle
basit bir User sınıfı oluşturup 4 alan ekleyip oldukça basit bir şekilde
bunları listeleyelim.
Not : Daha sonra
tekrar knockoutjs’yi projeye nasıl dahil edebileceğimizi anlatacağım.
Sayfa oluştuğu zaman sadece 1 adet örnek html içeriği
yükleniyor daha sonra o örnek html içeriğine göre javascript tarafında jsondan
veri alınıp html de gerekli yerine yazılmaktadır. Sayfa ilk oluşturulduğunda Sayfa Kaynağını Görüntüle basıp html
çıktısına bakalım.
Üsteki resimde görüldüğü gibi sadece tek örnek div
oluşturulup bırakılmış bu örnekte tek
div olduğu için performans gözlemi yapmak zor ancak daha geniş çaplı bir
uygulamada belki üye bilgileri listelenirken binlerce div vb. taglar olacaktır
sayfa yüklenirken tasarım mı yüklensin yoksa sayfaya veriler teker teker
yazılması çok uzun süreçler alacaktır bunun yerine örnek div oluşturup daha
sonra o div javascript tarafından client-side tarafında çoğaltılmaktadır.
Tarayıcımıza Öğeyi
Denetle yaptığımız zaman verimizin sayfaya yazıldığını görüyoruz.
KnockoutJs, ViewModel ile HTMl arasında
köprü vazifesini üslenmektedir.
Nispeten de olsa KnockoutJs nasıl çalıştığına göz attığımıza
göre knockoutjsyi projeye nasıl dahil edebiliriz ve yazdığımız kodların ne işe
yaradığına göz atalım.
Öncelikle NuGet packages de knockoutjs yi aratıp projeyemize
Instal edelim. Instal ettiğimiz zaman projemizin scripts klasörünün altına 2
tane JS dosyası gelecektir. Bunlar : knockout-3.2.0.js ve knockout-3.2.0.debug.js
ilki sıkıştırılmış hali ben onu kullanacağım ayrıca ben bu makaleyi yazarken
güncel sürüm 3.2.0 sizde bu sürümü veya dilediğiniz sürümü kullanabilirsiniz…
Bununla birlikte birde jquery 2.1.1 sürümüne ihtiyacımız var
buna da buradan
ulaşabilirsiniz.
Knockout-3.2.0.js ve jquery-2.1.1.js bu iki JS’yi head
tagları arasına koyuruz.
Controller tarafında user list döndüren bir actinonumuz var.
public ActionResult Index()
{
List<User> users = new List<User>(){
new User(){
UserId=1,
UserName="User1",
Password="1234567",
Email="User1@gmail.com"
}, new User(){
UserId=2,
UserName="User2",
Password="1234567",
Email="User2@gmail.com"
}, new User(){
UserId=3,
UserName="User3",
Password="1234567",
Email="User3@gmail.com"
}, new User(){
UserId=4,
UserName="User4",
Password="1234567",
Email="User4@gmail.com"
}, new User(){
UserId=5,
UserName="User5",
Password="1234567",
Email="User5@gmail.com"
},
};
return View(users);
}
Bizi aslın ilgilendiren View kısmındaki kodlar burada 2
js ekledikten sonra javascript yardımı ile .net tarafındaki User sınıfımızı
jquery tarafın da karşılayacak olan nesnemizi tanımlıyoruz. Buradaki
users:ko.observale() kısmındaki users bizim liste nasıl erişebileceğimizi
belirliyor.
var myViewModel = {
users: ko.observable()
};
Daha sonra model ile aldığımız veriyi json formatında
javascript tarafına aktarmamız gerekmektedir bunun için 2 yöntem mevcut ilk
yöntem @Html.Raw(Json.Encode(Model)) ile modeli json formatına çevirebiliriz
öncelikle bu yöntemi inceleyelim.
myViewModel.users(@Html.Raw(Json.Encode(Model)));
Ancak bu yöntem ile verileri jquery tarafına aktardığımız
zaman 2 sorun çıkıyor.
İlk sorun biz
verileri View’in model’inden aldığımız için ve bu modelede .js sınıfından
erişemeyeceğimize göre mecbur jquery kodlarını view’in içinde yani html
kodlarının arasında yazmak durumunda kalıyoruz buda kodun karışık olmasını
gösteriyor.
Buna çözüm olarak şunu önerebilirim
size bir .js kütüphanesi oluşturup bunun içinden ayrı bir actiondan veriyi
JsonResult ile tekrar post ederek hem veriyi kullanıcıya göstermemiş oluruz
hemde html kodları ile jquery kodlarını ayırmış oluruz.
Action kodları
Action kodları
public ActionResult Index()//sayfamızının
açılacağı action
{
return View();
}
[HttpPost]//Actionumuzun başına HttpPost koymayı unutmuyoruz yoksa
veriler sayfanın urlsinden de erişilebilir durumda olur
public JsonResult UserData()//Veriyi
çağıracağımız action
{
List<User> users = new List<User>(){
new User(){
UserId=1,
UserName="User1",
Password="1234567",
Email="User1@gmail.com"
}, new User(){
UserId=2,
UserName="User2",
Password="1234567",
Email="User2@gmail.com"
}, new User(){
UserId=3,
UserName="User3",
Password="1234567",
Email="User3@gmail.com"
}, new User(){
UserId=4,
UserName="User4",
Password="1234567",
Email="User4@gmail.com"
}, new User(){
UserId=5,
UserName="User5",
Password="1234567",
Email="User5@gmail.com"
},
};
return Json(users);
}
View kodlarımız
Burada
bir şeye dikkat çekmek istiyorum viewin içinde herhangi bir model tanımlaması
yapmadık. Sadece jquery kütüphanemizi referans ettik.
@{
Layout = null;
}<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="width=device-width" />
<title>Knockout Örnek</title>
<script src="https://code.jquery.com/jquery-2.1.1.js"></script>
<script src="~/Scripts/knockout-3.2.0.js"></script>
<script src="~/Scripts/knockoutData.js"></script>
</head>
<body>
<div data-bind="foreach:users">
<div data-bind="text:UserName"></div>
</div>
</body>
</html>
Jquery kütüphanesi kodları
$(function () {
var myViewModel = {
users: ko.observable()
};
$.post("/KnockoutJs/UserData", function (data) {
myViewModel.users(data);
ko.applyBindings(myViewModel);
});
});
Sonuç
Bu makalede knockoutun nasıl
çalıştığını projeye nasıl dahil edebileceğimizi kısaca görmüş olduk bununla
beraber veriyi nasıl bind edebileceğimize bakmış olduk. Tabi knockout birçok
özellik sunmakta bunları da ilerleyen zamanlarda detaylı inceleme fırsatımız olacak
bir sonraki makalede görüşmek üzere.