是否ConfigurationManager.AppSettings [关键词]每次从web.con

2019-07-03 19:12发布

我只是想知道如何ConfigurationManager.AppSettings [关键]的作品?

它与物理文件,每次读我需要的关键?

如果是这样,我应该读缓存我的web.config的所有应用程序设置,然后从它读?

或ASP.NET或IIS加载在application_startup只有一次web.config文件。

如何验证物理文件是否是由每个读取访问?

如果我改变web.config文件,重新启动IIS我的应用程序,以便无法验证这种方式。

谢谢,

Answer 1:

它缓存,在性能的第一次访问,所以它不会从物理文件中的每个你问一个值时读取。 这就是为什么有必要重新启动的Windows应用程序(或刷新的配置),以获得最新的价值,为什么一个ASP.Net应用程序时,您编辑的web.config自动重新启动。 为什么ASP.Net是硬连接,重新启动在回答引用讨论如何防止在web.config中被修改,重新启动ASP.NET应用程序 。

我们可以验证这一点使用ILSpy ,看着System.Configuration的内部结构:

public static NameValueCollection AppSettings
{
    get
    {
        object section = ConfigurationManager.GetSection("appSettings");
        if (section == null || !(section is NameValueCollection))
        {
            throw new ConfigurationErrorsException(SR.GetString("Config_appsettings_declaration_invalid"));
        }
        return (NameValueCollection)section;
    }
}

起初,这确实像它每次都会得到部分。 看着GetSection:

public static object GetSection(string sectionName)
{
    if (string.IsNullOrEmpty(sectionName))
    {
        return null;
    }
    ConfigurationManager.PrepareConfigSystem();
    return ConfigurationManager.s_configSystem.GetSection(sectionName);
}

这里的关键行是PrepareConfigSystem()方法; 这个初始化实例IInternalConfigSystem通过ConfigurationManager中召开现场-具体类型是ClientConfigurationSystem

作为这一负荷的一部分,该实例配置类实例化。 这个类是有效的配置文件的对象表示,并且似乎是由ClientConfigurationSystem的ClientConfigurationHost财产在静态场举行 - 因此,它被缓存。

你可以通过执行以下(在Windows窗体或WPF应用程序)测试这个经验:

  1. 启动您的应用程序了
  2. 访问在app.config中的值
  3. 做出改变的app.config
  4. 请检查新值是否存在
  5. 呼叫ConfigurationManager.RefreshSection("appSettings")
  6. 检查是否新的值是存在的。

其实,我可以救自己一些时间,如果我刚刚读了评论RefreshSection方法:-)

/// <summary>Refreshes the named section so the next time that it is retrieved it will be re-read from disk.</summary>
/// <param name="sectionName">The configuration section name or the configuration path and section name of the section to refresh.</param>


Answer 2:

简单的答案是否定的,它并不总是从文件中读取它。 至于如果文件被改变了一些建议,然后IIS执行重启,但并不总是! 如果你想保证你从文件读取,而不是你需要调用这样的高速缓存中的最新值:

ConfigurationManager.RefreshSection("appSettings");
string fromFile = ConfigurationManager.AppSettings.Get(key) ?? string.Empty;

和一个例子,我在我的代码中使用:

/// ======================================================================================
/// <summary>
/// Refreshes the settings from disk and returns the specific setting so guarantees the
/// value is up to date at the expense of disk I/O.
/// </summary>
/// <param name="key">The setting key to return.</param>
/// <remarks>This method does involve disk I/O so should not be used in loops etc.</remarks>
/// <returns>The setting value or an empty string if not found.</returns>
/// ======================================================================================
private string RefreshFromDiskAndGetSetting(string key)
{
    // Always read from the disk to get the latest setting, this will add some overhead but
    // because this is done so infrequently it shouldn't cause any real performance issues
    ConfigurationManager.RefreshSection("appSettings");
    return GetCachedSetting(key);
}

/// ======================================================================================
/// <summary>
/// Retrieves the setting from cache so CANNOT guarantees the value is up to date but
/// does not involve disk I/O so can be called frequently.
/// </summary>
/// <param name="key">The setting key to return.</param>
/// <remarks>This method cannot guarantee the setting is up to date.</remarks>
/// <returns>The setting value or an empty string if not found.</returns>
/// ======================================================================================
private string GetCachedSetting(string key)
{
    return ConfigurationManager.AppSettings.Get(key) ?? string.Empty;
}

这使您可以很容易选择(和读码看的时候),你是否每次都得到最新的值,或者如果你不希望这个值从应用程序启动时改变。



Answer 3:

var file =
            new FileInfo(@"\\MyConfigFilePath\Web.config");

        DateTime first  = file.LastAccessTime;

        string fn = ConfigurationManager.AppSettings["FirstName"];
        Thread.Sleep(2000);

        DateTime second = file.LastAccessTime;

        string sn = ConfigurationManager.AppSettings["Surname"];
        Thread.Sleep(2000);

        DateTime third = file.LastAccessTime;

所有显示相同的LastAccessTime这意味着它在启动时缓存。

        string fn1 = ConfigurationManager.AppSettings["FirstName"];
        Thread.Sleep(2000);

        DateTime fourth = file.LastAccessTime;


文章来源: Does ConfigurationManager.AppSettings[Key] read from the web.config file each time?