c# - net - Configuración personalizada, ConfigurationElements y ConfigurationProperties
custom section name (5)
Las 2 cosas en las que puedo pensar fuera de la cabeza sería usar un DefaultValue, así:
[ConfigurationProperty("customsettingitem", DefaultValue = -1)]
public int CustomSettingItem { get { return (int)this["customsettingitem"]; } }
Suponiendo que hay algún valor que no es válido. En este caso, CustomSettingItem == -1 significa que wasnt set, y> = 0 era un valor establecido en config. Por supuesto, eso supone que -1 no era una entrada válida en primer lugar.
La segunda idea es usar un int nullable en su lugar:
[ConfigurationProperty("customsettingitem", IsRequired = false)]
public int? CustomSettingItem { get { return (int?)this["customsettingitem"]; } }
Ahora bien, si nada está configurado en config, debería ser nulo en lugar de 0.
Estuve revisando la red durante los últimos 3 días y no puedo encontrar ninguna referencia a esta pregunta. Creé una clase de configuración personalizada para usar con mi app.config. Todo funciona bien El problema aparece cuando una propiedad de configuración (de un elemento de configuración) no es necesaria y no está definida en el archivo app.config. Parece que se devuelven valores predeterminados para la propiedad de configuración. ¿Alguien sabe cómo determinar si la propiedad no está definida en la aplicación.config? (He estado intentando publicar mi app.config, pero no puedo entender cómo hacerlo ... ¿Alguien sabe cómo?)
//Main
namespace TestStub
{
class Program
{
static void Main(string[] args)
{
CustomSettingsHandler config = (CustomSettingsHandler)ConfigurationManager.GetSection("CustomSettingsManager");
Console.WriteLine("Setting1 {0}", config.Setting1.CustomSettingItem);
Console.WriteLine("Setting2 {0}", config.Setting2.CustomSettingItem);
}
}
}
//Custom Configuration Class
namespace CustomConfiguration
{
public class CustomSettingsHandler : ConfigurationSection
{
[ConfigurationProperty("setting1", IsRequired = false)]
public CustomSettingElement Setting1 { get { return (CustomSettingElement)this["setting1"]; } }
[ConfigurationProperty("setting2", IsRequired = false)]
public CustomSettingElement Setting2 { get { return (CustomSettingElement)this["setting2"]; } }
}
public class CustomSettingElement : ConfigurationElement
{
[ConfigurationProperty("customsettingitem", IsRequired = false)]
public int CustomSettingItem { get { return (int)this["customsettingitem"]; } }
}
}
Hasta ahora no he podido decir que una propiedad sea nula si no está definida en el archivo de configuración. Parece que en su sabiduría infinita, Microsoft decidió que realmente quiere decir String.Empty o nuevo ConfigurationElement () cuando escribe null.
La forma en que lo estoy resolviendo actualmente es así:
bool _hasProp = true;
protected override object OnRequiredPropertyNotFound(string name)
{
if (name == "prop")
{
_hasProp = false;
return null; // note that this will still not make prop null
}
return base.OnRequiredPropertyNotFound(name);
}
[ConfigurationProperty("prop", IsRequired = true)]
public string Prop
{
get { return _hasProp ? (string) this["prop"] : null; }
}
Es un truco y marcará erróneamente la propiedad según se requiera. Si está usando una herramienta para editar su archivo de configuración, no le gustará esto.
Encontré que la mejor manera es anular ConfigurationSection.PostDeserialize()
y verificar la propiedad IsPresent
de cada miembro de la sección que se deriva de ConfigurationElement
.
public class CustomSettingsHandler : ConfigurationSection
{
// ...
protected override void PostDeserialize()
{
foreach (ConfigurationProperty property in Properties)
{
var configElement = this[property] as ConfigurationElement;
if (configElement != null
&& !configElement.ElementInformation.IsPresent)
{
this[property] = null;
}
}
base.PostDeserialize();
}
}
Cada ConfigurationElement
que no se haya leído desde el archivo de configuración será null
después.
Pruebe lo siguiente:
configElement.ElementInformation.Properties[propName].ValueOrigin =
PropertyValueOrigin.SetHere
La propiedad ValueOrigin
le dice de dónde proviene el valor.
También puede verificar usando lo siguiente:
config.Setting1.CustomSettingItem.ElementInformation.IsPresent
le dará falso si no se encuentra en su archivo de configuración.