XMLCache.cs 7.8 KB
using log4net;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Reflection;
using System.Text;
 
using System.Xml;
namespace OnlineStore.Common
{
    public class XMLCache<T>
    {
        public static readonly ILog LOGGER = LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType);
        public static Dictionary<string, Dictionary<int, T>> xmlCache = new Dictionary<string, Dictionary<int, T>>();

        public static Dictionary<int, T> getAllData(Type type)
        {

            if (!xmlCache.ContainsKey(type.Name))
            {
                if (type == null)
                {
                    return null;
                }

                loadXml(type);

            }

            Dictionary<int, T> allData = xmlCache[type.Name];
            return allData;


        }

        private static Dictionary<int, T> loadXml(Type type)
        {
            string className = type.Name;
            Dictionary<int, T> data = new Dictionary<int, T>();

            // Type type = Assembly.Load("testTool.xml." + className).GetType();
            string nodeName = className.Substring(0, className.Length - 3);
            string parNodeName = nodeName + "Info";
            string xmlName = className.Substring(0, className.Length - 3) + "Info.xml";
            XmlDocument xmlDoc = new XmlDocument();

            string xmlPath = System.Windows.Forms.Application.StartupPath + @"\data\";
            xmlDoc.Load(xmlPath + xmlName);

            XmlNode parNode = xmlDoc.SelectSingleNode(parNodeName);
            XmlNodeList xmlNodeList = parNode.ChildNodes;

            for (int i = 0; i < xmlNodeList.Count; i++)
            {
                XmlNode node = xmlNodeList.Item(i);
                XmlAttributeCollection collo = node.Attributes;
                XmlAttribute[] list = new XmlAttribute[collo.Count];
                collo.CopyTo(list, 0);


                var bllIns = type.Assembly.CreateInstance(type.FullName);

                //取得属性集合
                PropertyInfo[] props = type.GetProperties();
                int id = 0;
                foreach (XmlAttribute xmlA in list)
                {
                    try
                    {
                        var prop = props.First(c => c.Name == xmlA.Name);//获取同名属性
                        if (prop != null)
                        {//如果属性存在
                            prop.SetValue(bllIns, Convert.ChangeType(xmlA.Value, prop.PropertyType), null);//赋值****在这里需要考虑类型问题
                        }

                        if (xmlA.Name.Equals("id"))
                        {
                            id = int.Parse(xmlA.Value);
                        }
                    }
                    catch (Exception ex)
                    {
                        LogUtil.error(LOGGER, "出现错误:" + ex.Message);
                    }
                }
                if (!data.ContainsKey(id))
                {
                    data.Add(id, (T)bllIns);
                }
            }
            xmlCache.Add(className, data);

            return data;
        }

        internal static T getXmlById(Type type, int id)
        {
            if (!xmlCache.ContainsKey(type.Name))
            {
                if (type == null)
                {
                    return default(T);
                }

                loadXml(type);

            }

            Dictionary<int, T> allData = xmlCache[type.Name];
            if (!allData.ContainsKey(id))
            {
                System.Windows.Forms.MessageBox.Show("找不到ID=" + id + "的" + type.Name);
            }

            return allData[id];

        }

        public static void SaveXml(Type type, XmlData mo)
        {
            string className = type.Name;
            //判断xml是否已经存在
            string xmlName = className.Substring(0, className.Length - 3) + "Info.xml";
            XmlDocument xmlDoc = new XmlDocument();

            string xmlPath = System.Windows.Forms.Application.StartupPath + @"\data\";
            xmlDoc.Load(xmlPath + xmlName);
            string nodeName = className.Substring(0, className.Length - 3);
            string parNodeName = nodeName + "Info";
            XmlNode parNode = xmlDoc.SelectSingleNode(parNodeName);
            XmlNodeList xmlNodeList = parNode.ChildNodes;
            //新增
            if (mo.id == 0)
            {

                Dictionary<int, T> dic = getAllData(type);
                int id = 0;
                foreach (int key in dic.Keys)
                {
                    if (key >= id)
                    {
                        id = key + 1;
                    }
                }
                mo.id = id;
                XmlNode node = xmlNodeList.Item(xmlNodeList.Count - 1);
                XmlNode newNode = node.CloneNode(true);
                XmlAttributeCollection collo = node.Attributes;
                XmlAttribute[] list = new XmlAttribute[collo.Count];
                collo.CopyTo(list, 0);
                //取得属性集合 
                PropertyInfo[] props = type.GetProperties();
                //  parNode.RemoveChild(node);
                foreach (XmlAttribute xmlA in list)
                {
                    var prop = props.First(c => c.Name == xmlA.Name);//获取同名属性
                    if (prop != null)
                    {
                        node.Attributes.Remove(xmlA);

                        xmlA.Value = prop.GetValue(mo,null).ToString();
                        node.Attributes.Append(xmlA);
                    }
                }
                parNode.InsertBefore(newNode, node);
            }
            //修改
            else
            {
                xmlCache[className].Remove(mo.id);
                for (int i = 0; i < xmlNodeList.Count; i++)
                {
                    XmlNode node = xmlNodeList.Item(i);
                    XmlAttributeCollection collo = node.Attributes;
                    XmlAttribute[] list = new XmlAttribute[collo.Count];
                    collo.CopyTo(list, 0);

                    bool isRight = false;
                    foreach (XmlAttribute xmlA in list)
                    {
                        try
                        {
                            if (xmlA.Name.Equals("id"))
                            {
                                int id = int.Parse(xmlA.Value);
                                if (id.Equals(mo.id))
                                {
                                    isRight = true;
                                }
                                break;
                            }
                        }
                        catch (Exception ex)
                        {
                            LogUtil.error(LOGGER, "出现错误:" + ex.StackTrace);
                        }
                    }
                    if (isRight)
                    {  //取得属性集合 
                        PropertyInfo[] props = type.GetProperties();
                        //  parNode.RemoveChild(node);
                        foreach (XmlAttribute xmlA in list)
                        {
                            var prop = props.First(c => c.Name == xmlA.Name);//获取同名属性
                            if (prop != null)
                            {
                                node.Attributes.Remove(xmlA);

                                xmlA.Value = prop.GetValue(mo, null).ToString();
                                node.Attributes.Append(xmlA);
                            }
                        }

                        parNode.ReplaceChild(node, node);
                        break;
                    }

                }

            }
            xmlDoc.Save(xmlPath + xmlName);

            xmlCache[className].Add(mo.id, (T)(object)mo);
        }
    }


}