C#:嵌套的自定义配置在添加新属性后不起作用
C#: Nested custom config not working after adding a new attribute
在我想向嵌套配置元素之一添加新属性之前,我的嵌套自定义配置实现一直在工作 collection。这是我的工作配置:
<exchange name="myexchange">
<queue name="myqueue">
<process>
<sources>
<http url="[myUrl]/srcurl1" method="get" name="srcurl1" />
<http url="[myUrl]/srcurl2" method="get" name="srcurl2" />
</sources>
<destinations>
<http url="[intUrl]/someurl1" method="POST" name="someurl1" />
<http url="[intUrl]/someurl2" method="POST" name="someurl2" />
</destinations>
</process>
</queue>
</exchange>
我正在尝试将 isactive
属性添加到 <destinations>
配置元素 collection,但出现异常 Unrecognized attribute 'isactive'. Note that attribute names are case-sensitive.
。这就是我想要做的:
<destinations isactive="true">
<http url="[intUrl]/someurl1" method="POST" name="someurl1" />
<http url="[intUrl]/someurl2" method="POST" name="someurl2" />
</destinations>
这是我在添加新属性之前的工作代码。
public class ProcessConfigElement : ConfigurationElement
{
[ConfigurationProperty("sources", IsDefaultCollection = false)]
public HttpConfigElementCollection Sources
{
get { return (HttpConfigElementCollection)base["sources"]; }
}
[ConfigurationProperty("destinations", IsDefaultCollection = false)]
public HttpConfigElementCollection Destinations
{
get { return (HttpConfigElementCollection)base["destinations"]; }
}
}
public class HttpConfigElementCollection : ConfigurationElementCollection, IEnumerable<HttpConfigElement>
{
public new HttpConfigElement this[string name]
{
get
{
if (IndexOf(name) < 0) return null;
return (HttpConfigElement)BaseGet(name);
}
}
public HttpConfigElement this[int index]
{
get { return (HttpConfigElement)BaseGet(index); }
}
public int IndexOf(string name)
{
name = name.ToLower();
for (int idx = 0; idx < base.Count; idx++)
{
if (this[idx].Name.ToLower() == name)
return idx;
}
return -1;
}
public override ConfigurationElementCollectionType CollectionType
{
get { return ConfigurationElementCollectionType.BasicMap; }
}
protected override ConfigurationElement CreateNewElement()
{
return new HttpConfigElement();
}
protected override object GetElementKey(ConfigurationElement element)
{
return ((HttpConfigElement)element).Name;
}
protected override string ElementName
{
get { return "http"; }
}
public new IEnumerator<HttpConfigElement> GetEnumerator()
{
return this.OfType<HttpConfigElement>().GetEnumerator();
}
}
public class HttpConfigElement : ConfigurationElement
{
[ConfigurationProperty("url", IsRequired = true, DefaultValue = "")]
public string Url
{
get { return (string)this["url"]; }
set { this["url"] = value; }
}
[ConfigurationProperty("method", IsRequired = true, DefaultValue = "")]
public string Method
{
get { return (string)this["method"]; }
set { this["method"] = value; }
}
[ConfigurationProperty("name", IsRequired = true, IsKey = true, DefaultValue = "")]
public string Name
{
get { return (string)this["name"]; }
set { this["name"] = value; }
}
}
添加'isactive'属性。我将配置条目更改为:
<destinations isactive="true">
并认为我需要更改 ProcessConfigElement class 以使用新的 collection:
[ConfigurationProperty("destinations", IsDefaultCollection = false)]
public DestinationConfigElementCollection Destinations
{
get { return (DestinationConfigElementCollection)base["destinations"]; }
}
...我的 collection 和元素 class 看起来像:
public class DestinationConfigElementCollection : ConfigurationElementCollection, IEnumerable<DestinationConfigElement>
{
public DestinationConfigElementCollection()
{
DestinationConfigElement destinationConfigElement = (DestinationConfigElement)CreateNewElement();
if (destinationConfigElement.IsActive != "")
{
Add(destinationConfigElement);
}
}
public override ConfigurationElementCollectionType CollectionType
{
get
{
return ConfigurationElementCollectionType.BasicMap;
}
}
protected override ConfigurationElement CreateNewElement()
{
return new DestinationConfigElement();
}
protected override object GetElementKey(ConfigurationElement element)
{
return ((DestinationConfigElement)element).IsActive;
}
public DestinationConfigElement this[int index]
{
get
{
return (DestinationConfigElement)BaseGet(index);
}
set
{
if (BaseGet(index) != null)
{
BaseRemoveAt(index);
}
BaseAdd(index, value);
}
}
new public DestinationConfigElement this[string name]
{
get
{
return (DestinationConfigElement)BaseGet(name);
}
}
public int IndexOf(DestinationConfigElement destinationConfigElement)
{
return BaseIndexOf(destinationConfigElement);
}
public void Add(DestinationConfigElement destinationConfigElement)
{
BaseAdd(destinationConfigElement);
}
protected override void BaseAdd(ConfigurationElement element)
{
BaseAdd(element, false);
}
public void Remove(DestinationConfigElement destinationConfigElement)
{
if (BaseIndexOf(destinationConfigElement) >= 0)
BaseRemove(destinationConfigElement.IsActive);
}
public void RemoveAt(int index)
{
BaseRemoveAt(index);
}
public void Remove(string name)
{
BaseRemove(name);
}
public void Clear()
{
BaseClear();
}
protected override string ElementName
{
get { return "destination"; }
}
public new IEnumerator<DestinationConfigElement> GetEnumerator()
{
return this.OfType<DestinationConfigElement>().GetEnumerator();
}
}
public class DestinationConfigElement : ConfigurationElement
{
[ConfigurationProperty("isactive", IsRequired = false, IsKey = false, DefaultValue = "")]
public string IsActive
{
get { return (string)this["isactive"]; }
set { this["isactive"] = value; }
}
[ConfigurationProperty("https", IsDefaultCollection = false)]
public HttpConfigElementCollection Https
{
get { return (HttpConfigElementCollection)base["https"]; }
}
}
这没有用。我还尝试将配置更改为:
<destinations isactive="true">
<https>
<http url="[intUrl]/someurl1" method="POST" name="someurl1" />
<http url="[intUrl]/someurl2" method="POST" name="someurl2" />
</https>
</destinations>
我现在可以解决这个问题了。我认为在这里分享它是个好主意,这样如果我或任何人以后想回到这里。
问题出在我的 ProcessConfigElement class 中,我在其中使用 destinations
的集合。将其更改为使用使它起作用的元素。
public class ProcessConfigElement : ConfigurationElement
{
[ConfigurationProperty("sources", IsDefaultCollection = false)]
public HttpConfigElementCollection Sources
{
get { return (HttpConfigElementCollection)base["sources"]; }
}
[ConfigurationProperty("destinations", IsDefaultCollection = false)]
public DestinationConfigElement Destinations
{
get { return (DestinationConfigElement)base["destinations"]; }
}
}
...我还读到,在你有一个集合的地方构建你的配置是个好主意,然后用 in 元素。所以我添加了另一个嵌套级别 Endpoint
with in destinations
.
public class DestinationConfigElement : ConfigurationElement
{
[ConfigurationProperty("isactive", IsRequired = false, IsKey = false, DefaultValue = "")]
public string IsActive
{
get { return (string)this["isactive"]; }
set { this["isactive"] = value; }
}
[ConfigurationProperty("endpoints", IsDefaultCollection = false)]
public HttpConfigElementCollection Endpoints
{
get { return (HttpConfigElementCollection)base["endpoints"]; }
}
}
在我想向嵌套配置元素之一添加新属性之前,我的嵌套自定义配置实现一直在工作 collection。这是我的工作配置:
<exchange name="myexchange">
<queue name="myqueue">
<process>
<sources>
<http url="[myUrl]/srcurl1" method="get" name="srcurl1" />
<http url="[myUrl]/srcurl2" method="get" name="srcurl2" />
</sources>
<destinations>
<http url="[intUrl]/someurl1" method="POST" name="someurl1" />
<http url="[intUrl]/someurl2" method="POST" name="someurl2" />
</destinations>
</process>
</queue>
</exchange>
我正在尝试将 isactive
属性添加到 <destinations>
配置元素 collection,但出现异常 Unrecognized attribute 'isactive'. Note that attribute names are case-sensitive.
。这就是我想要做的:
<destinations isactive="true">
<http url="[intUrl]/someurl1" method="POST" name="someurl1" />
<http url="[intUrl]/someurl2" method="POST" name="someurl2" />
</destinations>
这是我在添加新属性之前的工作代码。
public class ProcessConfigElement : ConfigurationElement
{
[ConfigurationProperty("sources", IsDefaultCollection = false)]
public HttpConfigElementCollection Sources
{
get { return (HttpConfigElementCollection)base["sources"]; }
}
[ConfigurationProperty("destinations", IsDefaultCollection = false)]
public HttpConfigElementCollection Destinations
{
get { return (HttpConfigElementCollection)base["destinations"]; }
}
}
public class HttpConfigElementCollection : ConfigurationElementCollection, IEnumerable<HttpConfigElement>
{
public new HttpConfigElement this[string name]
{
get
{
if (IndexOf(name) < 0) return null;
return (HttpConfigElement)BaseGet(name);
}
}
public HttpConfigElement this[int index]
{
get { return (HttpConfigElement)BaseGet(index); }
}
public int IndexOf(string name)
{
name = name.ToLower();
for (int idx = 0; idx < base.Count; idx++)
{
if (this[idx].Name.ToLower() == name)
return idx;
}
return -1;
}
public override ConfigurationElementCollectionType CollectionType
{
get { return ConfigurationElementCollectionType.BasicMap; }
}
protected override ConfigurationElement CreateNewElement()
{
return new HttpConfigElement();
}
protected override object GetElementKey(ConfigurationElement element)
{
return ((HttpConfigElement)element).Name;
}
protected override string ElementName
{
get { return "http"; }
}
public new IEnumerator<HttpConfigElement> GetEnumerator()
{
return this.OfType<HttpConfigElement>().GetEnumerator();
}
}
public class HttpConfigElement : ConfigurationElement
{
[ConfigurationProperty("url", IsRequired = true, DefaultValue = "")]
public string Url
{
get { return (string)this["url"]; }
set { this["url"] = value; }
}
[ConfigurationProperty("method", IsRequired = true, DefaultValue = "")]
public string Method
{
get { return (string)this["method"]; }
set { this["method"] = value; }
}
[ConfigurationProperty("name", IsRequired = true, IsKey = true, DefaultValue = "")]
public string Name
{
get { return (string)this["name"]; }
set { this["name"] = value; }
}
}
添加'isactive'属性。我将配置条目更改为:
<destinations isactive="true">
并认为我需要更改 ProcessConfigElement class 以使用新的 collection:
[ConfigurationProperty("destinations", IsDefaultCollection = false)]
public DestinationConfigElementCollection Destinations
{
get { return (DestinationConfigElementCollection)base["destinations"]; }
}
...我的 collection 和元素 class 看起来像:
public class DestinationConfigElementCollection : ConfigurationElementCollection, IEnumerable<DestinationConfigElement>
{
public DestinationConfigElementCollection()
{
DestinationConfigElement destinationConfigElement = (DestinationConfigElement)CreateNewElement();
if (destinationConfigElement.IsActive != "")
{
Add(destinationConfigElement);
}
}
public override ConfigurationElementCollectionType CollectionType
{
get
{
return ConfigurationElementCollectionType.BasicMap;
}
}
protected override ConfigurationElement CreateNewElement()
{
return new DestinationConfigElement();
}
protected override object GetElementKey(ConfigurationElement element)
{
return ((DestinationConfigElement)element).IsActive;
}
public DestinationConfigElement this[int index]
{
get
{
return (DestinationConfigElement)BaseGet(index);
}
set
{
if (BaseGet(index) != null)
{
BaseRemoveAt(index);
}
BaseAdd(index, value);
}
}
new public DestinationConfigElement this[string name]
{
get
{
return (DestinationConfigElement)BaseGet(name);
}
}
public int IndexOf(DestinationConfigElement destinationConfigElement)
{
return BaseIndexOf(destinationConfigElement);
}
public void Add(DestinationConfigElement destinationConfigElement)
{
BaseAdd(destinationConfigElement);
}
protected override void BaseAdd(ConfigurationElement element)
{
BaseAdd(element, false);
}
public void Remove(DestinationConfigElement destinationConfigElement)
{
if (BaseIndexOf(destinationConfigElement) >= 0)
BaseRemove(destinationConfigElement.IsActive);
}
public void RemoveAt(int index)
{
BaseRemoveAt(index);
}
public void Remove(string name)
{
BaseRemove(name);
}
public void Clear()
{
BaseClear();
}
protected override string ElementName
{
get { return "destination"; }
}
public new IEnumerator<DestinationConfigElement> GetEnumerator()
{
return this.OfType<DestinationConfigElement>().GetEnumerator();
}
}
public class DestinationConfigElement : ConfigurationElement
{
[ConfigurationProperty("isactive", IsRequired = false, IsKey = false, DefaultValue = "")]
public string IsActive
{
get { return (string)this["isactive"]; }
set { this["isactive"] = value; }
}
[ConfigurationProperty("https", IsDefaultCollection = false)]
public HttpConfigElementCollection Https
{
get { return (HttpConfigElementCollection)base["https"]; }
}
}
这没有用。我还尝试将配置更改为:
<destinations isactive="true">
<https>
<http url="[intUrl]/someurl1" method="POST" name="someurl1" />
<http url="[intUrl]/someurl2" method="POST" name="someurl2" />
</https>
</destinations>
我现在可以解决这个问题了。我认为在这里分享它是个好主意,这样如果我或任何人以后想回到这里。
问题出在我的 ProcessConfigElement class 中,我在其中使用 destinations
的集合。将其更改为使用使它起作用的元素。
public class ProcessConfigElement : ConfigurationElement
{
[ConfigurationProperty("sources", IsDefaultCollection = false)]
public HttpConfigElementCollection Sources
{
get { return (HttpConfigElementCollection)base["sources"]; }
}
[ConfigurationProperty("destinations", IsDefaultCollection = false)]
public DestinationConfigElement Destinations
{
get { return (DestinationConfigElement)base["destinations"]; }
}
}
...我还读到,在你有一个集合的地方构建你的配置是个好主意,然后用 in 元素。所以我添加了另一个嵌套级别 Endpoint
with in destinations
.
public class DestinationConfigElement : ConfigurationElement
{
[ConfigurationProperty("isactive", IsRequired = false, IsKey = false, DefaultValue = "")]
public string IsActive
{
get { return (string)this["isactive"]; }
set { this["isactive"] = value; }
}
[ConfigurationProperty("endpoints", IsDefaultCollection = false)]
public HttpConfigElementCollection Endpoints
{
get { return (HttpConfigElementCollection)base["endpoints"]; }
}
}