C# – How to read custom configurations from appsettings.json

The appsettings.json file is a convenient way to store and retrieve your application’s configuration. You can add it to any project and then use the Microsoft.Extensions.Configuration library to work with it.

Since appsettings.json is just a JSON file, you can add anything to it (as long as it’s valid JSON). Compared with working with the XML-based app.config from earlier versions of .NET, dealing with customizations in appsettings.json is simpler and more flexible.

This article shows step by step how to add custom configurations to appsettings.json and how to load your customizations with steps specific to the type of project you’re working in (ASP.NET Core vs everything else).

Reading a custom class from appsettings.json in a Console App (or any project besides ASP.NET Core)

If you’re not working in ASP.NET Core, then you have to do a little bit more work to be able to read values from appsettings.json. Basically you have to add the appsettings.json file, add the configuration extension packages, initialize the configuration object, then read your custom values from the config.

1 – Add appsettings.json file

There’s nothing special about this file. It’s just a JSON file. To add it to any project:

  • Add new item.
  • Name it appsettings.json.
  • Initialize it as an empty JSON file:
{ }
Code language: JSON / JSON with Comments (json)
  • Make it copy appsettings.json to the output folder. You can do this in the UI, or by adding the following to the .csproj file:
<Project Sdk="Microsoft.NET.Sdk"> <PropertyGroup> <OutputType>Exe</OutputType> <TargetFramework>netcoreapp3.1</TargetFramework> </PropertyGroup> <ItemGroup> <None Update="appsettings.json"> <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> </None> </ItemGroup> </Project>
Code language: HTML, XML (xml)

2 – Install configuration nuget packages

  • Open Package Manager Console (View > Other Windows > Package Manager Console)
  • Install the packages:
Install-Package Microsoft.Extensions.Configuration.Json Install-Package Microsoft.Extensions.Configuration.Binder
Code language: PowerShell (powershell)

This’ll pull the latest packages and put the package references in your .csproj file:

<Project Sdk="Microsoft.NET.Sdk"> <PropertyGroup> <OutputType>Exe</OutputType> <TargetFramework>netcoreapp3.1</TargetFramework> </PropertyGroup> <ItemGroup> <PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="3.1.9" /> <PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="3.1.9" /> </ItemGroup> <ItemGroup> <None Update="appsettings.json"> <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory> </None> </ItemGroup> </Project>
Code language: HTML, XML (xml)

3 – Add a custom class – WeatherClientConfig

public class WeatherClientConfig { public bool IsEnabled { get; set; } public string WeatherAPIUrl { get; set; } public string Timeout { get; set; } }
Code language: C# (cs)

4 – Add the custom class JSON to appsettings.json

{ "WeatherClientConfig": { "IsEnabled": true, "WeatherAPIUrl": "https://localhost:12345", "Timeout": 5000 } }
Code language: JSON / JSON with Comments (json)

5 – Read the custom config from appsettings.json

To read the custom config, use ConfigurationBuilder to build the configuration object. Then use configuration.GetSection() to get your custom class JSON, then use Get<T>() to deserialize it into your custom class.

As you can see below, all of the hard work is abstracted away thanks to the Microsoft.Extension.Configuration packages.

using Microsoft.Extensions.Configuration; using System; namespace ReadingAppSettingsJson { class Program { static void Main(string[] args) { var config = new ConfigurationBuilder() .SetBasePath(AppDomain.CurrentDomain.BaseDirectory) .AddJsonFile("appsettings.json").Build(); var section = config.GetSection(nameof(WeatherClientConfig)); var weatherClientConfig = section.Get<WeatherClientConfig>(); Console.WriteLine(weatherClientConfig.WeatherAPIUrl); Console.WriteLine(weatherClientConfig.IsEnabled); Console.WriteLine(weatherClientConfig.Timeout); } } }
Code language: C# (cs)

As expected, this outputs the values from the WeatherClientConfig section in appsettings.json:

https://localhost:12345 True 5000
Code language: plaintext (plaintext)

Reading a custom class from appsettings.json in ASP.NET Core

The ASP.NET Core framework does most of the work for you. By default, it has the configuration packages as references, has the appsettings.json file included in the project, and it already initializes the Configuration object from appsettings.json.

You just need to add your customizations to appsettings.json, optionally create a custom class, and then load it in Startup.ConfigureServices.

To make this explanation consistent with how I showed how to do it in a Console App, I’m using a custom class – WeatherClientConfig.

Note: If you don’t want to add your own custom class, you could use services.Configure(customSection) and dependency inject IOptions instead. I’m showing the custom class approach here.

1 – Add a custom class

public class WeatherClientConfig { public bool IsEnabled { get; set; } public string WeatherAPIUrl { get; set; } public string Timeout { get; set; } }
Code language: C# (cs)

2 – Add the custom class JSON to appsettings.json

{ "Logging": { "LogLevel": { "Default": "Information", "Microsoft": "Warning", "Microsoft.Hosting.Lifetime": "Information" } }, "AllowedHosts": "*", "WeatherClientConfig": { "IsEnabled": true, "WeatherAPIUrl": "https://localhost:12345", "Timeout": 5000 } }
Code language: JSON / JSON with Comments (json)

3 – Register the custom class in Startup.ConfigureServices

