在.NET中创建2级(而不是3级)自定义配置部分

时间:2011-10-19 08:12:03

标签: .net visual-studio configuration customization

我知道有很多关于创建自定义配置部分的链接,之前已经提到了数十个相关问题。但我无法解决我的问题。

我可以创建自定义配置部分,如:

  <publicPaths>
    <paths>
      <add name="ProductServices" address="/services/productservices.asmx" />
      <add name="LoginByToken" address="LoginByToken.ashx" />
    </paths>
  </publicPaths>

但是,如您所见,此配置部分(添加到其中的项目)的满足处于第3个嵌套级别。换句话说,您应该遍历publicPaths -> paths -> add以获取表示该项目的元素。但我想要的是一个2级嵌套,如:

    <paths>
      <add name="ProductServices" address="/services/productservices.asmx" />
      <add name="LoginByToken" address="LoginByToken.ashx" />
    </paths>

我该怎么办?

更新:我的3级自定义配置部分的代码是:

public class PublicPaths : ConfigurationSection
{
    private static PublicPaths publicPaths = ConfigurationManager.GetSection("publicPaths") as PublicPaths;

    public static PublicPaths Instance
    {
        get { return publicPaths; }
    }

    [ConfigurationProperty("paths", IsRequired = false)]
    public PathCollection Paths
    {
        get { return this["paths"] as PathCollection; }
    }
}

public class PathCollection : ConfigurationElementCollection
{
    public Path this[int index]
    {
        get { return base.BaseGet(index) as Path; }
        set
        {
            if (base.BaseGet(index) != null)
            {
                base.BaseRemoveAt(index);
            }
            base.BaseAdd(index, value);
        }
    }

    protected override ConfigurationElement CreateNewElement()
    {
        return new Path();
    }

    protected override object GetElementKey(ConfigurationElement element)
    {
        return ((Path)element).Name;
    }
}

public class Path : ConfigurationElement
{
    [ConfigurationProperty("name", IsRequired = true, IsKey = true)]
    public string Name
    {
        get { return (string)this["name"]; }
        set { this["name"] = value; }
    }

    [ConfigurationProperty("address", IsRequired = true)]
    public string Address
    {
        get { return (string)this["address"]; }
        set { this["address"] = value; }
    }
}

1 个答案:

答案 0 :(得分:1)

您可以尝试使用此代码(它应该可以使用)。

public class PublicPaths : ConfigurationSection
{
    [ConfigurationProperty("", IsRequired = false, IsKey = false, IsDefaultCollection = true)]
    public PathCollection Items
    {
        get { return ((PathCollection)(base[""])); }
        set { base[""] = value; }
    } 
}

[ConfigurationCollection(typeof(Path), CollectionType = ConfigurationElementCollectionType.BasicMapAlternate)]
public class PathCollection : ConfigurationElementCollection
{
    internal const string ItemPropertyName = "add";

    public override ConfigurationElementCollectionType CollectionType
    {
        get { return ConfigurationElementCollectionType.BasicMapAlternate; }
    }

    protected override string ElementName
    {
        get { return ItemPropertyName; }
    }

    protected override bool IsElementName(string elementName)
    {
        return (elementName == ItemPropertyName);
    }

    protected override object GetElementKey(ConfigurationElement element)
    {
        return ((Path)element).Name;
    }

    protected override ConfigurationElement CreateNewElement()
    {
        return new Path();
    }

    public override bool IsReadOnly()
    {
        return false;
    }

} 

public class Path : ConfigurationElement
{
    [ConfigurationProperty("name", IsRequired = true, IsKey = true)]
    public string Name
    {
        get { return (string)this["name"]; }
        set { this["name"] = value; }
    }

    [ConfigurationProperty("address", IsRequired = true)]
    public string Address
    {
        get { return (string)this["address"]; }
        set { this["address"] = value; }
    }
}

使用此配置

<configuration>
  <configSections>
        <section name="publicPaths" type="{type}, {namespace}" />
  </configSections> 
  <publicPaths>    
      <add name="ProductServices" address="/services/productservices.asmx" />
      <add name="LoginByToken" address="LoginByToken.ashx" />    
 </publicPaths>
</configuration>

然后,您可以通过

访问这些值
    var config = ConfigurationManager.GetSection("publicPaths") as PublicPaths;

    foreach (Path s in config.Items)
    {
     //print   
    }