Bu makale makine çevirisi ayna makalesidir, orijinal makaleye geçmek için lütfen buraya tıklayın.

Görünüm: 16824|Yanıt: 0

[ASP.NET] Performans optimizasyonu ASP.NET özel bir dosya önbelleği oluşturun

[Bağlantıyı kopyala]
Yayınlandı 19.04.2015 22:06:12 | | | |
ASP.NET çıktı önbellekleme (yani statik HTML) .NET 4.0'a kadar bellek tabanlıydı. Bu, sitemizde çok fazla önbellek varsa, yerel belleği kolayca tüketebileceği anlamına gelir. Şimdi, . .NET 4.0'da OutputCacheProvider ile kendi önbelleğimizi oluşturmak için birkaç seçeneğimiz var. Örneğin, HTML çıktı önbelleğini memcache dağılık dağıtılmış küme sunucusunda veya MongoDB'de (yaygın kullanılan bir belge odaklı veritabanı, bu http://msdn.microsoft.com/zh-cn/magazine/gg650661.aspx okuyun) depolayabiliriz. Elbette, önbelleği sabit diskte dosya olarak da saklayabiliriz; ölçeklenebilirlik göz önüne alındığında bu en ucuz yöntemdir ve bu makale özel bir dosya önbelleği nasıl oluşturulurla ilgilidir.
1:OutputCacheProvider
OutputCacheProvider, dört yöntemini geçersiz kılmamız gereken soyut bir temel sınıftır; bunlar şunlardır:
Belirtilen öğeyi çıktı önbelleğine eklemek için yöntem ekleyin.
Get metodu ile çıktı önbelleğinde belirtilen öğeye referans döndürür.
Belirtilen öğeyi çıktı önbelleğinden çıkarmak için yöntemi kaldırın.
Set metodu, belirtilen öğeyi çıktı önbelleğe ekler ve önbellekliyse öğenin üzerine yazar.
2: Kendi dosya önbellekleme işleme sınıfınızı oluşturun
Tip FileCacheProvider'dır ve kod şu şekildedir:

  1. public class FileCacheProvider : OutputCacheProvider
  2. {
  3.     private static readonly ILog log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);

  4.     public override void Initialize(string name, NameValueCollection attributes)
  5.     {
  6.         base.Initialize(name, attributes);
  7.         CachePath = HttpContext.Current.Server.MapPath(attributes["cachePath"]);
  8.     }

  9.     public override object Add(string key, object entry, DateTime utcExpiry)
  10.     {
  11.         Object obj = Get(key);
  12.         if (obj != null)    //这一步很重要
  13.         {
  14.             return obj;
  15.         }
  16.         Set(key,entry,utcExpiry);
  17.         return entry;
  18.     }

  19.     public override object Get(string key)
  20.     {
  21.         string path = ConvertKeyToPath(key);
  22.         if (!File.Exists(path))
  23.         {
  24.             return null;
  25.         }
  26.         CacheItem item = null;
  27.         using (FileStream file = File.OpenRead(path))
  28.         {
  29.             var formatter = new BinaryFormatter();
  30.             item = (CacheItem)formatter.Deserialize(file);
  31.         }

  32.         if (item.ExpiryDate <= DateTime.Now.ToUniversalTime())
  33.         {
  34.             log.Info(item.ExpiryDate + "*" + key);
  35.             Remove(key);
  36.             return null;
  37.         }
  38.         return item.Item;
  39.     }


  40.     public override void Set(string key, object entry, DateTime utcExpiry)
  41.     {
  42.         CacheItem item = new CacheItem(entry, utcExpiry);
  43.         string path = ConvertKeyToPath(key);
  44.         using (FileStream file = File.OpenWrite(path))
  45.         {
  46.             BinaryFormatter formatter = new BinaryFormatter();
  47.             formatter.Serialize(file, item);
  48.         }
  49.     }
  50.       
  51.     public override void Remove(string key)
  52.     {
  53.         string path = ConvertKeyToPath(key);
  54.         if (File.Exists(path))
  55.             File.Delete(path);
  56.     }

  57.     public string CachePath
  58.     {
  59.         get;
  60.         set;
  61.     }

  62.     private string ConvertKeyToPath(string key)
  63.     {
  64.         string file = key.Replace('/', '-');
  65.         file += ".txt";
  66.         return Path.Combine(CachePath, file);
  67.     }
  68. }

  69. [Serializable]
  70. public class CacheItem
  71. {
  72.     public DateTime ExpiryDate;
  73.     public object Item;

  74.     public CacheItem(object entry, DateTime utcExpiry)
  75.     {
  76.         Item = entry;
  77.         ExpiryDate = utcExpiry;
  78.     }
  79. }
