36

I have a main Web.config file, and under that there is a Web.Test.config, Web.Development.Config etc.

When I preview the transformation via SlowCheetah on the Test config, it appears to transform the values correctly.

When I switch my build environment from Development to Testing and try to debug the application, the application runs under whatever values are in the main Web.config file (i.e. it is not transforming anything).

How do I make the build environment pick the correct config when debugging rather than just always using the base Web.config file? Is this possible?

Ilya Chumakov
  • 23,161
  • 9
  • 86
  • 114
mameesh
  • 3,651
  • 9
  • 37
  • 47

3 Answers3

60

You can transform Web.config on build. Add this target to *.csproj file:

<Import Project="$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)\WebApplications\Microsoft.WebApplication.targets" />
<Target Name="BeforeBuild">
    <TransformXml 
        Source="Web.Base.config" 
        Transform="Web.$(Configuration).config" 
        Destination="Web.config" />
</Target>

Keep the origin configuration in Web.Base.config. It's enough to enable transformation and it works for any XML config file. SlowCheetah is no longer needed at all.

To avoid unwanted transform on publish, use this (and check the comments and the link below for more details):

From a reminder in the comments I realized that I also have a problem with Visual Studio transforming the XML twice, when Publishing a project. The solution to this is to add a Condition to the Target-tag like this:

<Target Name="BeforeBuild" Condition="'$(PublishProfileName)' == '' And '$(WebPublishProfileFile)' == ''">

http://sebnilsson.com/a5410281/asp-net-transform-web-config-with-debug-release-on-build/

Ilya Chumakov
  • 23,161
  • 9
  • 86
  • 114
  • 1
    This is the most simple solution, I did it and it works great. But... there is always a but... I always get the "Debugging Not Enable" error when it is enable on Web.Base.config but my Web.config is empty at first time. By selecting "Modify the Web.config file to enable debugging" and clicking OK, it continues working fine. If Web.config has last run version with debugging enable it works fine. It seems that debug enable is checked before transformation. – Fernando Torres Oct 25 '17 at 05:52
  • 6
    This solution is working fine. But another draw back is, that anything that Visual Studio/NuGet/etc. changes in the `web.config` file, needs to be ported manually to the `Web.Base.config` file. – Simon Lang Nov 01 '17 at 14:45
  • 1
    For anyone else working with multiple versions of VS, replacing my hardcoded value with $(VisualStudioVersion) worked for me – Brandon Johnson Jul 11 '18 at 21:16
  • 2
    don't have to use base if you don't want to – Tyler Jun 06 '19 at 17:10
  • 2
    per the link provided this should be updated to correct double transform issue. "UPDATE: From a reminder in the comments I realized that I also have a problem with Visual Studio transforming the XML twice, when Publishing a project. The solution to this is to add a Condition to the Target-tag like this: " – Heriberto Lugo Jan 21 '21 at 06:00
  • 1
    Add the condition `'$(TF_BUILD)' == ''` if you're already transforming the file in Azure Pipelines, otherwise they will be transformed twice. – Rudey Jun 11 '22 at 15:03
  • 1
    @HeribertoLugo, thank you, I've updated the answer. Time goes so fast... – Ilya Chumakov Apr 21 '23 at 19:03
  • yes it certainly does. thanks for the update – Heriberto Lugo Apr 24 '23 at 08:19
5

XML transformations will only be applied when you publish web apps and not during build.

This blog post details a work around using build settings.

  • 1
    I combined the above solution `Target BeforeBuild` and this one. Making use of `Web.Base.config`. Thanks! – mike123 Jan 20 '17 at 00:20
  • @mike123 - Could you provide a more detailed explanation of how that looks like? Looks interesting. I managed to make this work with SlowCheetah using their nuget package for web.config files. – arviman Feb 28 '17 at 10:43
  • 2
    @arviman the csproj file needed changes in two places ` ... Web.config ... ` – mike123 Feb 28 '17 at 16:24
-1

The solution I applied was:

At application startup (ex: Global.asax), change the configuration file path with the following code snippet:

var oldConfigPath = (string) AppDomain.CurrentDomain.GetData("APP_CONFIG_FILE");
var directory = Directory.GetParent(oldConfigPath).FullName;

//Check if is using Web.config in source directory
if (Directory.GetFiles(directory).Any(s => s.EndsWith(".csproj")))
{                
   //Modify config file that must be used
   var path = $"{Assembly.GetExecutingAssembly().CodeBase}.config";
   AppDomain.CurrentDomain.SetData("APP_CONFIG_FILE", path);

   //Reset ConfigManager
   typeof(ConfigurationManager)
   .GetField("s_initState", BindingFlags.Static | BindingFlags.NonPublic)
   .SetValue(null, 0);

}
Daniel Reis
  • 850
  • 9
  • 10
  • Is is a really hacky workaround to a poorly understood problem and is, in general, really bad advice. – Marie Oct 12 '22 at 14:09