Scott Hanselman

Using the ASP.NET Core Environment Feature to manage Development vs. Production for any config file type

October 22, 2020 Comment on this post [4] Posted in ASP.NET
Sponsored By

ASP.NET Core can understand what "environment" it's running under. For me, that's "development," "test," "staging," "production," but for you it can be whatever makes you happy. By default, ASP.NET understand Development, Staging, and Production.

You can the change how your app behaves by asking "IsDevelopment" to do certain things. For example:

if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}

if (env.IsProduction() || env.IsStaging() || env.IsEnvironment("Staging_2"))
{
app.UseExceptionHandler("/Error");
}

There are helpers for the standard environments, or I can just pass in a string.

You can also make Environmental decisions with taghelpers like this in your Views/Razor Pages. I did this when I dynamically generated my robots.txt files:

@page
@{
Layout = null;
this.Response.ContentType = "text/plain";
}
# /robots.txt file for http://www.hanselman.com/
User-agent: *
<environment include="Development,Staging">Disallow: /</environment>
<environment include="Production">Disallow: /blog/private
Disallow: /blog/secret
Disallow: /blog/somethingelse</environment>

This is a really nice way to include things like banners or JavaScript when your site is running in a certain environment. These are easily set as environment variables if you're running in a container. If you're running in an Azure App Service you set the environment from the Config blade:

Now that I've moved this blog to Azure, we have a number of config files that are specific to this blog. Since the configuration features of ASP.NET are so flexible it was easy to extend this idea of environments to our own config files.

Our Startup class sets up the filesnames of our various config files. Note the second line, if we have no environment, we just look for the regular file name.

public Startup(IWebHostEnvironment env)
{
hostingEnvironment = env;

var envname = string.IsNullOrWhiteSpace(hostingEnvironment.EnvironmentName) ?
"." : string.Format($".{hostingEnvironment.EnvironmentName}.");

SiteSecurityConfigPath = Path.Combine("Config", $"siteSecurity{envname}config");
IISUrlRewriteConfigPath = Path.Combine("Config", $"IISUrlRewrite{envname}config");
SiteConfigPath = Path.Combine("Config", $"site{envname}config");
MetaConfigPath = Path.Combine("Config", $"meta{envname}config");
AppSettingsConfigPath = $"appsettings.json";

...

Here's the files in my Visual Studio. Note that another benefit of this naming structure is that the files nest nicely underneath their parent file.

Nested config files

The formalization of environments is not a new thing, but the adoption of it deeply into our application at every level has allowed us to move from dev to staging to production very easily. It's very likely that you have done this in your application, but you may have rolled your own solution. Take a look if you can remove code and adopt this built in technique.

Here's some articles I've already written on the subject of moving this blog to the cloud:

If you find any issues with this blog like

  • Broken links and 404s where you wouldn't expect them
  • Broken images, zero byte images, giant images
  • General oddness

Please file them here https://github.com/shanselman/hanselman.com-bugs and let me know!


Sponsor: Suffering from a lack of clarity around software bugs? Give your customers the experience they deserve and expect with error monitoring from Raygun.com. Installs in minutes, try it today!

About Scott

Scott Hanselman is a former professor, former Chief Architect in finance, now speaker, consultant, father, diabetic, and Microsoft employee. He is a failed stand-up comic, a cornrower, and a book author.

facebook twitter subscribe
About   Newsletter
Hosting By
Hosted in an Azure App Service
October 26, 2020 14:27
In that implementation I understand that all config files are always deployed.
I prefer to use XML Custom transformation rules, and to deploy only the transformed .config file without (.Development.config, .Staging.config, .Production.config). I currently use them in Build Pipelines and makes build artifact clearer.
And the code in " Startup()" method could be skipped.
October 29, 2020 10:39
This was a good article; a surprising number of developers don't know how this works. Perhaps at some point you can write something that also includes how to use environmental variables to overwrite the values in appsettings. This is often how you do things in a cloud hosted environment with different settings per cloud deployment.
October 29, 2020 12:38
So I would you to use Magento CMS. For better support solutions, speed, security, and performance, you will have to migrate. And, the sooner you do it, the better it is for you. Make the move now so that you can afford to spend some time learning the new technology. Also there a lot of useful extensions can check in this article <a href="https://elogic.co/blog/top-20-free-and-paid-magento-2-extensions-for-your-ecommerce-website/">https://elogic.co/blog/top-20-free-and-paid-magento-2-extensions-for-your-ecommerce-website/</a>
October 30, 2020 9:57
I really like environment tag helper. It really allows to structure code well, without code smells.

Comments are closed.

Disclaimer: The opinions expressed herein are my own personal opinions and do not represent my employer's view in any way.