January, 2010 Archives
Jan
Transforming an App.config file
by Mikael Lundin in Programming
The first thing you’ll notice as you start working with ASP.NET 4, is that they’ve finally solved the problem with deploying web.config files. This is a major time sink in our team as we spend hours every sprint updating configuration files on our environments. Not anymore, right!?
Wrong!
They only solved the problem for web.config. There’s still no way to do the same thing (that I’ve found) for other XML-based configuration files. If you’re like me, you probably like to extract configuration from web.config into other files (like log4net.config) to make it more manageable. These do however not work under the .NET 4 Web Deployment Tool.
Do it with XSLT
What Microsoft has created is a simplified version of XSLT. They have however also supplied the solution to our problem in the latest version of their build system MsBuild. The task is called XslTransformation and resides in Microsoft.Build.Tasks.v4.0.dll.
The problem of different environments
My problem is that I work with the same project on different computers, and I have a continuous integration mechanism that deploys my solution continuously to a test environment. Every environment has its own database connectionstring, and further on they will have different configurations for logging, caching, etc.
The web deployment tool will take care of individual changes for each environment concerning web.config, but my integration test project stores its database connection string in App.config which leaves me totally screwed.
The solution is to specify indiviual changes for each environment
My App.config looks like this.
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<connectionStrings>
<add name="ApplicationDatabase"
connectionString="Data Source=SERVER\SQLEXPRESS;Initial Catalog=ApplicationDatabase;Integrated Security=True;"
providerName="System.Data.SqlClient" />
</connectionStrings>
</configuration>
And I create change files for each and every computer that I have. The name between App and config is the name of the environment, or rather the value of $(Computer) in MSBuild. If you have several environments on the same machine you might need to start using Build Configurations in Visual Studio and select your configuration change file on that.
Now, let’s look at what that MAIA (my main developer machine) configuration looks like.
<?xml version="1.0" encoding="utf-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:msxsl="urn:schemas-microsoft-com:xslt" exclude-result-prefixes="msxsl">
<xsl:output method="xml" indent="yes"/>
<!-- Default template -->
<xsl:template match="node()|@*">
<xsl:copy><xsl:apply-templates select="node()|@*"/></xsl:copy>
</xsl:template>
<!-- Connection string replacement template -->
<xsl:template match="/configuration/connectionStrings/add[@name='ApplicationDatabase']">
<add name="ApplicationDatabase"
connectionString="Data Source=MAIA\SQLEXPRESS;Initial Catalog=ApplicationDatabase;Integrated Security=True;"
providerName="System.Data.SqlClient" />
</xsl:template>
</xsl:stylesheet>
The first part after the XML declaration means, “match every node and attribute and apply a template that matches” which will be recursive since that template matches just about everything.
If you write another template matching something more precise like the connectionString configuration, that will override the base rule and let us change the contents of the node that we’re matching.
This is now applied before every build I make. This is done by opening up the csproj-file (which is a msbuild script) and manually adding the following at the end.
<Target Name="ApplyMachineSpecificConfiguration" Condition="Exists('App.$(Computername).config')">
<XslTransformation XmlInputPaths="App.config" XslInputPath="App.$(Computername).config" OutputPaths="App.config_output" />
<Copy SourceFiles="App.config_output" DestinationFiles="App.config" />
</Target>
<Target Name="BeforeBuild">
<CallTarget Targets="ApplyMachineSpecificConfiguration"/>
</Target>
The target BeforeBuild is by default run before any compilation and that is where we call our target that will apply the XSL on App.config. We store the result in a temporary file, because the XslTransformation does not like it when we try to overwrite the XML-file that we’re reading from.
Now I can edit all configuration from one place and do not have to worry about manually merging between environments anymore. Sweet!
Inspiration to this article came mainly from Fredrik Knutson.
Jan
Database change management
by Mikael Lundin in Programming
I thought I would get started with database change management and Tarantino, but after spending a day trying to figure it out, I eventually decided that it would go much faster to just roll my own.
What is database change management?
Most developers today are familiar with source version control. Even if some use it only for backups only, the main idea is for you to go back in history when needed or to try out different approaches in other branches.
Using SVC (software version control) has become a standard in the industry, but very few apply the same idea on databases even though they also are a major part of most application development.
How not to version control databases
- Check in the database to source control
It works as long as you are only one developer to check in the binary database file to your repository. You will however not be able to merge changes from different developers and you will have to do manual updates of your production environment when the time comes. - Share database with team members on a central server
The most common way to handle database development is not to version control at all, but to setup the database on a shared central server. This fails when you need to revert to a previous version, but it also makes it harder to work as a team. When you make changes to the database you will affect your team members because they don’t have your code to support the database changes. In worst case the whole team will halt production until you’ve checked in your code to support the database change.
Why should I care?
If you manage to version control your database development, you will not only be able to revert to old revisions, work in branches but also automatically get old databases up to date within your release process. This is much more efficient than manually merging the databases at every release, and also less error prone.
- You bring stability to your release cycle
- You reduce hold ups in the production line for your team
- You bring greater control to your database development process
How do I get started?
If you use NAnt or MsBuild as build script you should probably head over to Tarantino and download their software since it has excellent support for your environment. If not, you may keep on reading.
Since I’m using psake at the moment, I decided to implement my database change management in PowerShell v2. The concept is very simple. You keep a directory in your source control where you store database creation/update scripts. The key component is that you never ever change any of these scripts after their first commit. When you need to change something in the database you create a new script. That way you will always be able to create a new database and bring it up to head revision at any time.
The naming convention here is very important.
Next thing you need is a database where you have a table and a column that tells you what version this database is. As you’ve already guessed, this is exactly up to what revision the change scripts has been applied.
All you need now is one function that can look at your database, decide what version it is and apply those changes that has not yet been applied. Actually, I do it in three functions and they look like this.
- Update-Database $connection_string $database_directory
Connects to the database and get the version number. Finds all change scripts in the database directory that are above the specific version and applies them to the database. Last it updates the database with the current version number. - Build-Database $sql_server $database_name
Connects to the DBMS and creates an empty database. In this database it adds the necessary table and column to keep track of database versions. - Drop-Database $sql_server $database_name
Removes the database from the DBMS.
Example usage
In my current project I want to run integration tests on a fresh database every time I check in code. That means I will have the following build process executed.
- Compile
- Drop-Database “MAIA\SQLEXPRESS” “IntegrationTests”
- Build-Database “MAIA\SQLEXPRESS” “IntegrationTests”
- Update-Database “Data Source=MAIA\SQLEXPRESS;Initial Catalog=IntegrationTests;Integrated Security=True;” “.\Database”
- Run integration tests
When I check in code I will rebuild the database and execute my integration tests on it. That way I will not only test my code, but also verify that my change scripts are working. When it is time for release I will be able to run Update-Database on my production database, because I know that those build scripts has been thoroughly tested.
Here is my PowerShell script if you’re interested. I still see myself as a novice in PowerShell scripting, but it works and is quite minimalistic.
Jan
WCF: The connection was closed unexpectedly
by Mikael Lundin in Programming
Have you ever gotten the following error working with WCF services?
System.ServiceModel.CommunicationException: The underlying connection was closed: The connection was closed unexpectedly.
In your frustration of pulling your hair because the lack of more information you went to Google, pasted the error message and found this blog. Here I will tell you what to do.
- Open up your web.config/app.config on the server side and add the following
<system.diagnostics> <!-- This logging is great when WCF does not work. --> <sources> <source name="System.ServiceModel" switchValue="Information, ActivityTracing" propagateActivity="true"> <listeners> <add name="traceListener" type="System.Diagnostics.XmlWriterTraceListener" initializeData= "c:\traces.svclog" /> </listeners> </source> </sources> </system.diagnostics>
- A file called traces.svclog will be stored on your harddrive. This will contain the the error message that you’re looking for. All you now need is the right tool to open it up. It is called svctraceviewer.exe and usually resides in the folder C:\Program Files\Microsoft SDKs\Windows\v6.0A\bin. If you don’t have this folder or anything like it, you go download the Microsoft Windows SDK from here.
- Now you can open your log and look for the error that is thrown. There you will find a detailed stacktrace of what’s wrong.

Good Luck!
Jan
Certified Scrum Master
by Mikael Lundin in Technicalities
Today I became a certified scrum master. That’s really nothing to brag about. You have to participate in two days of training and come out as certified scrum master. I don’t really like titles that doesn’t mean anything.
Scrum
The last six months I’ve been working in a scrum project that have been delivering flawlessly. We have been reporting low level of bugs every sprint review and none reoccurring bugs. The customer has been satisfied with our releases and we’ve been able to congratulate ourselves for a work well done every third week.
Is this scrum?
When you put together the right kind of people, driven to do their very best, to work on an exciting and rewarding project, I don’t believe it really matters what process you would use. They will find a way to get it to work. I would not say that Scrum hasn’t helped us, but the choice of process would not matter unless you are
- Motivated
- Team worker
- Exploratory
- Brave
- (and all those other qualities you look for in any team member)
Todays shit is Scrum, and I welcome the support this process will give us today that we haven’t found in any other development process. I believe however that the measure of success is more of a people matter.


