ASP.NET 5 (vNext) - Настройка конфигурации
Я пишу основное приложение для изучения ASP.NET 5. Одна область, которую я нахожу очень запутанной, - это конфигурация. До ASP.NET 5 я мог бы сделать следующее:
var settingValue = ConfigurationManager.AppSettings["SomeKey"];
У меня были бы строки кода, подобные тому, которые были разбросаны по всему моему коду. Теперь, в мире vNext, у меня есть файл config.json, который выглядит так:
config.json
{
"AppSettings": {
"SomeKey":"SomeValue"
}
}
Затем в Startup.cs у меня есть следующее:
Startup.cs
public IConfiguration Configuration { get; set; }
public Startup(IHostingEnvironment environment)
{
Configuration = new Configuration()
.AddJsonFile("config.json");
}
Оттуда я полностью в тупике. У меня есть MyClass.cs в /src/Website/Code/Models/MyClass.cs.
MyClass.cs
public class MyClass
{
public string DoSomething()
{
var result = string.Empty;
var keyValue = string.Empty; // TODO: What do I do here? How do I get the value of "AppSettings:SomeKey"?
return result;
}
}
Как получить значение "AppSettings: SomeKey"?
Ответы
Ответ 1
Я настоятельно рекомендую использовать OptionsModel
вместо прямого чтения конфигурации. Это позволяет привязать сильную типизированную модель к конфигурации.
Вот пример: GitHub.com/aspnet/Options/test/Microsoft.Extensions.Options.Test/OptionsTest.cs
Для вашего конкретного случая создайте модель:
class AppSettings {
public string SomeSetting {get;set;}
}
а затем привяжите его к вашей конфигурации:
var config = // The configuration object
var options = ConfigurationBinder.Bind<AppSettings>(config);
Console.WriteLine(options.SomeSetting);
Таким образом, вам не нужно беспокоиться о том, откуда взялась эта настройка, о том, как она хранится или какова структура. Вы просто предопределяете свою модель моделей и волшебство.
Ответ 2
ASP.NET 5 сильно использует Injection Dependency, поэтому, если вы также используете Dependency Injection, это очень просто. Если вы посмотрите пример проекта MVC6, вы увидите, как это работает:
Во-первых, существует класс AppSettings, определенный в свойствах, который представляет собой строго типизированную версию параметров, поддерживаемых вашим классом. В примере проекта это просто содержит SiteTitle.
public class AppSettings
{
public string SiteTitle { get; set; }
}
Затем этот класс инициализируется посредством инъекции зависимостей в ConfigureServices. Configuration
вот тот, который вы создали в конструкторе класса Startup.
public void ConfigureServices(IServiceCollection services)
{
services.Configure<AppSettings>(Configuration.GetSubKey("AppSettings"));
// ...
}
Затем, предполагая, что ваш класс создается экземпляром контейнера инъекций зависимостей, вы можете просто запросить IOptions, и вы его получите. Например, в контроллере у вас может быть следующее:
public class HomeController
{
private string _title;
public HomeController(IOptions<AppSettings> settings)
{
_title = settings.Options.SiteTitle;
}
}
Ответ 3
Я использую инъекцию зависимости ASP.NET 5, например.
config.json:
{
"random": "Hello World!"
}
startup.cs:
public class Startup
{
public Startup(IHostingEnvironment env, IApplicationEnvironment appEnv)
{
var builder = new ConfigurationBuilder(appEnv.ApplicationBasePath)
.AddJsonFile("config.json");
Configuration = builder.Build();
}
public IConfiguration Configuration { get; set; }
public void ConfigureServices(IServiceCollection services)
{
services.AddMvc();
services.AddSingleton<IConfiguration>(sp => { return Configuration; });
}
public void Configure(IApplicationBuilder app)
{
app.UseMvc(routes =>
{
routes.MapRoute(name: "default", template: "{controller=Home}/{action=Index}/{id?}");
});
}
}
Контроллер:
public class HomeController : Controller
{
IConfiguration config;
public HomeController(IConfiguration config)
{
this.config = config;
}
public IActionResult Index()
{
var template = "<marquee>{0}</marquee>";
var content = string.Format(template, config.Get("random"));
return Content(content, "text/html");
}
}
Ответ 4
Используйте это:
var value = Configuration.Get("AppSettings:SomeKey");
Основано на этом сообщении в блоге. Двоеточие похоже на точечную нотацию и используется для навигации по иерархии.
Если вам нужно значение в других классах, вы должны ввести его. ASP.NET имеет встроенную инъекцию зависимостей, но если вам просто нужен один экземпляр MyClass, вы можете его обновить вместо настройки контейнера DI.
public IConfiguration Configuration { get; set; }
public Startup(IHostingEnvironment environment)
{
Configuration = new Configuration()
.AddJsonFile("config.json");
//generally here you'd set up your DI container. But for now we'll just new it up
MyClass c = new MyClass(Configuration.Get("AppSettings:SomeKey"));
}
public class MyClass
{
private readonly string Setting; //if you need to pass multiple objects, use a custom POCO (and interface) instead of a string.
public MyClass(string setting) //This is called constructor injection
{
Setting = setting;
}
public string DoSomething()
{
var result = string.Empty;
//Use setting here
return result;
}
}