I guess most of you working with web application in Visual Studio 2010 have seen the two extra configfiles added when you add a new Web Project:
Web-Transform is a good thing if the alternative is to copy paste it to another file just because you want another ConnectionString when you release the code to production. But to base the configfile on the Solution Configuration in Visual Studio is NOT a good thing. I don’t really see Microsofts intention here… Do we normally have a separate configfile for Debug and Release? I don’t. In my opinion, If you have Release dll’s in Production then you should also have Release dll’s in Test(or at least in some kind of Staging environment).
What develeopers need to separate is the config files for the different environments and therefore some add web.test.config, web.staging.config and web.production.config files. –To make it work out of the box in Visual Studio you also need a Solution Configuration for each configurationfile. As long as you remember to switch Configuration before you build then all the magic will be executed and a nice transformed web.config will be written to the destination. And the “as long as you remember” is the key of this blogpost. Developers DON’T always remember. Suddenly they have built their development environment to use the web.production.config and they start insert stuff into the production database… (There should maybe be a separation on IP-level so we could not access the production database, but that is usually not the case.)
The only process that should be transforming these configfiles is an automated build process that is doing the same EVERY time. And therefore would not do mistakes.
Couple of years ago I extracted the msbuild TransformWebConfig-target process so I in our Deployscripts we could invoke this target directly, -but It worked only for web.config. Not app.config, log4net.config etc. Sayed-Ibrahim-Hashimi has written a detailed blogpost about a similar (and better) approach here, and also an add-in for VS here. A custom msbuild transform task could look like this:
<Project ToolsVersion="4.0" DefaultTargets="Demo" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <UsingTask TaskName="TransformXml" AssemblyFile="$(MSBuildExtensionsPath)MicrosoftVisualStudiov10.0WebMicrosoft.Web.Publishing.Tasks.dll"/> <Target Name="Demo"> <TransformXml Source="app.config" Transform="Transform.xml" Destination="app.prod.config"/> </Target> </Project>
Ctt is simple and does exactly what I want:
ctt.exe s:source.config t:transform.config d:destination.config
Let the build/deploy process handle all the transformations of configfiles. Please don’t transform the config files based on Solution Configuration. One day you will regret…