web-dev-qa-db-ja.com

IOptionsSnapshotを使用したASP.NET Core構成reloadOnChangeがまだ応答しない

私はASP.NET Core 2.0を使用しており、Mainメソッドに次のような構成コードがあります。

public static void Main(string[] args)
{
    var environment = Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT");
    var configuration = new ConfigurationBuilder()
        .SetBasePath(Directory.GetCurrentDirectory())
        .AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
        .AddJsonFile($"appsettings.{environment ?? "Production"}.json", optional: true, reloadOnChange: true)
        .AddEnvironmentVariables()
        .AddCommandLine(args)
        .Build();
}

私はreloadOnChangeをtrueに設定しており、コントローラーではIOptionsSnapshotを使用しています。

public HomeController(ILogger<HomeController> logger, IOptionsSnapshot<AppSettings> options)

しかし、appsettings.jsonの値を変更すると、毎回アプリを再起動する必要があります。そうしないと、ブラウザを更新しただけでは変更が反映されません。何が悪いのですか?

私はコンソールとIIS Expressの両方でアプリを実行しようとしました。私もIOptionsMonitorと同じことを試しました。IOptionsMonitorの違いは何ですか?とIOptionsSnapshot

12
Ray

ドキュメント で述べたように、reloadOnChangeを有効にして、_IOptionsSnapshot<T>_ではなく_IOptions<T>_を注入するだけで十分です。ただし、そのタイプTを適切に構成する必要があります。通常、構成の登録は次のようになります。

_services.Configure<AppSettings>(Configuration.GetSection("AppSettings"));
_

ただし、コードを詳しく見ると、プログラムを構成する新しいASP.NET Core 2.0の方法を使用しているようには見えません。設定は依存関係注入の一部になりました。そのため、WebHostBuilderを使用して、ConfigureAppConfigurationの一部として設定します。たとえば、次のようになります。

_public static IWebHost BuildWebHost()
    => new WebHostBuilder()
        .UseKestrel()
        .UseContentRoot(Directory.GetCurrentDirectory())
        .ConfigureAppConfiguration((builderContext, config) =>
        {
            IHostingEnvironment env = builderContext.HostingEnvironment;

            config.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true);
            config.AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true, reloadOnChange: true);
        })
        .UseStartup<Startup>()
        .Build();
_

WebHost.CreateDefaultBuilder()を使用してデフォルトのビルダーを使用している場合は、reloadOnChangeが有効になっている状態で構成が自動的に設定されるため、これを行う必要はありません。


IOptionsSnapshotIOptionsMonitorの違いは、IOptionsSnapshotが_IOptionsSnapshot<T>_の時点でオプションのsnapshotを提供するだけであることですオブジェクトを構築しています。

そのため、使用方法は_IOptions<T>_とまったく同じです。コンストラクタに挿入し、インスタンスに_options.Value_を格納して、後でオプションにアクセスします。その時点で、そのオブジェクトは固定されており、変更されることはありません。 _IOptionsSnapshot<T>_は、_IOptions<T>_のような単一の依存関係ではなく、スコープ付き依存関係として登録されるだけなので、1回だけではなく、すべてのリクエストで現在の構成値を取得できます。

ただし、_IOptionsMonitor<T>_は、現在の構成値をいつでも取得できるシングルトンサービスです。そのため、必要なときに現在の構成を取得する必要があるシングルトンサービスに特に役立ちます。さらに、オプションモニターはプッシュメカニズムを提供して、構成ソースによる構成変更の通知を受け取ります。これにより、構成の変更を明示的に処理できます。

オプションのスナップショットは、一時的またはスコープ付きの依存関係に使用するように設計されているため、ほとんどの場合それらを使用するだけで問題ありません。 haveシングルトンサービスを使用するalsoが最新の構成を必要とするまれな場合にのみ、オプションモニターを使用する必要があります。これらの場合、スナップショットからモニターに切り替えるだけでは不十分であることに注意してください。通常、変更された構成を何らかの方法で処理する必要があります(たとえば、状態のクリーンアップ、キャッシュのクリアなど)。したがって、実際にeverythingのリロード可能な構成が実際に必要かどうか、またはアプリケーションの再起動だけが実行可能な代替策ではないかどうかを常に検討する必要があります。

34
poke