[英]How to change location of app.config
我想更改应用程序查找app.config文件的位置。
我知道我可以使用ConfigurationManager.OpenExeConfiguration()来访问任意配置文件 - 但是,当.Net Framework读取配置文件(例如,对于ConnectionStrings或EventSources)时,它将查看默认位置。 我想实际更改整个.Net Framework的位置(当然,对于我的应用程序)。
我也知道我可以使用AppDomainSetup来更改app.config的位置以用于新的AppDomain。 但是,这不适用于应用程序的主AppDomain。
我也知道我可以覆盖函数Main()并创建一个新的AppDomain,并在新的AppDomain中运行我的应用程序。 但是,这有其他副作用 - 例如,Assembly.GetEntryAssembly()将返回空引用。
鉴于.Net中其他所有工作方式,我希望有一些方法来配置我的应用程序的启动环境 - 通过应用程序清单,或者其他一些 - 但我一直无法在这个方向找到一线希望。
任何指针都会有所帮助。
大卫穆林
我使用该方法从Main()启动另一个AppDomain,指定配置文件的“新”位置。
GetEntryAssembly()没有问题; 当从非托管代码调用时它只返回null - 或者至少它不适合我,因为我使用ExecuteAssembly()来创建/运行第二个AppDomain,就像这样:
int Main(string[] args)
{
string currentExecutable = Assembly.GetExecutingAssembly().Location;
bool inChild = false;
List<string> xargs = new List<string>();
foreach (string arg in xargs)
{
if (arg.Equals("-child"))
{
inChild = true;
}
/* Parse other command line arguments */
else
{
xargs.Add(arg);
}
}
if (!inChild)
{
AppDomainSetup info = new AppDomainSetup();
info.ConfigurationFile = /* Path to desired App.Config File */;
Evidence evidence = AppDomain.CurrentDomain.Evidence;
AppDomain domain = AppDomain.CreateDomain(friendlyName, evidence, info);
xargs.Add("-child"); // Prevent recursion
return domain.ExecuteAssembly(currentExecutable, evidence, xargs.ToArray());
}
// Execute actual Main-Code, we are in the child domain with the custom app.config
return 0;
}
请注意,我们正在有效地重新运行EXE,就像AppDomain和不同的配置一样。 另请注意,您需要有一些“魔法”选项,以防止这种情况无休止地进行。
我从一个更大的(真实的)代码块中精心设计出来,所以它可能无法正常工作,但应该说明这个概念。
var configPath = YOUR_PATH;
if (!Directory.Exists(ProductFolder))
{
Directory.CreateDirectory(ProductFolder);
}
if (!File.Exists(configPath))
{
File.WriteAllText(configPath, Resources.App);
}
var map = new ExeConfigurationFileMap
{
ExeConfigFilename = configPath,
LocalUserConfigFilename = configPath,
RoamingUserConfigFilename = configPath
};
Configuration config = ConfigurationManager.OpenMappedExeConfiguration(map, ConfigurationUserLevel.None);
然后根据需要使用config成员。
我不确定您为什么要更改配置文件的位置 - 也许可以有不同的方法来解决您的实际问题。 我有一个要求,我希望在相关应用程序之间共享配置文件 - 我选择使用自己的xml文件,因为它给了我完全控制架构的额外好处。
在您的情况下,可以使用configSource属性将配置文件的各个部分外部化为单独的文件。 见这里下的“使用外部配置文件”,以检查它如何被用于连接字符串部分完成。 也许,这可能会对你有所帮助。
另一种方法是将配置文件保留为可执行文件,并将相关的可更改部分移动到外部xml文件,这些文件可以位于您选择的任何位置。
如果您以只读容量使用配置文件,则可以使用XML Inlcude将相关块添加到位于其他位置的XML文件中。 如果您尝试使用Configuration.Save方法将值直接写回app.config,则此方法无效。
的app.config:
<?xml version="1.0"?> <configuration xmlns:xi="http://www.w3.org/2001/XInclude"> <appSettings> <xi:include href="AppSettings.xml"/> </appSettings> <connectionStrings> <xi:include href="ConnectionStrings.xml"/> </connectionStrings> <startup><supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7"/></startup> </configuration>
ConnectionStrings.xml:
<?xml version="1.0"?> <add name="Example1ConnectionString" connectionString="Data Source=(local)\\SQLExpress;Initial Catalog=Example1DB;Persist Security Info=True;User ID=sa;Password=password" providerName="System.Data.SqlClient" /> <add name="Example2ConnectionString" connectionString="Data Source=(local)\\SQLExpress;Initial Catalog=Example2DB;Persist Security Info=True;User ID=sa;Password=password" providerName="System.Data.SqlClient" />
AppSettings.xml:
<?xml version="1.0"?> <add key="Setting1" value="Value1"/> <add key="Setting2" value="Value2"/>
文件URI如下所示:
file:///C:/whatever.txt
您甚至可以定义故障转移文件,以防您尝试引用的文件丢失。 此模式来自https://www.xml.com/pub/a/2002/07/31/xinclude.html :
<xi:include href="http://www.whitehouse.gov/malapropisms.xml"> <xi:fallback> <para> This administration is doing everything we can to end the stalemate in an efficient way. We're making the right decisions to bring the solution to an end. </para> </xi:fallback>
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.