Paul Michaels
Paul Michaels

Reputation: 16705

RefreshSection not working as expected

I'm trying to update the app.config file for a running application. The update does work (that is, the file gets updated), but when I re-read the file, it shows the old value. The answer to this question does imply that the app.config is cached, but that calling RefreshSection should force a re-read.

Here's the app.config (straight from an MS example):

<configuration>      
    <startup> 
        <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5.2" />
    </startup>
    <system.serviceModel>  
        <bindings>  
            <wsHttpBinding>  
                <binding name="WSHttpBinding_ICalculator" />  
            </wsHttpBinding>  
        </bindings>  
        <client>  
            <endpoint address="http://localhost:8000/ServiceModelSamples/Service/CalculatorService"  
                binding="wsHttpBinding" bindingConfiguration="WSHttpBinding_ICalculator"  
                contract="ServiceReference1.ICalculator" name="WSHttpBinding_ICalculator">  
                <identity>  
                    <userPrincipalName value="[email protected]" />  
                </identity>  
            </endpoint>  
        </client>      
    </system.serviceModel>  
</configuration>

And here's the code for the console app that I'm using to update it:

static void Main(string[] args)
{
    Console.WriteLine("Before change");            
    ShowConfig();

    Console.WriteLine("Change");
    ChangeConfig();

    Console.WriteLine("After change");
    ShowConfig();            

    Console.ReadLine();
}

private static void ChangeConfig()
{            

    Configuration configuration = ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None);
    string appConfig = File.ReadAllText(configuration.FilePath);
    appConfig = appConfig.Replace("localhost:8000", "myAddress.this.com:8080");
    File.WriteAllText(configuration.FilePath, appConfig);
    configuration.Save(ConfigurationSaveMode.Modified);

    ConfigurationManager.RefreshSection("endpoint");
    ConfigurationManager.RefreshSection("client");
    ConfigurationManager.RefreshSection("system.serviceModel");
    ConfigurationManager.RefreshSection("configuration");

}

private static void ShowConfig()
{
    ClientSection clientSection =
        ConfigurationManager.GetSection("system.serviceModel/client") as ClientSection;

    ChannelEndpointElementCollection endpointCollection =
        clientSection.ElementInformation.Properties[string.Empty].Value as ChannelEndpointElementCollection;

    foreach (ChannelEndpointElement endpointElement in endpointCollection)
    {
        Console.WriteLine(endpointElement.Address);
    }
}

The file does get updated, because I can see that in a text editor while the program is running... but the console shows the same values read twice. Most of what I've seen for RefreshSection seems to imply it relates more to appSettings, although I haven't seen anything that states that outright. Is it possible to cause a refresh on the app.config as I am trying to?

Upvotes: 1

Views: 1136

Answers (2)

NineBerry
NineBerry

Reputation: 28499

This solution replaces writing the file yourself and uses the Configuration object instead to make the changes in the specified section:

private static void ChangeConfig()
{
    Configuration configuration = ConfigurationManager.OpenExeConfiguration(ConfigurationUserLevel.None);

    var section = configuration.GetSection("system.serviceModel/client");

    if(section != null)
    {
        var xmlString = section.SectionInformation.GetRawXml();
        xmlString = xmlString.Replace("localhost:8000", "myAddress.this.com:8080");
        section.SectionInformation.SetRawXml(xmlString);

        configuration.Save(ConfigurationSaveMode.Modified);
        ConfigurationManager.RefreshSection(section.SectionInformation.SectionName);
    }
}

Upvotes: 1

Jamey
Jamey

Reputation: 1633

You need to add:

ConfigurationManager.RefreshSection("system.serviceModel/client");

Your calls to RefreshSection need to reference everything that inherits from System.Configuration.ConfigurationSection.

Upvotes: 3

Related Questions