zoukankan      html  css  js  c++  java
  • 自定义ConfigurationSection,创建多个嵌套的ConfigurationElementCollection节点

    由于接口地址都是固定的,所以想到使用自定义节点,来将接口都配置到web.config中。

    很快,v1.0版本出炉: 

    public class RequestConfigSection : ConfigurationSection
        {
            [ConfigurationProperty("sources", IsDefaultCollection = true)]
            [ConfigurationCollection(typeof(RequestConfigSourceCollection), AddItemName = "add")]
            public RequestConfigSourceCollection ConfigCollection
            {
                get { return (RequestConfigSourceCollection)this["sources"]; }
                set { this["sources"] = value; }
            }
        }
        
        public class RequestConfigSourceCollection : ConfigurationElementCollection
        {
            /// <summary>
            /// 创建新元素
            /// </summary>
            /// <returns></returns>
            protected override ConfigurationElement CreateNewElement()
            {
                return new RequestConfigSource();
            }
    
            /// <summary>
            /// 获取元素的键
            /// </summary>
            /// <param name="element"></param>
            /// <returns></returns>
            protected override object GetElementKey(ConfigurationElement element)
            {
                return ((RequestConfigSource)element).Name;
            }
    
            /// <summary>
            /// 获取所有键
            /// </summary>
            public IEnumerable<string> AllKeys { get { return BaseGetAllKeys().Cast<string>(); } }
    
            /// <summary>
            /// 索引器
            /// </summary>
            /// <param name="name"></param>
            /// <returns></returns>
            public new RequestConfigSource this[string name]
            {
                get { return (RequestConfigSource)BaseGet(name); }
            }
        }
    
        public class RequestConfigSource : ConfigurationElement
        {
            /// <summary>
            /// 名称
            /// </summary>
            [ConfigurationProperty("name")]
            public string Name
            {
                get { return (string)this["name"]; }
                set { this["name"] = value; }
            }
    
            /// <summary>
            /// 地址
            /// </summary>
            [ConfigurationProperty("url")]
            public string Url
            {
                get { return (string)this["url"]; }
                set { this["url"] = value; }
            }
    
            /// <summary>
            /// 访问类型
            /// </summary>
            [ConfigurationProperty("type")]
            public RequestType RequestType
            {
                get
                {
                    return (RequestType)Enum.Parse(typeof(RequestType), this["type"].ToString(), true);
                }
                set { this["type"] = value; }
            }
        }
    

    在web.config中的配置方式为:

    <apiRequestConfig>
      <sources>
        <add name="..." url="..." type="POST" />
        <add name="..." url="..." type="POST" />
        <add name="..." url="..." type="POST" />
      </sources>
    </apiRequestConfig>
    

     这时候又看了一遍需求文档,发现有说明不同平台的接口地址是不一样的,但接口做的事情是一样的。

    然后就开始想,如果接着在下边追加,则不同平台的同一接口的名称是不能相同的。

    所以想到的理想的配置方式为:

    <apiRequestConfig>
      <sources platform="android">
        <add name="..." url="..." type="POST" />
        <add name="..." url="..." type="POST" />
        <add name="..." url="..." type="POST" />
      </sources>
      <sources platform="ios">
        <add name="..." url="..." type="POST" />
        <add name="..." url="..." type="POST" />
        <add name="..." url="..." type="POST" />
      </sources>
    </apiRequestConfig>
    

     但是sources 名称的节点只能出现一次…好吧,蛋疼了。

    研究尝试了一上午也没有找到合适的解决方式,又懒得再重新写一套代码来读取XML,…开始在网上搜解决方案

    用中文做关键字找不着…翻了墙,用英文来当关键字 one or more ConfigurationElementCollection…

    最终在一老外的博客里找到了一个替代的解决方案,最终的配置为:

    <apiRequestConfig>
        <requestConfigs>
          <request platform="android">
            <sources>
              <add name="..." url="..." type="POST" />
              <add name="..." url="..." type="POST" />
              <add name="..." url="..." type="POST" />
            </sources>
          </request>
          <request platform="ios">
            <sources>
              <add name="..." url="..." type="POST" />
              <add name="..." url="..." type="POST" />
              <add name="..." url="..." type="POST" />
            </sources>
          </request>
        </requestConfigs>
      </apiRequestConfig>
    

    C#代码如下:

    public class RequestConfigSection : ConfigurationSection
        {
            [ConfigurationProperty("requestConfigs", IsDefaultCollection = true)]
            [ConfigurationCollection(typeof(RequestConfigTypeCollection), AddItemName = "request")]
            public RequestConfigTypeCollection ConfigCollection
            {
                get { return (RequestConfigTypeCollection)this["requestConfigs"]; }
                set { this["requestConfigs"] = value; }
            }
    
            /// <summary>
            /// 根据平台和名称获取请求配置信息
            /// </summary>
            /// <param name="name"></param>
            /// <param name="platform"></param>
            /// <returns></returns>
            public RequestConfigSource GetRequestConfigSource(string platform, string name)
            {
                return ConfigCollection[platform].SourceCollection[name];
            }
        }
    
        public class RequestConfigTypeCollection : ConfigurationElementCollection
        {
            /// <summary>
            /// 创建新元素
            /// </summary>
            /// <returns></returns>
            protected override ConfigurationElement CreateNewElement()
            {
                return new RequestConfigType();
            }
    
            /// <summary>
            /// 获取元素的键
            /// </summary>
            /// <param name="element"></param>
            /// <returns></returns>
            protected override object GetElementKey(ConfigurationElement element)
            {
                return ((RequestConfigType)element).Platform;
            }
    
            /// <summary>
            /// 获取所有键
            /// </summary>
            public IEnumerable<string> AllKeys { get { return BaseGetAllKeys().Cast<string>(); } }
    
            /// <summary>
            /// 索引器
            /// </summary>
            /// <param name="name"></param>
            /// <returns></returns>
            public new RequestConfigType this[string platform]
            {
                get { return (RequestConfigType)BaseGet(platform); }
            }
        }
    
        public class RequestConfigType : ConfigurationElement
        {
            /// <summary>
            /// 获取全部请求配置信息
            /// </summary>
            /// <returns></returns>
            public RequestConfigSource[] GetAllRequestSource()
            {
                var keys = this.SourceCollection.AllKeys;
    
                return keys.Select(name => this.SourceCollection[name]).ToArray();
            }
            /// <summary>
            /// 平台标识
            /// </summary>
            [ConfigurationProperty("platform")]
            public string Platform
            {
                get { return (string)this["platform"]; }
                set { this["platform"] = value; }
            }
    
            [ConfigurationProperty("sources", IsDefaultCollection = true)]
            [ConfigurationCollection(typeof(RequestConfigSourceCollection), AddItemName = "add")]
            public RequestConfigSourceCollection SourceCollection
            {
                get { return (RequestConfigSourceCollection)this["sources"]; }
                set { this["sources"] = value; }
            }
        }
    
        public class RequestConfigSourceCollection : ConfigurationElementCollection
        {
            /// <summary>
            /// 创建新元素
            /// </summary>
            /// <returns></returns>
            protected override ConfigurationElement CreateNewElement()
            {
                return new RequestConfigSource();
            }
    
            /// <summary>
            /// 获取元素的键
            /// </summary>
            /// <param name="element"></param>
            /// <returns></returns>
            protected override object GetElementKey(ConfigurationElement element)
            {
                return ((RequestConfigSource)element).Name;
            }
    
            /// <summary>
            /// 获取所有键
            /// </summary>
            public IEnumerable<string> AllKeys { get { return BaseGetAllKeys().Cast<string>(); } }
    
            /// <summary>
            /// 索引器
            /// </summary>
            /// <param name="name"></param>
            /// <returns></returns>
            public new RequestConfigSource this[string name]
            {
                get { return (RequestConfigSource)BaseGet(name); }
            }
        }
    
        /// <summary>
        /// 请求的配置信息
        /// </summary>
        public class RequestConfigSource : ConfigurationElement
        {
            /// <summary>
            /// 名称
            /// </summary>
            [ConfigurationProperty("name")]
            public string Name
            {
                get { return (string)this["name"]; }
                set { this["name"] = value; }
            }
    
            /// <summary>
            /// 地址
            /// </summary>
            [ConfigurationProperty("url")]
            public string Url
            {
                get { return (string)this["url"]; }
                set { this["url"] = value; }
            }
    
            /// <summary>
            /// 访问类型
            /// </summary>
            [ConfigurationProperty("type")]
            public RequestType RequestType
            {
                get
                {
                    return (RequestType)Enum.Parse(typeof(RequestType), this["type"].ToString(), true);
                }
                set { this["type"] = value; }
            }
        }
    

    本人的开发环境为 .net framework 4.0

    最初RequestConfigSection 类中的ConfigCollection 和  RequestConfigType 类中的SourceCollection  没有定义ConfigurationCollection特性

    而是在RequestConfigTypeCollectionRequestConfigTypeCollection 中重载了ElementName属性,返回子级的节点名。

    结果抛出节点名未定义的异常…

    改由特性ConfigurationCollection定义,并给特性属性AddItemName赋值为子级的节点名 解决…

  • 相关阅读:
    Maven 集成Tomcat插件
    dubbo 序列化 问题 属性值 丢失 ArrayList 解决
    docker 中安装 FastDFS 总结
    docker 从容器中拷文件到宿主机器中
    db2 相关命令
    Webphere WAS 启动
    CKEDITOR 4.6.X 版本 插件 弹出对话框 Dialog中 表格 Table 自定义样式Style 问题
    SpringMVC JSONP JSON支持
    CKEDITOR 3.4.2中 按钮事件中 动态改变图标和title 获取按钮
    git回退到远程某个版本
  • 原文地址:https://www.cnblogs.com/amylis_chen/p/6000654.html
Copyright © 2011-2022 走看看