1.パッケージ追加
・microsoft.extensions.configuration.json
JSON形式の設定ファイル(
パッケージのインストール
Visual Studioツール>NuGetマネージャー>パッケージ マネージャー コンソール以下を実行
PM> Install-Package Microsoft.Extensions.Configuration.Json
・microsoft.extensions.hosting
依存関係の注入 (DI)、構成管理 (Configuration)などを統合的に管理するためのライブラリ(汎用ホスト)
2.appsettiongs.json追加
・ソリューションエクスプローラー>プロジェクト選択>追加>JavaScript JSON 構成ファイル>名前入力>追加
appsettings.jsonなど)を読み込むための構成プロバイダーパッケージのインストール
Visual Studioツール>NuGetマネージャー>パッケージ マネージャー コンソール以下を実行
PM> Install-Package Microsoft.Extensions.Configuration.Json
・microsoft.extensions.hosting
依存関係の注入 (DI)、構成管理 (Configuration)などを統合的に管理するためのライブラリ(汎用ホスト)パッケージのインストール
Visual Studioのツール>NuGetマネージャー>ソリューションのNuGet パッケージの管理
Microsoft.Extensions.Hostingを検索>選択>プロジェクトにチェック>インストール
2.appsettiongs.json追加
(ファイル名は他と干渉しなければ任意)
・ソリューションエクスプローラー>プロジェクト選択>追加>JavaScript JSON 構成ファイル>名前入力>追加
・追加されたappsettiongs.jsonを右クリック>プロパティー>ビルドアクション>ドロップダウンで[コンテンツ]に変更
・出力ディレクトリにコピー>ドロップダウンで[新しい場合はコピーする]に変更
この設定を行うことで、ビルド時に実行ファイル(.exe)と同じフォルダにJSONファイルが出力され、DIコンテナ(Microsoft.Extensions.Configuration など)から正しく読み込めるようになる。
2.Jsonに対応するクラス追加
appsettingsをいくつかに分割する前提で、全体を管理するクラスを作る。名前は任意。
分割した個々の要素(Section)に対応するクラスを作り、そのインスタンスをプロパティーとして設定する。
public class RootSettings { // AppSettings をプロパティとして持つ public AppSettings AppSettings { get; set; } = new(); }
appsettings.jsonの構成要素名と一致する名前でクラスを作る。
上記の例ではappsettings.jsonの中に”AppSettings"という要素がある。
3.App.xaml変更
StartupUriの設定を削除。
StartupUri="MainWindow.xaml">3.App.xaml.cs変更
コンストラクタでDIから受け取るServiceを登録
public static IHost? AppHost { get; private set; } /// <summary> /// ホスト(Host)を構築し、設定ファイルとウインドウをDIコンテナに登録します。 /// </summary> public App() { //他のアプリから起動された場合、カレントディレクトリが異なる場合があるため、exeのあるフォルダに変更する。 System.Environment.CurrentDirectory = System.AppContext.BaseDirectory;AppHost = Host.CreateDefaultBuilder() .ConfigureServices((context, services) => { services.AddSingleton<StorageService>(); services.Configure<AppSettings>(context.Configuration); var rootSettings = context.Configuration.Get<AppSettings>() ?? new AppSettings(); services.PostConfigure<AppSettings>(settings => { settings.PostConfigure(); }); // MainWindow や他の設定クラスに渡す AppSettings は、Options パターン(IOptions)を経由して取得したものをシングルトン登録する services.AddSingleton<AppSettings>(provider => { // ここで .Value を要求した時にAppSettingsが読み込まれ、PostConfigureが実行される var options = provider.GetRequiredService<Microsoft.Extensions.Options.IOptions<AppSettings>>(); return options.Value; }); // AppSettings には、rootSettings のAppSettingsインスタンスをそのまま渡す services.AddSingleton<DirSettings>(provider => { // DIコンテナから登録済みの rootSettings を取り出し、その中の AppSettings を返す var appSettings = provider.GetRequiredService<AppSettings>(); return appSettings.DirSettings; }); services.AddSingleton<FileSettings>(provider => { // DIコンテナから登録済みの rootSettings を取り出し、その中の AppSettings を返す var appSettings = provider.GetRequiredService<AppSettings>(); return appSettings.FileSettings; }); // 画面をDIコンテナに登録 services.AddTransient<MainWindow>(); services.PostConfigure<AppSettings>(settings => { settings.PostConfigure(); }); }) .Build(); }protected override async void OnStartup(StartupEventArgs e) { // ホストの起動 await AppHost.StartAsync(); // DIコンテナからMainWindowを取得(自動的にAppSettingsが注入される) var mainWindow = AppHost.Services.GetRequiredService<MainWindow>(); mainWindow.Show(); base.OnStartup(e); } protected override async void OnExit(ExitEventArgs e) { // アプリ終了時にホストをクリーンアップ
if (AppHost != null)
{
await AppHost.StopAsync();
}
AppHost.Dispose(); base.OnExit(e); }
4.MainWindow.xaml.cs変更
コンストラクタでDIから登録したServiceを受け取る。
MainWindowの設定に関わるものがある場合は、InitializeComponentの前に呼ぶ。
public MainWindow(AppSettings settings) { this.DataContext = settings; InitializeComponent(); }
0 件のコメント:
コメントを投稿