Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- using Castle.DynamicProxy;
- using Newtonsoft.Json;
- using System;
- using System.Collections.Concurrent;
- using System.IO;
- namespace Utils {
- public class JsonSettingProvider<T> where T : class, new() {
- private static string settingFileDir = AppDomain.CurrentDomain.BaseDirectory;
- private static string settingFileName = typeof(T).Name + ".config";
- private static string settingFile = Path.Combine(settingFileDir, settingFileName);
- private volatile static bool loaded = false;
- private volatile static bool innerSet = false;
- private static T setting = new T();
- private static FileSystemWatcher fsw;
- private static object locker = new object();
- static JsonSettingProvider() {
- if (!File.Exists(settingFile)) {
- if (!Directory.Exists(settingFileDir)) {
- Directory.CreateDirectory(settingFileDir);
- }
- Save();
- }
- fsw = new FileSystemWatcher(settingFileDir, settingFileName);
- fsw.IncludeSubdirectories = false;
- fsw.Changed += Fsw_Changed;
- fsw.EnableRaisingEvents = true;
- }
- public static T Setting {
- get {
- if (loaded) {
- return setting;
- }
- lock (locker) {
- var settingInFile = JsonConvert.DeserializeObject<T>(File.ReadAllText(settingFile));
- ProxyGenerator generator = new ProxyGenerator();
- setting = generator.CreateClassProxyWithTarget<T>(settingInFile, new SettingChangeInterceptor());
- try {
- innerSet = true;
- foreach (var property in settingInFile.GetType().GetProperties()) {
- var obj = property.GetValue(settingInFile);
- property.SetValue(setting, obj);
- }
- } finally {
- innerSet = false;
- }
- loaded = true;
- }
- return setting;
- }
- }
- private static void Fsw_Changed(object sender, FileSystemEventArgs e) {
- loaded = false;
- }
- private static void Save() {
- var data = JsonConvert.SerializeObject(setting, Formatting.Indented);
- try {
- if (fsw != null) fsw.EnableRaisingEvents = false;
- File.WriteAllText(settingFile, data);
- } finally {
- if (fsw != null) fsw.EnableRaisingEvents = true;
- }
- loaded = true;
- }
- class SettingChangeInterceptor : StandardInterceptor {
- private ConcurrentDictionary<string, object> OrignalValues = new ConcurrentDictionary<string, object>();
- protected override void PreProceed(IInvocation invocation) {
- if (invocation.Method.Name.StartsWith("set_")) {
- var propertyName = invocation.Method.Name.Substring(4);
- var orignalValue = invocation.TargetType.GetMethod("get_" + propertyName).Invoke(invocation.Proxy, new object[] { });
- OrignalValues.AddOrUpdate(propertyName, orignalValue, (k, v) => orignalValue);
- }
- }
- protected override void PostProceed(IInvocation invocation) {
- if (!innerSet && invocation.Method.Name.StartsWith("set_")) {
- var propertyName = invocation.Method.Name.Substring(4);
- var orignalValue = OrignalValues[propertyName];
- if (orignalValue != invocation.GetArgumentValue(0)) {
- Save();
- }
- }
- }
- }
- }
- }
Add Comment
Please, Sign In to add comment