C# (.NET) Application Configuration: A Complete Guide
Configuration management is one of the key tasks when developing modern applications in C# (.NET). The Microsoft.Extensions.Configuration library provides a powerful and flexible mechanism for reading settings from various sources: JSON files, environment variables, command-line arguments, and secrets. In this article, we will thoroughly examine how to configure .NET applications using best practices and code examples.
Key Features of the Library
- Multiple data sources: JSON, XML, INI, environment variables, command-line arguments, Azure Key Vault, and others.
- Hierarchical structure: support for nested sections using colon-separated keys (
Section:Subsection:Key). - Binding to classes (Options Pattern): automatic population of POCO objects from configuration.
- Flexible overriding: the last added source has the highest priority.
- Secrets support:
Secret Managerfor development, secure storage for production.
Installation and Setup
To work with configuration in a .NET application (console, ASP.NET Core, MAUI, etc.), you need to install the NuGet package:
dotnet add package Microsoft.Extensions.Configurationdotnet add package Microsoft.Extensions.Configuration.Jsondotnet add package Microsoft.Extensions.Configuration.EnvironmentVariablesdotnet add package Microsoft.Extensions.Configuration.CommandLineIn ASP.NET Core, these packages are already included by default.
Basic Example: Reading from appsettings.json
Create a file appsettings.json:
{ "Logging": { "LogLevel": { "Default": "Information", "Microsoft": "Warning" } }, "ConnectionStrings": { "DefaultConnection": "Server=localhost;Database=MyDb;User Id=sa;Password=MyPass;" }, "AppSettings": { "AppName": "MyApp", "Version": "1.0.0", "MaxRetries": 3 }}Code for reading configuration in a console application:
using Microsoft.Extensions.Configuration;
class Program{ static void Main(string[] args) { // Create configuration var configuration = new ConfigurationBuilder() .SetBasePath(Directory.GetCurrentDirectory()) .AddJsonFile("appsettings.json", optional: false, reloadOnChange: true) .AddEnvironmentVariables() .AddCommandLine(args) .Build();
// Reading simple values string appName = configuration["AppSettings:AppName"]; Console.WriteLine($"App Name: {appName}");
// Reading nested sections string connString = configuration.GetConnectionString("DefaultConnection"); Console.WriteLine($"Connection String: {connString}");
// Reading an integer int maxRetries = int.Parse(configuration["AppSettings:MaxRetries"]); Console.WriteLine($"Max Retries: {maxRetries}");
// Getting an entire section var appSettingsSection = configuration.GetSection("AppSettings"); Console.WriteLine($"Version: {appSettingsSection["Version"]}"); }}Options Pattern (Binding to Classes)
The best practice is to use strongly typed configuration via IOptions<T>. To do this:
- Create a class for the configuration section:
public class AppSettings{ public string AppName { get; set; } public string Version { get; set; } public int MaxRetries { get; set; }}- Register the configuration in the DI container (for ASP.NET Core or using
Micros