C# - DIで実行パラメータを渡す


Generic Host とかで Dependency Injection する時に型付けされたデータを渡せる Options というのがある。
これは、ファイル等から読み取った値を設定するだけでなく、渡す値をコードで書ける。

何がしたいか

以下のようなコードを書いて、"param"を XXXXService に渡したい時、
とりあえずどうすれば良いか、と思った次第です。

services.AddXXXXService("param");

対応

Optionsは次のような書き方ができ、値を直接設定できる。

services.Configure<XXXXOption>(option =>
{
    option.Param = "param";
});

そしてDIされるServiceにおいて、IOptions<XXXXOption>として注入ができる。

// コンストラクタ
public XXXXService(IOptions<XXXXOption> option)
{
    this._option = option.Value;
}

Hello XXXX と表示するだけのサービスを作ってみる。

必要なものは Microsoft.Extensions.Hosting を nuget しておけば大体揃う。

using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Options;
using Microsoft.Extensions.DependencyInjection;

Generic Host の構成とサービス呼び出し部。

class Program
{
    static void Main(string[] args)
    {
        var appHost = Host.CreateDefaultBuilder(args)
            .ConfigureServices(services =>
            {
                services.Configure<HelloOption>(option =>
                {
                    option.Name = "dekirukigasuru";
                })
                .AddSingleton<HelloService>();
            })
            .Build();

        var hello = appHost.Services.GetRequiredService<HelloService>();
        hello.Hello();
    }
}

HelloService と HelloOption はそれぞれ以下の通り。

public class HelloService
{
    public HelloService(IOptions<HelloOption> option)
    {
        this._name = option.Value.Name;
    }

    private string _name{ get; }

    public void Hello()
    {
        Console.WriteLine($"Hello {this._name} !");
    }
}
public class HelloOption
{
    public string Name { get; set; }
}

IServiceCollectionに拡張メソッドを用意すれば、Generic Host 構成時の ConfigureServices()services.AddHelloService("dekirukigasuru") と書くことができるようになる。

public static class HelloExtentions
{
    public static IServiceCollection AddHelloService(this IServiceCollection services, string name)
    {
        services.Configure<HelloOption>(option =>
        {
            option.Name = name;
        })
        .AddSingleton<HelloService>();

        return services;
    }
}

以上


関連記事