At Pariveda, we typically use a standard Config project in Visual Studio to keep track of all our configuration files and accessor classes. We then write MSBuild scripts to deploy them to the appropriate web, service, winform, wpf, wcf directories as appropriate. This provides the ability to maintain a single set of config files even if they are being deployed to multiple application source environments.
This is especially appropriate with testing frameworks such as nUnit and Team Test. In order to test effectively, many files need to be copied to the running test directory as well as the main application directory. Instead of having to write duplicate msbuild tasks for copying to these directories, it would be nice if we could iterate through a list of directories that the files needed to be copied to.
You see this question being asked all the time: How do I recursively copy a series of files to another folder? That question has been answered multiple times on multiple sites. But what about needing to copy that same series of files to multiple different deployment folders? The scenario is like the one I described above or if you were wanting to automate deployment of files to a web farm. The answer is using the ItemGroup appropriately. If you can create an ItemGroup that contains the list of deployment directories that need to receive the files, you can write the script once that will iterate over this list of deployment directories and copy them to all of them.
MSBuild is certainly not as intuitive to me as NAnt. NAnt seems to be more understandable proceduraly (foreach tasks, etc) while MSBuild is more geared towards XSL type transformations. Once I got the hang of how to use ItemGroups, however, I can see how powerful MSBuild as a scripting language can be.
<Project DefaultTargets="CopyConfig" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<!-- Define the list of directories to be copied to -->
<PropertyGroup>
<ConfigFolder>c:\msbuild\config</ConfigFolder>
</PropertyGroup>
<!-- Setup the directories to deploy to -->
<ItemGroup>
<ConfigDeploy Include="Service">
<Path>c:\msbuild\Service</Path>
</ConfigDeploy>
<ConfigDeploy Include="Test">
<Path>c:\msbuild\Test</Path>
</ConfigDeploy>
</ItemGroup>
<!-- Now the task that copies the config files-->
<Target Name="CopyConfig" Condition="'@(ConfigDeploy)'!=''">
<!-- Delete any pre-existing deployment folders (Optional but good for testing) -->
<RemoveDir Directories="%(ConfigDeploy.Path)" />
<!-- Get all Files within the config directory and create multiple sets of the files
with metadata that describes where the files are to be deployed to -->
<CreateItem Include="$(ConfigFolder)\**\*.*"
AdditionalMetadata="ToDir=%(ConfigDeploy.Path)">
<Output TaskParameter="Include" ItemName="ConfigFilesToDeploy" />
</CreateItem>
<!-- Now copy all of the files to the appropriate folders -->
<Copy SourceFiles="@(ConfigFilesToDeploy)"
DestinationFolder="%(ToDir)\%(RecursiveDir)" />
</Target>
</Project>
posted on Saturday, May 19, 2007 12:43 PM