How to invoke XDT from code

Comments [0]

A few weeks ago we released XDT on NuGet, XDT is the technology driving web.config transforms, on NuGet with a license allowing you to redistribute it with your applications. We are working to open source XDT as well so hopefully I will be able to announce that soon as well.

In this post I will show you how you can create a simple application which uses XDT. For this sample we will be creating a console application which will invoke XDT for you. In Visual Studio create a Console Application. I named this project XdtSample. After that we need to add the XDT library. We can easily do this using NuGet. You can execute the following command to insert the package into your project.

 Install-Package Microsoft.Web.Xdt -Pre
  

Note: after we release the final version you can remove the –Pre flag.

Executing this command will download the XDT assembly as well as add a reference to your project. In program.cs to have the following content.

namespace XdtSample {
    using Microsoft.Web.XmlTransform;
    using System;
    using System.IO;
    using System.Text;

    class Program {
        static void Main(string[] args) {
            if (args == null || args.Length < 3) {
                ShowUsage();
                return;
            }

            string sourceFile = args[0];
            string transformFile = args[1];
            string destFile = args[2];

            if (!File.Exists(sourceFile)) { throw new FileNotFoundException("sourceFile doesn't exist"); }
            if (!File.Exists(transformFile)) { throw new FileNotFoundException("transformFile doesn't exist"); }

            using (XmlTransformableDocument document = new XmlTransformableDocument()) {
                document.PreserveWhitespace = true;
                document.Load(sourceFile);

                using (XmlTransformation transform = new XmlTransformation(transformFile)) {

                    var success = transform.Apply(document);

                    document.Save(destFile);

                    System.Console.WriteLine(
                        string.Format("\nSaved transformation at '{0}'\n\n",
                        new FileInfo(destFile).FullName));

                    int exitCode = (success == true) ? 0 : 1;
                    Environment.Exit(exitCode);
                }
            }
        }

        static void ShowUsage() {
            StringBuilder sb = new StringBuilder();
            sb.AppendLine("\n\nIncorrect set of arguments");
            sb.AppendLine("\tXdtSample.exe sourceXmlFile transformFile destFile\n\n");
            System.Console.Write(sb.ToString());
        }
    }
}

The files will be passed in as command line arguments. Below is the usage of the .exe.

xdtsample. sourceFile transformFile destFile 

In the main method here you can see that we load up the source file in an instance of XmlTransformableDocument. We use the XmlTransformation class to represent the transformFile. After applying the transform we simply save the result to the target location.

Pretty simple. Let me know if you have any questions.

I’ve posted this sample on github https://github.com/sayedihashimi/XdtSample.

Sayed Ibrahim Hashimi | http://msbuildbook.com | @SayedIHashimi


Comment Section

Comments are closed.


Someone sent me an email the other day to discuss some issues with the web packing experience in Visual Studio. One of his concerns were the directory structure in the .zip file that VS generates. If you are not familiar with this I’ll give you a quick overview. In Visual Studio 2012 when you create a web deploy package you typically end up with the full directory structure of your source inside the package. For example I have a project named WebApplication1 located at c:\temp\package\, when I create a package it contains the following files.

archive.xml
Content\C_C\Temp\package\WebApplication1\obj\Release\Package\PackageTmp
Content\C_C\Temp\package\WebApplication1\obj\Release\Package\PackageTmp\bin
Content\C_C\Temp\package\WebApplication1\obj\Release\Package\PackageTmp\bin\WebApplication1.dll
Content\C_C\Temp\package\WebApplication1\obj\Release\Package\PackageTmp\index.html
Content\C_C\Temp\package\WebApplication1\obj\Release\Package\PackageTmp\Web.config
parameters.xml
systemInfo.xml
 

These paths can get pretty long depending on where you keep your source. This has been one of my pet peeves as well.

I decided to take a closer look at this and I have a solution. To create a web deploy package in VS you will first create a publish profile for that. When you do this, a .pubxml file will be created for you under Properties\PublishProfiles. This is your publish profile file, its an MSBuild file. You can customize your publish process by editing this file. We will modify this file in order to update these paths in the package.

The best way to solve the issue here is to update the package process to include a replace rule. This replace rule will update the full path into a simple path. We already have this concept baked into our Web Publish Pipeline. The replace rule that we would like to create will replace the paths C:\Temp\package\WebApplication1\obj\Release\Package\PackageTmp with website. Here is how to do it.

Edit the .pubxml file for the profile and add the following before the closing tag.


  website
  true
  
    $(PackageDependsOn);
    AddReplaceRuleForAppPath;
    

  
    <_PkgPathFull>$([System.IO.Path]::GetFullPath($(WPPAllFilesInSingleFolder)))
  
  
  
  
    
  
  
  
  
    
      $(_PkgPathRegex)
      $(PackagePath)
    
  

 

