¿Hay alguna manera de cargar la configuración de un archivo diferente que no sea el archivo predeterminado App.config
en tiempo de ejecución? Me gustaría hacer esto después de que se cargue el archivo de configuración predeterminado.Cargando Properties.Settings de un archivo diferente en tiempo de ejecución
Uso la interfaz gráfica de usuario Settings.Settings
en Visual Studio para crear mi archivo App.config
para mí. El archivo de configuración termina pareciéndose a esto:
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<configSections>
<sectionGroup name="applicationSettings" type="System.Configuration.ApplicationSettingsGroup, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" >
<section name="SnipetTester.Properties.Settings" type="System.Configuration.ClientSettingsSection, System, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
</sectionGroup>
</configSections>
<applicationSettings>
<SnipetTester.Properties.Settings>
<setting name="SettingSomething" serializeAs="String">
<value>1234</value>
</setting>
</SnipetTester.Properties.Settings>
</applicationSettings>
</configuration>
En el código, que soy capaz de acceder a la configuración de la siguiente manera:
Console.WriteLine("Default setting value: " + Properties.Settings.Default.SettingSomething);
La idea es que cuando se ejecuta la aplicación, que debería estar capaz de especificar un archivo de configuración en tiempo de ejecución y hacer que la aplicación cargue el archivo de configuración en el objeto Properties.Settings.Default
en lugar de usar el archivo predeterminado app.config
. Los formatos de los archivos de configuración serían los mismos, pero los valores de la configuración serían diferentes.
Yo sé de una manera de hacer esto con el ConfigurationManager.OpenExeConfiguration(configFile);
. Sin embargo, en las pruebas que he ejecutado, no actualiza el objeto Properties.Settings.Default
para reflejar los nuevos valores del archivo de configuración.
Después de pensar en esto un poco más de tiempo, he podido encontrar una solución que me gusta un poco mejor. Estoy seguro de que tiene algunos inconvenientes, pero creo que funcionará para lo que necesito que haga.
Esencialmente, la clase Properties.Settings
se genera automáticamente por Visual Studio; genera el código para la clase para ti. Pude encontrar dónde se generó el código y agregar algunas llamadas a funciones para cargar un archivo de configuración por sí mismo. Aquí está mi además:
internal sealed partial class Settings : global::System.Configuration.ApplicationSettingsBase
{
//Parses a config file and loads its settings
public void Load(string filename)
{
System.Xml.Linq.XElement xml = null;
try
{
string text = System.IO.File.ReadAllText(filename);
xml = System.Xml.Linq.XElement.Parse(text);
}
catch
{
//Pokemon catch statement (gotta catch 'em all)
//If some exception occurs while loading the file,
//assume either the file was unable to be read or
//the config file is not in the right format.
//The xml variable will be null and none of the
//settings will be loaded.
}
if(xml != null)
{
foreach(System.Xml.Linq.XElement currentElement in xml.Elements())
{
switch (currentElement.Name.LocalName)
{
case "userSettings":
case "applicationSettings":
foreach (System.Xml.Linq.XElement settingNamespace in currentElement.Elements())
{
if (settingNamespace.Name.LocalName == "SnipetTester.Properties.Settings")
{
foreach (System.Xml.Linq.XElement setting in settingNamespace.Elements())
{
LoadSetting(setting);
}
}
}
break;
default:
break;
}
}
}
}
//Loads a setting based on it's xml representation in the config file
private void LoadSetting(System.Xml.Linq.XElement setting)
{
string name = null, type = null, value = null;
if (setting.Name.LocalName == "setting")
{
System.Xml.Linq.XAttribute xName = setting.Attribute("name");
if (xName != null)
{
name = xName.Value;
}
System.Xml.Linq.XAttribute xSerialize = setting.Attribute("serializeAs");
if (xSerialize != null)
{
type = xSerialize.Value;
}
System.Xml.Linq.XElement xValue = setting.Element("value");
if (xValue != null)
{
value = xValue.Value;
}
}
if (string.IsNullOrEmpty(name) == false &&
string.IsNullOrEmpty(type) == false &&
string.IsNullOrEmpty(value) == false)
{
switch (name)
{
//One of the pitfalls is that everytime you add a new
//setting to the config file, you will need to add another
//case to the switch statement.
case "SettingSomething":
this[name] = value;
break;
default:
break;
}
}
}
}
El código añadí expone una función Properties.Settings.Load(string filename)
. La función acepta un nombre de archivo config como parámetro. Analizará el archivo y cargará cualquier configuración que encuentre en el archivo de configuración. Para volver a la configuración original, simplemente llame al Properties.Settings.Reload()
.
¡Espero que esto ayude a otra persona!
esto parece muy prometedor, pero ¿cómo podemos utilizar los tipos – tofutim