Monday, January 31, 2011

VS2010 and Building Websetup MSI - because you might have to...

So I have been having mostly good experiences in moving up from Visual Studio 2008 to 2010... but now funkiness relating to having to deploy to IIS 6 servers has become just annoying. Largely, I have been building MVC web applications in 2008 previously and now 2010  more recently. There are tons of reasons I like build MVC apps and I may revisit those reasons, but for now, I digress into something more VS2010 specific.

Because of the servers available for my applications (in the company I work for), I have been building msi setup files for the infrastructure folks to deploy. In 2008, I used a copyconfigifnew.bat file that can be found on Scott Hanselman's blog to adjust the config file as needed for the target environment. (Yes, I know continuous integration through CruiseControl and the like account for these headaches, but that is also outside my current boundaries.)

Let me get to the meat of this post: no continuous integration for me through TFS or CruiseControl, I'm not publishing directly to a file directory or FTP, but I wanted ensure configuration was build specific automagically.

Microsoft didn't seem to see it necessary to integrate the build configuration features in VS2010 into the Websetup project build sequence. Bummer. But why in the world would someone developing in the 2010 IDE still be using msi's?? Good question, but there are as many varied valid answers as there are developers. So, I dug around the interwebs to try and find someone who had already covered this ground. Most posts were directed at those using the publish/deploy package goodness in VS2010 - nice. Really. But not useful to me for this right now. It took a while, but I finally found it here. The last post as of this writing was from kakoskin on 9-21-2010 and it was exactly what I needed. 

For convenience, I am reposting his content here but I can't take any credit other than to say "yep, it worked for me, too."
How to use web.config transformations with web setup projects:
What is needed before applying this:
- web application project
- web setup project linked to web application project

1. Create needed configurations (Dev,QA,Production etc.) and associated web config transformations.
2. Use notepad or other text editor and include following in your web application project file (.csproj file) before tag <ProjectExtensions> (near the end of the project file):

  <Target Name="AfterBuild">
    <TransformXml Source="Web.config" Transform="$(ProjectConfigTransformFileName)" Destination="Web.Transformed.config" />
 Do not include Web.Transformed.config in the web application project - if you do visual studio will alert you about the changes after every build which is pretty annoying.
3. In the web setup project:
select Content files - > Exclude Filter and add Web.config (and all other Web.*.config files containing transformation rules).
4. In the web setup project:
select file system editor icon -> web application folder ->  Add File
and select Web.Transformed.config in the root of your web application project folder.
5. In the same screen: right click Web.Transformed.config and rename it to Web.config
Now you are able to generate .msi files with selected configuration and root web.config file is transformed!
Please note that this does not affect web.config files in the sub folders.
Hopefully, you don't run into this issue because you are deploying to an IIS7 environment or are otherwise not constricted in the same way I am. If you are, try this solution out. You could still use the copyconfigifnew.bat if you wanted, but why do it the same way everywhere? That would make it consistent or something. Who wants that?

And oh yeah, don't try adding that <Target> copy paste stuff to the csproj.user file... it won't work. Yep, I'm an idiot. Adding it to the proper .csproj file makes it work like a charm.

No comments:

Post a Comment