Передача конфигурации через IOptions

Данное руководство устарело. Актуальное руководство: Руководство по ASP.NET Core 7

Последнее обновление: 14.11.2019

С помощью механизма внедрения зависимостей можно передавать конфигурацию как сервис различные компоненты middleware и прочие классы приложения. Но кроме того, с помощью объекта IOptions можно передавать конфигурацию не просто как набор настроек в виде пар ключ-значение, а как объекты определенных классов.

Допустим, у нас проект ASP.NET Core по типу Empty. Определим в проекте файл конфигурации person.json со следующим содержимым:

{
  "age": 18,
  "name": "Tom",
  "languages": [
    "English",
    "German",
    "Spanish"
  ],
  "company": {
    "title": "Microsoft",
    "country":  "USA"
  }
}

Данный файл по сути описывает одного пользователя. Элемент name сопоставляется с именем пользвателя, age - с возрастом, languages представляет языки, которыми владеет пользователь, а элемент company - компания, в которой пользователь работает. И мы хотим эти данные использовать эти настройки в приложении как целостный объект. Для этого добавим вначале в проект класс Person:

public class Person
{
	public string Name { get; set; }
	public int Age { get; set; }
	public List<string> Languages { get; set; }
	public Company Company { get; set; }
}
public class Company
{
	public string Title { get; set; }
	public string Country { get; set; }
}

Для представления компании пользователя определен дополнительный класс Company. Но, как можно заметить, определение класса Person совпадает со структурой json-файла.

И чтобы передать конфигурационные настройки через объект Person, мы можем использовать сервис IOptions<TOptions>. Для этого определим в проекте новый класс PersonMiddleware, который фактически будет выводить информацию о пользователе на веб-станицу:

using System.Threading.Tasks;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Options;
using System.Text;

namespace ConfigurationApp
{
    public class PersonMiddleware
    {
        private readonly RequestDelegate _next;

        public PersonMiddleware(RequestDelegate next, IOptions<Person> options)
        {
            _next = next;
            Person = options.Value;
        }

        public Person Person { get; }

        public async Task InvokeAsync(HttpContext context)
        {
            StringBuilder stringBuilder = new StringBuilder();
            stringBuilder.Append($"<p>Name: {Person?.Name}</p>");
            stringBuilder.Append($"<p>Age: {Person?.Age}</p>");
            stringBuilder.Append($"<p>Company: {Person?.Company?.Title}</p>");
            stringBuilder.Append("<h3>Languages</h3><ul>");
            foreach(string lang in Person.Languages)
                stringBuilder.Append($"<li>{lang}</li>");
            stringBuilder.Append("</ul>");

            await context.Response.WriteAsync(stringBuilder.ToString());
        }
    }
}

Через конструктор система будет передавать в контроллер объект IOptions<Person>. Но чтобы эта передача произошла, нам еще надо изменить класс Startup:

using Microsoft.AspNetCore.Builder;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Configuration;

namespace ConfigurationApp
{
    public class Startup
    {
        public Startup()
        {
            var builder = new ConfigurationBuilder().AddJsonFile("person.json");
            AppConfiguration = builder.Build();
        }

        public IConfiguration AppConfiguration { get; set; }

        public void ConfigureServices(IServiceCollection services)
        {
            // создание объекта Person по ключам из конфигурации
            services.Configure<Person>(AppConfiguration);
        }

        public void Configure(IApplicationBuilder app)
        {
            app.UseMiddleware<PersonMiddleware>();
        }
    }
}

В методе ConfigureServices() по данным конфигурации из свойства AppConfiguration создается объект Person:

services.Configure<Person>(AppConfiguration);

В итоге PersonMiddleware при получении запроса отправит данные объекта Person, а по сути данные из файла конфигурации.

Options в ASP.NET Core

При необходимости мы можем переопределить настройки с помощью перегрузки метода services.Configure():

public void ConfigureServices(IServiceCollection services)
{
	services.Configure<Person>(AppConfiguration);
	services.Configure<Person>(opt =>
    {
        opt.Age = 22;
    });
}

Также можно передавать отдельные секции конфигурации. Например, передадим секцию Company:

public void ConfigureServices(IServiceCollection services)
{
	services.Configure<Person>(AppConfiguration);
	services.Configure<Company>(AppConfiguration.GetSection("company"));
}
Помощь сайту
Юмани:
410011174743222
Перевод на карту
Номер карты:
4048415020898850