public SettingsController(ISettings settings) { // example of saving _settings.General.SiteName = "دات نت تیپس"; _settings.Seo.HomeMetaTitle = ".Net Tips"; _settings.Seo.HomeMetaKeywords = "َAsp.net MVC,Entity Framework,Reflection"; _settings.Seo.HomeMetaDescription = "ذخیره تنظیمات برنامه"; _settings.Save(); }
- تنظیمات به صورت گروه بندی شده در کنار هم قرار گرفتهاند و یافتن تنظیمات برای زمانی که نیاز به دسترسی به آنها داریم، راحتتر و سادهتر خواهد بود.
- به این شکل تنظیمات قابل دسترس در یک گروه، از دیتابیس بازیابی خواهند شد.
اصلا چرا باید این تنظیمات را در دیتابیس ذخیره کنیم؟
- ساخت یک Asp.net Web Application
- ساخت مدل Setting و افزودن آن به کانتکست Entity Framework
- ساخت کلاس SettingBase برای بازیابی و ذخیره سازی تنظیمات با رفلکشن
- ساخت کلاس GenralSettins و SeoSettings که از کلاس SettingBase ارث بری کردهاند.
- ساخت کلاس Settings به منظور مدیریت تمام انواع تنظیمات
namespace DynamicSettingAPI.Models { public interface IUnitOfWork { DbSet<Setting> Settings { get; set; } int SaveChanges(); } } public class ApplicationDbContext : IdentityDbContext<ApplicationUser>,IUnitOfWork { public DbSet<Setting> Settings { get; set; } public ApplicationDbContext() : base("DefaultConnection", throwIfV1Schema: false) { } public static ApplicationDbContext Create() { return new ApplicationDbContext(); } } namespace DynamicSettingAPI.Models { public class Setting { public string Name { get; set; } public string Type { get; set; } public string Value { get; set; } } }
protected override void OnModelCreating(DbModelBuilder modelBuilder) { modelBuilder.Entity<Setting>() .HasKey(x => new { x.Name, x.Type }); modelBuilder.Entity<Setting>() .Property(x => x.Value) .IsOptional(); base.OnModelCreating(modelBuilder); }
namespace DynamicSettingAPI.Service { public abstract class SettingsBase { //1 private readonly string _name; private readonly PropertyInfo[] _properties; protected SettingsBase() { //2 var type = GetType(); _name = type.Name; _properties = type.GetProperties(); } public virtual void Load(IUnitOfWork unitOfWork) { //3 get setting for this type name var settings = unitOfWork.Settings.Where(w => w.Type == _name).ToList(); foreach (var propertyInfo in _properties) { //get the setting from setting list var setting = settings.SingleOrDefault(s => s.Name == propertyInfo.Name); if (setting != null) { //4 set propertyInfo.SetValue(this, Convert.ChangeType(setting.Value, propertyInfo.PropertyType)); } } } public virtual void Save(IUnitOfWork unitOfWork) { //5 get all setting for this type name var settings = unitOfWork.Settings.Where(w => w.Type == _name).ToList(); foreach (var propertyInfo in _properties) { var propertyValue = propertyInfo.GetValue(this, null); var value = (propertyValue == null) ? null : propertyValue.ToString(); var setting = settings.SingleOrDefault(s => s.Name == propertyInfo.Name); if (setting != null) { // 6 update existing value setting.Value = value; } else { // 7 create new setting var newSetting = new Setting() { Name = propertyInfo.Name, Type = _name, Value = value, }; unitOfWork.Settings.Add(newSetting); } } } } }
propertyInfo.SetValue(this, Convert.ChangeType(setting.Value, propertyInfo.PropertyType));
public class GeneralSettings : SettingsBase { public string SiteName { get; set; } public string AdminEmail { get; set; } public bool RegisterUsersEnabled { get; set; } } public class GeneralSettings : SettingsBase { public string SiteName { get; set; } public string AdminEmail { get; set; } }
public interface ISettings { GeneralSettings General { get; } SeoSettings Seo { get; } void Save(); } public class Settings : ISettings { // 1 private readonly Lazy<GeneralSettings> _generalSettings; // 2 public GeneralSettings General { get { return _generalSettings.Value; } } private readonly Lazy<SeoSettings> _seoSettings; public SeoSettings Seo { get { return _seoSettings.Value; } } private readonly IUnitOfWork _unitOfWork; public Settings(IUnitOfWork unitOfWork) { _unitOfWork = unitOfWork; // 3 _generalSettings = new Lazy<GeneralSettings>(CreateSettings<GeneralSettings>); _seoSettings = new Lazy<SeoSettings>(CreateSettings<SeoSettings>); } public void Save() { // only save changes to settings that have been loaded if (_generalSettings.IsValueCreated) _generalSettings.Value.Save(_unitOfWork); if (_seoSettings.IsValueCreated) _seoSettings.Value.Save(_unitOfWork); _unitOfWork.SaveChanges(); } // 4 private T CreateSettings<T>() where T : SettingsBase, new() { var settings = new T(); settings.Load(_unitOfWork); return settings; } }
private readonly ICache _cache; public Settings(IUnitOfWork unitOfWork, ICache cache) { // ARGUMENT CHECKING SKIPPED FOR BREVITY _unitOfWork = unitOfWork; _cache = cache; _generalSettings = new Lazy<GeneralSettings>(CreateSettingsWithCache<GeneralSettings>); _seoSettings = new Lazy<SeoSettings>(CreateSettingsWithCache<SeoSettings>); } private T CreateSettingsWithCache<T>() where T : SettingsBase, new() { // this is where you would implement loading from ICache throw new NotImplementedException(); }
public ActionResult Index() { using (var uow = new ApplicationDbContext()) { var _settings = new Settings(uow); _settings.General.SiteName = "دات نت تیپس"; _settings.General.AdminEmail = "admin@gmail.com"; _settings.General.RegisterUsersEnabled = true; _settings.Seo.HomeMetaTitle = ".Net Tips"; _settings.Seo.MetaKeywords = "Asp.net MVC,Entity Framework,Reflection"; _settings.Seo.HomeMetaDescription = "ذخیره تنظیمات برنامه"; var settings2 = new Settings(uow); var output = string.Format("SiteName: {0} HomeMetaDescription: {1} MetaKeywords: {2} MetaTitle: {3} RegisterEnable: {4}", settings2.General.SiteName, settings2.Seo.HomeMetaDescription, settings2.Seo.MetaKeywords, settings2.Seo.HomeMetaTitle, settings2.General.RegisterUsersEnabled.ToString() ); return Content(output); } }