Working with Azure App Services Application Settings and Connection Strings in ASP.NET Core
ASP.NET Core’s configuration system has been re-architected from previous versions of ASP.NET, which relied on System.Configuration
and XML configuration files like web.config
. The new configuration model provides streamlined access to key/value based settings that can be retrieved from a variety of sources: from files using built-in support for JSON, XML, and INI formats, as well as from environment variables, command line arguments or an in-memory collection.
Azure App Services gives us the possibility to set these settings directly in the Azure Portal and retrieve them from our Application Code:
App settings
This section contains name/value pairs that you web app will load on start up.
- For .NET apps like the previous versions of ASP.NET, these settings are injected into your .NET configuration
AppSettings
at runtime, overriding existing settings. - These settings also are injected as environment variables at runtime. For each app setting, two environment variables are created; one with the name specified by the app setting entry, and another with a prefix of APPSETTING_. Both contain the same value.
Connection strings
For .NET apps like the previous versions of ASP.NET, these connection strings are injected into your .NET configuration connectionStrings
settings at runtime, overriding existing entries where the key equals the linked database name.
These settings will also be available as environment variables at runtime, prefixed with the connection type. The environment variable prefixes are as follows:
- SQL Server:
SQLCONNSTR_
- MySQL:
MYSQLCONNSTR_
- SQL Database:
SQLAZURECONNSTR_
- Custom:
CUSTOMCONNSTR_
For example, if a Custom connection string were named Redis
, it would be accessed through the environment variable CUSTOMCONNSTR_Redis
.
We can see these environment variables through KUDU: https://<sitename>.scm.azurewebsites.net/Env.cshtml
Getting these settings from ASP.NET Core
UPDATE: Jeff Sanders wrote an excellent blog explaining how to get these settings and work with them directly from your controllers in an elegant and simple way: Azure .NET Core Application Settings
The way to get these settings from our ASP.NET Core is accessing to the injected environment variables. Hence we have to load these environment variables into our Configuration in the Startup.cs file:
public Startup(IHostingEnvironment env)
{
var builder = new ConfigurationBuilder()
.SetBasePath(env.ContentRootPath)
.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
.AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true)
.AddEnvironmentVariables();
Configuration = builder.Build();
}
The order in which configuration sources are specified is important, as this establishes the precedence with which settings will be applied if they exist in multiple locations. In the example below, if the same setting exists in both appsettings.json and in an environment variable, the setting from the environment variable will be the one that is used. The last configuration source specified “wins” if a setting exists in more than one location. The ASP.NET team recommends specifying environment variables last, so that the environment where your app is running can override anything set in deployed configuration files.
Grouped in sections
In ASP.NET Core we can group our related settings in sections, one group for the connection string, another one for Application Insights configuration, another for AzureAD...
An example of appsettings.json
file would be:
If we want, for example, to retrieve the AzureAD's ClientId we could get it through our Configuration: Configuration["Authentication:AzureAd:ClientId"]
or the Application Insights' InstrumentationKey: Configuration["ApplicationInsights:InstrumentationKey"]
Overriding nested keys in Azure App Services (through environment variables)
To override nested keys in the App Settings section we can define a variable using the full path Authentication:AzureAd:ClientId
as name or using double underscore Authentication__AzureAd__ClientId
Connection Strings
To get the connection string named "Redis" defined in the appsettings.json
file we could just use the same approach that we used earlier: Configuration["ConnectionStrings:Redis"].
However there's a better way to access to the connection strings, an extension method Configuration.GetConnectionString("Redis")
which when is loading the keys from the appsettings.json
file is just acting as a Shorthand for the ConnectionStrings
section but when is working with the environment variables that Azure App Services defines for the connection strings is able to locate the "Redis" connection string regardless of the type the connection string has in the portal: SQL Server, MySQL, SQL Database or Custom.
So we can use Configuration.GetConnectionString("Redis")
to get a development connection string from our appsettings.json
file and override it setting a different one in the Connection String panel of our Web App when the application is deployed and running in Azure.
May the PaaS be with you!
Carlos.