public class Startup { public void ConfigureServices(IServiceCollection services) { services.AddControllers(); var section = Configuration.GetSection(nameof(WeatherClientConfig)); var weatherClientConfig = section.Get<WeatherClientConfig>(); services.AddSingleton(weatherClientConfig); } //The rest of Startup class }
Code language: C# (cs)

4 – Dependency inject the custom class into a controller

Take advantage of the ASP.NET Core dependency injection functionality. Because of registering WeatherClientConfig in the services collection in the previous step, anything that has WeatherClientConfig as a dependency (i.e. constructor parameter) will automatically get the registered object passed to it.

So add the WeatherClientConfig as a parameter in a controller, and add a GET endpoint that simply returns this configuration (so you can see it working with a simple GET request).

[ApiController] [Route("[controller]")] public class WeatherController : ControllerBase { private readonly WeatherClientConfig weatherClientConfig; public WeatherController(WeatherClientConfig weatherClientConfig) { this.weatherClientConfig = weatherClientConfig; } [HttpGet] public WeatherClientConfig Get() { return weatherClientConfig; } }
Code language: C# (cs)

When I do a GET request on this endpoint, I get the WeatherClientConfig JSON back:

{ "isEnabled": true, "weatherAPIUrl": "https://localhost:12345", "timeout": "5000" }
Code language: JSON / JSON with Comments (json)

Reading a single value from appsettings.json

The sections above explained how to read a custom class from appsettings.json. What if you just want a single value?

Get a single value within a section

Let’s say your appsettings.json looks like this:

{ "WeatherClientConfig": { "IsEnabled": true, "WeatherAPIUrl": "https://localhost:12345", "Timeout": 5000 } }
Code language: JSON / JSON with Comments (json)

To get WeatherClientConfig.IsEnabled (without getting the whole WeatherClientConfig object), you can use either of these two options:

//option 1 - GetValue(sectionName:key) var weatherIsEnabled = config.GetValue<bool>("WeatherClientConfig:IsEnabled"); //option 2 - GetSection(sectionName) + GetValue(key) var weatherIsEnabled = config.GetSection("WeatherClientConfig").GetValue<bool>("IsEnabled");
Code language: C# (cs)

Note: If the WeatherClientConfig section or the IsEnabled property is missing, then both of these options will return false.

Get a single top-level value

How about if you want to get a single value not contained in a section? For example, let’s say your appsettings.json looks like this:

{ "Debug": true }
Code language: JSON / JSON with Comments (json)

To get Debug, use this:

var debug = config.GetValue<bool>("Debug");
Code language: C# (cs)

Note: If the Debug property were missing from appsettings.json, this would return false.

16 thoughts on “C# – How to read custom configurations from appsettings.json”

  1. After many hours scratching around trying to access my custom configuration within my IHostBuilder CreateHostBuilder(string[] args) method this finally gave me the simplest answer I was looking for!


  2. Great article, thanks – moved to Core from ‘old’ .NET and getting nowhere with settings until I read this!

  3. Hello,

    Thanks for information for custom configuration. But I need to use it with ASP.NET Core Razor Pages, I’m not using MVC.

    I’m new to ASP.NET Core, so not sure to integrate in Razor pages. There are few issues :
    1. is there any way to handle it without MVC?
    2. I’m using latest version of ASP.NET Core 6.0 and there are no Startup.cs file any more.

    Awaiting for response.

    • Hi,

      1. Follow the first two original steps since they’re the same (add a custom class + put settings in appsettings.json).

      2. Because you’re using the new project template (where everything is in Main()), read the config and register the custom config class in Main():

      public static void Main(string[] args)
          var builder = WebApplication.CreateBuilder(args);

          //step 1 – Read from config file
          var section = builder.Configuration.GetSection(nameof(WeatherClientConfig));
          var weatherClientConfig = section.Get<WeatherClientConfig>();

          //step 2 – Register config instance with DI container

          var app = builder.Build();

          //rest of the code

      3. Now here’s the part that’s different for Razor Pages.
      First, add the custom config class as a constructor parameter (this enables constructor injection):

      public class IndexModel : PageModel
          public readonly WeatherClientConfig WeatherClientConfig;

          public IndexModel(WeatherClientConfig weatherClientConfig)
              WeatherClientConfig = weatherClientConfig;

      Now you can use this in the Model or Page. Here’s an example of displaying a property from the config on the page:

      @model IndexModel


  4. Hi when i run my app , section.Get() returns null and i don’t know the reason.
    Can i have the help please?

    • Hi Raphael,

      section.Get() returns null if it’s an empty IConfigurationSection. When you use config.GetSection(), it returns an empty IConfigurationSection if the section doesn’t exist in the appsettings.json.

      Check three things:
      1. Verify you are using the right name with config.GetSection():
      var section = config.GetSection("ThisIsTheWrongName"); //This would return an empty IConfigurationSection since it’s the wrong name
      var weatherClientConfig = section.Get<WeatherClientConfig>();

      2. If you’re using the right name with config.GetSection(), then verify that the section exists in appsettings.json.

      3. If it exists and the name is right, then you’re probably loading the wrong appsettings.json accidently (or it isn’t being copied to the build output folder, so doesn’t have your class in it).

      You can print out the file path for troubleshooting:

      var filePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "appsettings.json");
      Console.WriteLine("File is here: " + filePath);

      Go take a look at the file and see if it’s what you expect.

      Note: I’m assuming you’re using AppDomain.CurrentDomain.BaseDirectory.

      If you’re still having trouble, feel free to reply and share the relevant parts of your code (including appsettings.json).

  5. What if your appsettings.json has an array of items in it. I’m having trouble with this.

    var result = config.GetValue<List<Restriction>>(“MyCorp:Restriction”);

    “MyCorp”: {
    “Restriction”: [
    “Company”: “ABC”,
    “Account”: 8999
    “Company”: “XYZ”,
    “Account”: 8988

    • Hi,

      Instead of GetValue, use GetSection + Get, like this:

      var section = config.GetSection("MyCorp:Restriction");
      var restrictionList = section.Get<List<CompanyAccount>>();

      foreach(var ca in restrictionList)


Leave a Comment