Let me break this down a bit. You create the target AddReplaceRuleForAppPath, and inject that into the package process by adding it to PackageDependsOn property. Once this target is executed it will add a replace rule into the MSDeployReplaceRules item group. The replace rule added is equivalent to the command line switch shown below.

-replace:match='C:\\Temp\\package\\WebApplication1\\obj\\Release\\Package\\PackageTmp',replace='website'

Now when I create a package the contents are.

archive.xml
Content\website
Content\website\bin
Content\website\bin\WebApplication1.dll
Content\website\index.html
Content\website\Web.config
parameters.xml
systemInfo.xml

That's a lot better! If you try this out let me know if you have any issues.

 

Sayed Ibrahim Hashimi | @SayedIHashimi


Comment Section

Comments are closed.


With the release of VS2012 we have improved the command line publish experience. We’ve also made all the web publish related features available for VS2010 users in the Azure SDK.

The easies way to publish a project from the command line is to create a publish profile in VS and then use that. To create a publish profile in Visual Studio right click on the web project and select Publish. After that it will walk you though creating a publish profile. VS Web publish profile support the following publish methods.

  • Web Deploy – The preferred method. You can publish to any host/server which has Web Deploy configured
  • Web Deploy Package  - Used to create a package which can be published offline at a later time
  • File system  - Used to publish to a local/network folder
  • FTP  - Used to publish to any FTP server
  • FPSE – Used to publish to a server using Front Page Server Extensions

Command line publishing is only supported for Web Deploy, Web Deploy Package, and File System. If you think we should support command line scenarios for other publish methods the best thing to do would be to create a suggestion at http://aspnet.uservoice.com. If there is enough interest we may work on that support.

Let’s first take a look at how you can publish a simple Web project from the command line. I have created a simple Web Forms project and want to publish that. I’ve created a profile named SayedProfile. In order to publish this project I will execute the following command.

msbuild MyProject.csproj /p:DeployOnBuild=true /p:PublishProfile= /p:Password= /p:VisualStudioVersion=11.0

In this command you can see that I have passed in these properties;

  • DeployOnBuild – when true the build process will be extended to perform a publish as well
  • PublishProfile  - name of the publish profile (you can also provide a full path to a .pubxml file)
  • Password – Password value
  • VisualStudioVersion – Special property see comments below

You may not have expected the VisualStudioVersion property here. This is a new property which was introduced with VS 2012. It is related to how VS 2010 and VS 2012 are able to share the same projects. Take a look at my previous blog post at http://sedodream.com/2012/08/19/VisualStudioProjectCompatabilityAndVisualStudioVersion.aspx. If you are building the project file, instead of the solution file then you should always set this property.

If you are publishing using the .sln file you can omit the VisualStudioVersion property. That property will be derived from the version of the solution file itself. Note that there is one big difference when publishing using the project or solution file. When you build an individual project the properties you pass in are given to that project alone. When you build from the command line using the solution file, the properties you have specified are passed to all the projects. So if you have multiple web projects in the same solution it would attempt to publish each of the web projects.

FYI in case you haven’t already heard I’m working on an update to my book. More info at msbuildbook.com

Sayed Ibrahim Hashimi | @SayedIHashimi


Comment Section

Comments are closed.


I have had a number of request to get SlowCheetah working for Azure Worker Roles. I think I have it working now. I have not yet released the support to the download page yet but after the support is verified I will update the release.

If you would like to try out a build which has support to transform app.config, as well as other XML files, for Azure Worker Roles you can find the VSIX at https://dl.dropbox.com/u/40134810/SlowCheetah/issue-44/SlowCheetah-issue-44.zip. After installing for worker role projects you can create XML transforms for app.config, and any other XML file. When you publish to azure, or create a package your files should be transformed.

More info on this on the following issues.

BTW if you are interested in my upcoming MSBuild book checkout msbuildbook.com

Sayed Ibrahim Hashimi @SayedIHashimi


Comment Section

Comments are closed.


I wanted to let everyone know that William Bartholomew and I are working to update our MSbuild book. This will be the third edition. We are going at this a bit different than our second edition. Instead of doing a complete rewrite of the previous book, we have decided that we will release a small book to supplement the existing book. We did this for a number of reasons but it boiled down to the fact that most of the existing content is still accurate. So it would be better to release a small update just covering new stuff. This is going to be really great for everyone who already owns the second edition. You can quickly learn all the new material, and it will be much cheaper than a full sized book. I’m not sure of the cost yet but I will keep you all posted.

For more info on the book please checkout out my new site msbuildbook.com. At that site you can get info on the second edition as well as the third. You can get info on downloading samples for both versions of the book as well. FYI the source for the msbuildbook.com site is available at https://github.com/msbuild-book/msbuildbook.com.

Sayed Ibrahim Hashimi @SayedIHashimi


Comment Section

Comments are closed.


<< Older Posts | Newer Posts >>