我們經常會遇到這樣的場景: 今天來了個業務,需要加一個字段,但是考慮的以后可能有變動,需要配成“活”的。 一般最初的做法就是加一個配置到Web.Config文件的AppSettings中去。但是這樣有一個問題,那就是改一下配置節點,AppDomain就需要重啟,很是不爽。 變通一點的會搞出一個xml文件,利用序列化去動態的讀取。但是,哥!每次都讀文件不覺得太耗IO嗎?尤其是使用頻率高話?
下面上代碼吧,懶的廢話了,關鍵地方都注釋了,也不是什么高深的技術:
先來配置文件(注意Config路徑要自己建,代碼沒有處理)和對應的配置文件代碼:
<?xml version="1.0" encoding="utf-8"?><SimpleBizConfig xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema"> <ID>12</ID> <Key>MyKey</Key> <ListSimple> <string>簡單</string> <string>list</string> <string>集合</string> </ListSimple></SimpleBizConfig>
using System.Text;using Glutton.Web.Configuration;using System;using System.Collections.Generic;using System.Linq;using System.Web;namespace WebTest.Models{ public class SimpleBizConfig : ISimpleConfig { /// <summary> /// 默認配置文件路徑 /// </summary> public string GetPath() { return "~/Config/SimpleBizConfig.cfg"; } public string GetCacheKey() { return "~/MyConfig_SimpleBizConfig"; } public SimpleBizConfig() { this.ID = 1; this.Key = "MyKey"; this.ListSimple = new List<string>(); } public int ID { get; set; } public string Key { get; set; } public List<string> ListSimple { get; set; } internal string Desc() { StringBuilder sb = new StringBuilder(); sb.Append("類型:SimpleBizConfig").Append("<br/>"); sb.Append("ID = " + this.ID.ToString()).Append("<br/>"); sb.Append("Key = " + this.Key).Append("<br/>"); sb.Append("list").Append("<br/>"); for (int i = 0; i < this.ListSimple.Count; i++) { sb.Append("index:" + i.ToString() + ",value:" + ListSimple[i]).Append("<br/>"); } return sb.ToString(); } }}
再來管理配置文件的類:
using System;using System.Collections.Generic;using System.IO;using System.Linq;using System.Runtime.InteropServices;using System.Text;using System.Threading.Tasks;using System.Web;using System.Web.Caching;using System.Xml.Serialization;namespace Glutton.Web.Configuration{ public interface ISimpleConfig { string GetPath(); string GetCacheKey(); } public class ConfigManager { public static T GetConfig<T>() where T : class ,ISimpleConfig, new() { T tmpT = new T(); string cacheKey = tmpT.GetCacheKey(); //先嘗試從cache中取數據 T t = GetFromCache<T>(cacheKey);//很郁悶,沒有靜態泛型接口 if (t != null) { return t; } //cache沒有數據,直接讀配置文件 XmlSerializer xmlSerializer = new XmlSerializer(typeof(T)); string configFilePath = HttpContext.Current.Server.MapPath(tmpT.GetPath()); if (!File.Exists(configFilePath)) { //文件不存在,初始化,這里需要配置文件類實現默認的初始化動作 using (TextWriter writer = new StreamWriter(configFilePath)) { t = new T(); xmlSerializer.Serialize(writer, t); } } else { using (FileStream fs = new FileStream(configFilePath, FileMode.Open)) { t = xmlSerializer.Deserialize(fs) as T; } } //存到緩存里面去,依賴web緩存的文件依賴功能實現監控配置文件修改 SetToCache<T>(cacheKey, configFilePath, t); return t; } PRivate static void SetToCache<T>(string cacheKey, string configFilePath, T t) where T : class ,new() { HttpRuntime.Cache.Insert(cacheKey, t, new CacheDependency(configFilePath), //文件依賴過期 Cache.NoAbsoluteExpiration, Cache.NoSlidingExpiration, CacheItemPriority.NotRemovable, null); } private static T GetFromCache<T>(string cacheKey) where T : class ,new() { return HttpRuntime.Cache[cacheKey] as T; } }}
看看調用的方法,HomeController里面加了一個測試方法:
using System;using System.Collections.Generic;using System.Linq;using System.Web;using System.Web.Mvc;using Glutton.Web.Configuration;using WebTest.Models;namespace WebTest.Controllers{ public class HomeController : Controller { public ActionResult Index() { return View(); } public ActionResult About() { ViewBag.Message = "Your application description page."; return View(); } public ActionResult Contact() { ViewBag.Message = "Your contact page."; return View(); } public string TestCfg() { return ConfigManager.GetConfig<SimpleBizConfig>().Desc(); } }}
看看效果,:-D:
新聞熱點
疑難解答