Kopya kodu
Özel dikkat gerektiren iki yer vardır:
Ekle yönteminde, bu şekilde ele alınması gereken koşullu bir karar vardır; aksi takdirde önbellek mekanizması ilk sonucu önbelleyecek ve önbellek son kullanma tarihinden sonra sona erer ve yeniden inşa edilmez.
Örnek programda, önbelleği önbellek dizinine koyuyoruz ve gerçek proje uygulamasında, önbelleğe alınan sayfaların binlerce olacağı göz önüne alındığında, dizin sınıflandırması yapmak zorundayız, aksi takdirde önbellek dosyalarını bulmak ve okumak verimlilik darboğazı haline gelir ve CPU'yu tüketir.
3: Yapılandırma dosyası

Web.config'de önbellek işleyicisinin özel bir FileCacheProvider olduğunu yapılandırmamız gerekiyor, yani FileCacheProvider altına bir düğüm eklemek gerekir:
  1. <caching>
  2.   <outputCache defaultProvider="FileCache">
  3.     <providers>
  4.       <add name="FileCache" type="MvcApplication2.Common.FileCacheProvider" cachePath="~/Cache" />
  5.     </providers>
  6.   </outputCache>
  7. </caching>
Kopya kodu

4: Önbellek kullanımı

MVC'nin kontrolünde kullanıldığında (ASP.NET sayfasında kullanmak istiyorsanız, page@OutputCache VaryByParam="none" Duration="10" %> içine %<% ekleyin) ve Index'in çıktı önbelleğe alınmadığını, Index2'nin ise 10 saniye önbelleğe alındığını görebilirsiniz.
  1. public class HomeController : Controller
  2. {
  3.     private static readonly ILog log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);
  4.     static string s_conn = "Data Source=192.168.0.77;Initial Catalog=luminjidb;User Id=sa;Password=sa;";
  5.     public ActionResult Index()
  6.     {
  7.         using (DataSet ds = Common.SqlHelper.ExecuteDataset(s_conn, CommandType.Text, "select top 1* from NameTb a, DepTb b where a.DepID = b.ID ORDER BY NEWID()"))
  8.         {
  9.             ViewBag.Message = ds.Tables[0].Rows[0]["name"].ToString();
  10.         }
  11.         return View();
  12.     }

  13.     [OutputCache(Duration = 10, VaryByParam = "none")]
  14.     public ActionResult Index2()
  15.     {
  16.         using (DataSet ds = Common.SqlHelper.ExecuteDataset(s_conn, CommandType.Text, "select top 1* from NameTb a, DepTb b where a.DepID = b.ID ORDER BY NEWID()"))
  17.         {
  18.             ViewBag.Message = ds.Tables[0].Rows[0]["name"].ToString();
  19.         }
  20.         return View();
  21.     }
  22. }
Kopya kodu
5: Etkisini kontrol et
Yukarıdaki kod, Index2'ye erişildikten sonra, Cache klasöründe aşağıdaki gibi bir önbellek dosyası oluşturur:

Şimdi, çıkış önbelleği ile çıktı önbelleği arasındaki performans karşılaştırmasını değerlendirelim ve 100 kullanıcıdan gelen 100 eşzamanlı talebi şu şekilde simüle edelim:








Önceki:Session'ın yaşam döngüsü
Önümüzdeki:C#. .NET SQL enjeksiyon saldırılarını önlemek için
Feragatname:
Code Farmer Network tarafından yayımlanan tüm yazılım, programlama materyalleri veya makaleler yalnızca öğrenme ve araştırma amaçları içindir; Yukarıdaki içerik ticari veya yasa dışı amaçlarla kullanılamaz, aksi takdirde kullanıcılar tüm sonuçları ödemelidir. Bu sitedeki bilgiler internetten alınmakta olup, telif hakkı anlaşmazlıklarının bu siteyle hiçbir ilgisi yoktur. Yukarıdaki içeriği indirmeden sonraki 24 saat içinde bilgisayarınızdan tamamen silmelisiniz. Programı beğendiyseniz, lütfen orijinal yazılımı destekleyin, kayıt satın alın ve daha iyi orijinal hizmetler alın. Herhangi bir ihlal olursa, lütfen bizimle e-posta yoluyla iletişime geçin.

Mail To:help@itsvse.com