<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" media="screen" href="/~d/styles/rss2full.xsl"?><?xml-stylesheet type="text/css" media="screen" href="http://feeds.feedburner.com/~d/styles/itemcontent.css"?><rss xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" version="2.0"><channel><title>sfeldman.NET</title><link>http://weblogs.asp.net/sfeldman/default.aspx</link><description>.NET, code, personal thoughts</description><dc:language>en</dc:language><generator>CommunityServer 2007 SP1 (Build: 20510.895)</generator><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="self" href="http://feeds.feedburner.com/sfeldmannet" type="application/rss+xml" /><atom10:link xmlns:atom10="http://www.w3.org/2005/Atom" rel="hub" href="http://pubsubhubbub.appspot.com" /><item><title>BizTalk Custom Pipeline</title><link>http://weblogs.asp.net/sfeldman/archive/2009/11/05/biztalk-custom-pipeline.aspx</link><pubDate>Thu, 05 Nov 2009 14:17:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7247956</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7247956</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7247956</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/11/05/biztalk-custom-pipeline.aspx#comments</comments><description>&lt;p&gt;I am starting a project that involves a lot BizTalk 2009. Since this is a completely new territory for myself, I decided to blog about it. There a lot of resources available out there, especially from &lt;a href="http://msdn.microsoft.com/en-us/biztalk/default.aspx" target="_blank"&gt;MSDN&lt;/a&gt;. &lt;/p&gt;  &lt;p&gt;First thing I decided to look at was a Custom pipeline. Two types of pipeline exist – sending and receiving. To understand better pipelines, I read &lt;a href="http://msdn.microsoft.com/en-us/library/ms935116%28BTS.10%29.aspx" target="_blank"&gt;BizTalk 2004: A Message Engine Overview&lt;/a&gt; on MSDN. It provides more information than just pipelines that is very useful for general BizTalk understanding (which I find a vital if you plan to develop for BizTalk). &lt;/p&gt;  &lt;p&gt;A typical receive pipeline has 4 sections (or “component areas”) and send pipeline 3.&lt;/p&gt;  &lt;p&gt;&lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_1ECB906C.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="image" border="0" alt="image" src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_02BD6232.png" width="389" height="90" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;&lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_6B91E7B3.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="image" border="0" alt="image" src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_3B6A9CF0.png" width="325" height="89" /&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;In BizTalk project these pipelines are presented as a flow, with designated areas where you can drop&amp;#160; components designed especially for any given stage in a pipeline of a certain type. &lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_445A2F2F.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; margin-left: 0px; border-top: 0px; margin-right: 0px; border-right: 0px" title="image" border="0" alt="image" align="right" src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_539097FC.png" width="227" height="623" /&gt;&lt;/a&gt; You can develop pipeline custom components in managed code, but you have to link it to the designer. How that is done? Each component has to be marked with a &lt;em&gt;ComponentCategory&lt;/em&gt; attribute to indicate where in pipeline it can be assigned. A component that should be only assigned to Decoding section would be marked as:&lt;/p&gt;  &lt;div style="border-bottom: silver 1px solid; text-align: left; border-left: silver 1px solid; padding-bottom: 4px; line-height: 12pt; background-color: #f4f4f4; margin: 20px 0px 10px; padding-left: 4px; width: 59.63%; padding-right: 4px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; height: 86px; max-height: 200px; font-size: 8pt; overflow: auto; border-top: silver 1px solid; cursor: text; border-right: silver 1px solid; padding-top: 4px" id="codeSnippetWrapper"&gt;   &lt;div style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px" id="codeSnippet"&gt;     &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;[ComponentCategory(CategoryTypes.CATID_PipelineComponent)]&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;[ComponentCategory(CategoryTypes.CATID_Decoder)]&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;[System.Runtime.InteropServices.Guid(&lt;span style="color: #006080"&gt;&amp;quot;9D0E4103-4CCE-4536-83FA-4A5040674AD6&amp;quot;&lt;/span&gt;)]&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;The interoperability GUID 9D0E4103-4CCE-4536-83FA-4A5040674AD6 stands for “receive pipeline, decode section” and it is used to indicate to Visual Studio designer where the component can be dropped. For this purpose, I have create a component called “CustomPipelineComponent” and decorated with these attributes. Dragged and dropped the component and this is how the BizTalk pipeline looks like after that (XML view):&lt;/p&gt;

&lt;div style="border-bottom: silver 1px solid; text-align: left; border-left: silver 1px solid; padding-bottom: 4px; line-height: 12pt; background-color: #f4f4f4; margin: 20px 0px 10px; padding-left: 4px; width: 59.84%; padding-right: 4px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; height: 210px; max-height: 200px; font-size: 8pt; overflow: auto; border-top: silver 1px solid; cursor: text; border-right: silver 1px solid; padding-top: 4px" id="codeSnippetWrapper"&gt;
  &lt;div style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px" id="codeSnippet"&gt;
    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #0000ff"&gt;&amp;lt;?&lt;/span&gt;&lt;span style="color: #800000"&gt;xml&lt;/span&gt; &lt;span style="color: #ff0000"&gt;version&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;1.0&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;encoding&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;utf-16&amp;quot;&lt;/span&gt;?&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Document&lt;/span&gt; &lt;span style="color: #ff0000"&gt;xmlns:xsi&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;http://www.w3.org/2001/XMLSchema-instance&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;xmlns:xsd&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;http://www.w3.org/2001/XMLSchema&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;PolicyFilePath&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;BTSReceivePolicy.xml&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;MajorVersion&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;1&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;MinorVersion&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;0&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Description&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Stages&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Stage&lt;/span&gt; &lt;span style="color: #ff0000"&gt;CategoryId&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;&lt;u&gt;&lt;strong&gt;9d0e4103-4cce-4536-83fa-4a5040674ad6&lt;/strong&gt;&lt;/u&gt;&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;      &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Components&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;        &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Component&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;          &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Name&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;SimplePipeline.CustomPipelineComponent&lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Name&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;          &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;ComponentName&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;SIMPLE Pipeline component&lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;ComponentName&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;          &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Description&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;CustomPipelineComponent&lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Description&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;          &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Version&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;1.0.0.0&lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Version&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;          &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;CachedIsManaged&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;true&lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;CachedIsManaged&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;        &lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Component&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;      &lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Components&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Stage&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Stage&lt;/span&gt; &lt;span style="color: #ff0000"&gt;CategoryId&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;9d0e4105-4cce-4536-83fa-4a5040674ad6&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;      &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Components&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Stage&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Stage&lt;/span&gt; &lt;span style="color: #ff0000"&gt;CategoryId&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;9d0e410d-4cce-4536-83fa-4a5040674ad6&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;      &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Components&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Stage&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Stage&lt;/span&gt; &lt;span style="color: #ff0000"&gt;CategoryId&lt;/span&gt;&lt;span style="color: #0000ff"&gt;=&amp;quot;9d0e410e-4cce-4536-83fa-4a5040674ad6&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;      &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Components&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Stage&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  &lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Stages&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Document&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;If you look close, each section in pipeline (or Stage) has a designated GUID. Decoder has 9D0E4103-4CCE-4536-83FA-4A5040674AD6, same as we used to decorate our component with.&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;Now the saucy part – how do I debug and test it?&lt;/p&gt;

&lt;p&gt;To debug (which is &lt;strong&gt;NOT&lt;/strong&gt; testing) I used BizTalk 2009 SDK utility called Pipeline.exe and located in %ProgramFiles%\Microsoft BizTalk Server 2009\SDK\Utilities\PipelineTools. One disadvantage I found with this utility is the fact that you have to deploy your custom pipeline component assembly to BizTalk 2009 designated location (%ProgramFiles%\Microsoft BizTalk Server 2009\Pipeline Components). Well, at least you can debug your custom component. For that I had to update the project settings of my custom pipeline component project and setup 3 things:&lt;/p&gt;

&lt;ol&gt;
  &lt;li&gt;Specify &lt;strong&gt;Output&lt;/strong&gt; for build artifact (Figure 1)&lt;/li&gt;

  &lt;li&gt;Set &lt;strong&gt;Start Action &lt;/strong&gt;to Pipeline.exe (Figure 2)&lt;/li&gt;

  &lt;li&gt;Specify &lt;strong&gt;Command Line Arguments&lt;/strong&gt; to use pipeline that contains custom component&lt;/li&gt;
&lt;/ol&gt;

&lt;p align="center"&gt;&lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_50EA6CFC.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image" border="0" alt="image" src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_41D8AF84.png" width="694" height="496" /&gt;&lt;/a&gt; Figure 1&lt;/p&gt;

&lt;p align="left"&gt;&lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_1EAB44D2.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image" border="0" alt="image" src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_5111A902.png" width="561" height="272" /&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p align="center"&gt;Figure 2&lt;/p&gt;

&lt;p align="left"&gt;When a new instance of Debugger is invoked on component project, debugger will kick in and stop at breakpoints. &lt;/p&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_5995084C.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="image" border="0" alt="image" src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_678BF99C.png" width="831" height="434" /&gt;&lt;/a&gt; &lt;/p&gt;

&lt;p&gt;&amp;#160;&lt;/p&gt;

&lt;p&gt;To test a custom component you will have to dig dipper. I have figured a few things:&lt;/p&gt;

&lt;ol&gt;
  &lt;li&gt;You cannot do unit testing. BizTalk has &lt;strong&gt;integration testing baked in&lt;/strong&gt;.&lt;/li&gt;

  &lt;li&gt;You have to include BizTalk test assemblies, located in &lt;strong&gt;%ProgramFiles%\Microsoft BizTalk Server 2009\Developer Tools&lt;/strong&gt; (I wish other blogs would mentions this folder!)&lt;/li&gt;

  &lt;li&gt;You will have to &lt;strong&gt;cast your objects to BizTalk base classes&lt;/strong&gt; (the ones your maps/pipelines/schemas) in order to invoke testing methods (such as map.TestMap(…), schema.ValidateInstance(…), and pipeline.TestPipeline(…) accordingly) &lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;I found &lt;a href="http://geekswithblogs.net/michaelstephenson/archive/2008/12/12/127827.aspx" target="_blank"&gt;one good blog post&lt;/a&gt; about how actually to write a state based testing, so I will not reproduce it here.&lt;/p&gt;

&lt;p&gt;PS: an attempt to test pipeline components as unit testing is showed in &lt;a href="http://geekswithblogs.net/michaelstephenson/archive/2008/03/30/120852.aspx" target="_blank"&gt;this blog&lt;/a&gt;.&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7247956" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/BizTalk/default.aspx">BizTalk</category></item><item><title>Lost Generation – Really Good</title><link>http://weblogs.asp.net/sfeldman/archive/2009/10/28/lost-generation-really-good.aspx</link><pubDate>Wed, 28 Oct 2009 20:36:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7241781</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7241781</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7241781</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/10/28/lost-generation-really-good.aspx#comments</comments><description>&lt;div style="padding-bottom: 0px; margin: 0px; padding-left: 0px; padding-right: 0px; display: inline; float: none; padding-top: 0px" id="scid:5737277B-5D6D-4f48-ABFC-DD9C333F4C5D:d919dc37-1c95-4882-ac2a-9cd600530549" class="wlWriterEditableSmartContent"&gt;&lt;div&gt;&lt;a href="http://www.youtube.com/watch?v=Hds3jvjZY-Y" target="_new"&gt;&lt;img src="http://weblogs.asp.net/blogs/sfeldman/video51b125601347_194ED9F9.jpg" style="border-style: none" galleryimg="no" alt=""&gt;&lt;/a&gt;&lt;/div&gt;&lt;/div&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7241781" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/Personal/default.aspx">Personal</category></item><item><title>Creativity</title><link>http://weblogs.asp.net/sfeldman/archive/2009/10/26/creativity.aspx</link><pubDate>Tue, 27 Oct 2009 03:02:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7240136</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7240136</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7240136</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/10/26/creativity.aspx#comments</comments><description>&lt;p&gt;One picture is worth a thousand words :)&lt;/p&gt;  &lt;p&gt;&lt;a href="http://weblogs.asp.net/blogs/sfeldman/PA269561_13E163A3.jpg"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: block; float: none; margin-left: auto; border-top: 0px; margin-right: auto; border-right: 0px" title="PA269561" border="0" alt="PA269561" src="http://weblogs.asp.net/blogs/sfeldman/PA269561_thumb_55989931.jpg" width="1028" height="772" /&gt;&lt;/a&gt;&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7240136" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/Personal/default.aspx">Personal</category></item><item><title>Presentation: From Good to Great Developer</title><link>http://weblogs.asp.net/sfeldman/archive/2009/10/22/presentation-from-good-to-great-developer.aspx</link><pubDate>Fri, 23 Oct 2009 01:52:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7236588</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7236588</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7236588</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/10/22/presentation-from-good-to-great-developer.aspx#comments</comments><description>&lt;p&gt;I really liked &lt;a href="http://www.infoq.com/presentations/Good-to-Great-Developer-Chris-Hedgate" target="_blank"&gt;this presentation&lt;/a&gt;. Highly recommended.&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7236588" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/Other/default.aspx">Other</category></item><item><title>LINQ to XML for Better Maintainability</title><link>http://weblogs.asp.net/sfeldman/archive/2009/10/08/linq-to-xml-for-better-maintainability.aspx</link><pubDate>Fri, 09 Oct 2009 03:28:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7225905</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>4</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7225905</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7225905</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/10/08/linq-to-xml-for-better-maintainability.aspx#comments</comments><description>&lt;p&gt;Today I was trying to solve a simple technical problem. Given a specific XML, needed to clean it up by removing any elements of a particular type.&lt;/p&gt;  &lt;div id="codeSnippetWrapper"&gt;   &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;     &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Attachment&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;file1.pdf&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Id&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;1&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Id&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Attachment&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Attachment&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;file2.pdf&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Id&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;2&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Id&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Attachment&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Result had to be without Id elements&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;
    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Attachment&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;file1.pdf&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Attachment&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Attachment&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;file2.pdf&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;Attachment&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;A few choices for implementation:&lt;/p&gt;

&lt;ol&gt;
  &lt;li&gt;Regex&lt;/li&gt;

  &lt;li&gt;XmlDocument&lt;/li&gt;

  &lt;li&gt;LINQ to XML&lt;/li&gt;&lt;li&gt;XSLT &lt;i&gt;&lt;font color="#cc6633"&gt;(as suggested in comments)&lt;/font&gt;&lt;/i&gt;&lt;br&gt;&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;Regex option is probably the most efficient, but not the most maintainable. Myself, looking sometimes at the solutions with Regex I ask “what the heck did I try to do here”. So much for “code doesn’t lie”.&lt;/p&gt;

&lt;p&gt;XmlDocument is more expressive than Regex option, but way too chatty.&lt;/p&gt;

&lt;p&gt;LINQ to XML same as XmlDocument, expressive. As well as very clear and fluent. I picked this option not for performance, but for maintainability sake. I know it will take less developer type to understand and/or modify code when it’s time to change it. And it documents itself very well, with no need to write any comments.&lt;/p&gt;

&lt;div id="codeSnippetWrapper"&gt;
  &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;
    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;var xdoc = XDocument.Load(&lt;span style="color: rgb(0, 0, 255);"&gt;new&lt;/span&gt; StringReader(received_content));&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;b&gt;xdoc.Descendants().Where(element =&amp;gt; element.Name == &lt;span style="color: rgb(0, 96, 128);"&gt;"Id"&lt;/span&gt;).Remove();&lt;/b&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;return&lt;/span&gt; xdoc.ToString();&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;&amp;nbsp;&lt;/p&gt;

&lt;p&gt;&amp;nbsp;&lt;/p&gt;

&lt;p&gt;&amp;nbsp;&lt;/p&gt;

&lt;p&gt;Note: this is a very specific case, which does not indicate it’s a solution to all kinds of problems. Regex / XmlDocument are valid tools for all sorts of other problems.&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7225905" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/.NET/default.aspx">.NET</category></item><item><title>Too Loosely Coupled Code – One Year Later</title><link>http://weblogs.asp.net/sfeldman/archive/2009/10/06/too-loosely-coupled-code-one-year-later.aspx</link><pubDate>Wed, 07 Oct 2009 02:00:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7224498</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>1</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7224498</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7224498</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/10/06/too-loosely-coupled-code-one-year-later.aspx#comments</comments><description>&lt;p&gt;More than a year ago, I have posted a &lt;a href="http://weblogs.asp.net/sfeldman/archive/2008/06/09/too-loosely-coupled-code.aspx" target="_blank"&gt;blog entry&lt;/a&gt; related to what I was trying to implement in one of the projects. Unfortunately, not my team could understand what I was trying to do, neither I was able to make myself clear. Either way, I ended up closing the blog with a question “&lt;em&gt;can code be too loosely (coupled), or your code is so coupled, that anything else is difficult to digest?&lt;/em&gt;”. Now I can answer my own question question.&lt;/p&gt;  &lt;p&gt;Today, my current team had a team learning session, when the latest project demonstration showed what are we doing with a &lt;a href="http://weblogs.asp.net/sfeldman/archive/2008/02/14/understanding-ioc-container.aspx" target="_blank"&gt;IoC&lt;/a&gt; container we started to leverage (&lt;a href="http://structuremap.sourceforge.net/Default.htm" target="_blank"&gt;StructureMap&lt;/a&gt;). The team is not the same one I had back a year+ ago. This team has also had &lt;strong&gt;same&lt;/strong&gt; difficulty in the beginning – code that was too coupled. We have started from “Poor mans’ injection”,&amp;#160; moved to home-grown Dependency Resolver with a typical Startup Task, and now have reached the point, where a third party open-source IoC container is used. I think that could be achieved because:&lt;/p&gt;  &lt;ul&gt;   &lt;li&gt;We worked on decoupling code, learning the pros and cons&lt;/li&gt;    &lt;li&gt;We got to the point were &lt;a href="http://en.wikipedia.org/wiki/Single_responsibility_principle" target="_blank"&gt;SRP&lt;/a&gt; is followed&lt;/li&gt;    &lt;li&gt;We have got to the point were &lt;a href="http://en.wikipedia.org/wiki/Design_by_contract" target="_blank"&gt;Design by Contract&lt;/a&gt; is almost entirely how we develop&lt;/li&gt;    &lt;li&gt;We have a complete &lt;a href="http://en.wikipedia.org/wiki/Test_driven_development" target="_blank"&gt;TDD&lt;/a&gt; development in place&lt;/li&gt; &lt;/ul&gt;  &lt;p&gt;So why I could not root the idea in my previous team? Because it was way too early for my team mates and I was not ready to wait. &lt;/p&gt;  &lt;p&gt;Oh, and how the code looks now? Even better than before ;)&lt;/p&gt;  &lt;p&gt;&amp;#160;&lt;/p&gt;  &lt;div id="codeSnippetWrapper"&gt;   &lt;div style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px" id="codeSnippet"&gt;     &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&lt;span style="color: #0000ff"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff"&gt;class&lt;/span&gt; ComponentB : IComponentB   &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;{&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  &lt;span style="color: #0000ff"&gt;private&lt;/span&gt; IComponentA dependency;   &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&amp;#160;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  &lt;strong&gt;&lt;span style="color: #0000ff"&gt;public&lt;/span&gt; ComponentB(IComponentA dependency)&lt;/strong&gt;    &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  {   &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;this&lt;/span&gt;.dependency = dependency;  &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  } &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;&amp;#160;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  &lt;span style="color: #0000ff"&gt;public&lt;/span&gt; &lt;span style="color: #0000ff"&gt;void&lt;/span&gt; SomeFunctionality(&lt;span style="color: #0000ff"&gt;string&lt;/span&gt; param)&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  {&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    var result = dependency.OperationDefinedByDependencyContract(param);  &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;    &lt;span style="color: #0000ff"&gt;return&lt;/span&gt; DoSomethingWith(result);   &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: #f4f4f4; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;  }&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-bottom-style: none; text-align: left; padding-bottom: 0px; line-height: 12pt; border-right-style: none; background-color: white; margin: 0em; padding-left: 0px; width: 100%; padding-right: 0px; font-family: &amp;#39;Courier New&amp;#39;, courier, monospace; direction: ltr; border-top-style: none; color: black; font-size: 8pt; border-left-style: none; overflow: visible; padding-top: 0px"&gt;}&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;&lt;/p&gt;

&lt;p&gt;Benefits:&lt;/p&gt;

&lt;ul&gt;
  &lt;li&gt;&lt;a href="http://weblogs.asp.net/sfeldman/archive/2008/12/12/quot-hello-world-quot-tdd-style.aspx" target="_blank"&gt;TDD/BDD&lt;/a&gt; development style is enforced better when there’s no default constructor with Dependency Resolver or Poor’s man injection&lt;/li&gt;

  &lt;li&gt;No messy Startup Task that is a must when doing Dependency Resolver&lt;/li&gt;

  &lt;li&gt;Can leverage smarts of IoC container to perform tasks on a massive scale (interceptors, events, etc)&lt;/li&gt;

  &lt;li&gt;Easy way to verify if all dependencies are wired or not (contract based dependencies)&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;And as one commenter of the original blog post has asked correctly: “&lt;em&gt;The question might be more appropriately be, is the code self-documenting? Can someone who did not write the original code follow the logic and modify and maintain it?&lt;/em&gt;”. The answer is: &lt;strong&gt;it depends&lt;/strong&gt;. &lt;/p&gt;

&lt;p&gt;You have to get to a certain level to answer Yes. Until you get to that level, the answer will always be No. In order for code to be self-documenting, it needs to be of high quality and accompanied with tests/specifications. In order to be modified, maintained, and logic followed by a person who did not write it, it has to have the listed above &lt;strong&gt;AND&lt;/strong&gt; have the person to be at a certain level of skills.&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7224498" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/OO/default.aspx">OO</category><category domain="http://weblogs.asp.net/sfeldman/archive/tags/Patterns/default.aspx">Patterns</category><category domain="http://weblogs.asp.net/sfeldman/archive/tags/TDD/default.aspx">TDD</category></item><item><title>Consuming ASMX Web Service With WCF</title><link>http://weblogs.asp.net/sfeldman/archive/2009/10/02/consuming-asmx-web-service-with-wcf.aspx</link><pubDate>Fri, 02 Oct 2009 06:23:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7221479</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>1</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7221479</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7221479</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/10/02/consuming-asmx-web-service-with-wcf.aspx#comments</comments><description>&lt;p&gt;ASMX web services were a breakthrough when appeared on .NET platform. A lot of services were created to take advantage of web services technology.&lt;/p&gt;  &lt;p&gt;Now, that WCF is replacing legacy web services, we still have a lot of legacy web services running and being used. Connecting to legacy web services from WCF can be achieved either by leveraging Visual Studio .NET auto-generated proxies, or by &lt;a href="http://weblogs.asp.net/sfeldman/archive/2009/09/22/dynamic-wcf-proxy.aspx" mce_href="http://weblogs.asp.net/sfeldman/archive/2009/09/22/dynamic-wcf-proxy.aspx" target="_blank"&gt;creating dynamic channel&lt;/a&gt; I talked about before. Creating dynamic channel looks like a cleaner solution, but there are a few caveats:&lt;/p&gt;  &lt;p&gt;1. Legacy web service does not always expose a known/published interface (quiet often just implementation and no contracts);&lt;/p&gt;  &lt;p&gt;2. Configuration might be a little tweaky;&lt;/p&gt;  &lt;p&gt;In order to overcome the 1st issue, we can “re-invent” the contract that a legacy web service “would” implement.&lt;/p&gt;  &lt;div style="border: 1px solid silver; margin: 20px 0px 10px; padding: 4px; overflow: auto; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 97.5%; font-family: 'Courier New',courier,monospace; direction: ltr; max-height: 200px; font-size: 8pt; cursor: text;" id="codeSnippetWrapper"&gt;   &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;     &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;[XmlSerializerFormat]&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;public interface ILegacyService&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;{&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  [OperationContract]&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  Version GetVersion();&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;}&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Next we can generate a dynamic channel&lt;/p&gt;

&lt;div style="border: 1px solid silver; margin: 20px 0px 10px; padding: 4px; overflow: auto; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 97.5%; font-family: 'Courier New',courier,monospace; direction: ltr; max-height: 200px; font-size: 8pt; cursor: text;" id="codeSnippetWrapper"&gt;
  &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;
    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;var channel = &lt;span style="color: rgb(0, 0, 255);"&gt;new&lt;/span&gt; ChannelFactory&amp;lt;ILegacyService&amp;gt;().CreateChannel();&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;using&lt;/span&gt; (channel &lt;span style="color: rgb(0, 0, 255);"&gt;as&lt;/span&gt; IDisposable)&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;return&lt;/span&gt; channel.GetVersion();&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;Once we have channel – time to configure &lt;/p&gt;

&lt;div style="border: 1px solid silver; margin: 20px 0px 10px; padding: 4px; overflow: auto; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 97.5%; font-family: 'Courier New',courier,monospace; direction: ltr; max-height: 200px; font-size: 8pt; cursor: text;" id="codeSnippetWrapper"&gt;
  &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;
    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;system.serviceModel&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;client&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;    &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;endpoint&lt;/span&gt; &lt;span style="color: rgb(255, 0, 0);"&gt;name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="SomeServiceEndPoint"&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;              &lt;span style="color: rgb(255, 0, 0);"&gt;address&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="http://some.where.com/LegacyService/LegacyService.asmx"&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;              &lt;span style="color: rgb(255, 0, 0);"&gt;binding&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="customBinding"&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;              &lt;span style="color: rgb(255, 0, 0);"&gt;contract&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="ILegacyService"&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;              &lt;span style="color: rgb(255, 0, 0);"&gt;bindingConfiguration&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="custom.binding.for.SomeService"&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;    &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;endpoint&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;client&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;bindings&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;    &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;customBinding&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;      &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;binding&lt;/span&gt; &lt;span style="color: rgb(255, 0, 0);"&gt;name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="custom.binding.for.SomeService"&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;        &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;textMessageEncoding&lt;/span&gt; &lt;span style="color: rgb(255, 0, 0);"&gt;messageVersion&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="Soap12"&lt;/span&gt; &lt;span style="color: rgb(255, 0, 0);"&gt;writeEncoding&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="utf-8"&lt;/span&gt; &lt;span style="color: rgb(0, 0, 255);"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;        &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;httpTransport&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;      &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;binding&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;    &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;customBinding&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;bindings&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&amp;nbsp;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;system.serviceModel&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;One comment about ServiceContract attribute. When consuming a legacy web service, and it has a pre-defined namespace. Modification to “re-invented” service will include the required information (such as Namespace)&lt;/p&gt;

&lt;div style="border: 1px solid silver; margin: 20px 0px 10px; padding: 4px; overflow: auto; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 97.5%; font-family: 'Courier New',courier,monospace; direction: ltr; max-height: 200px; font-size: 8pt; cursor: text;" id="codeSnippetWrapper"&gt;
  &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;
    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;[XmlSerializerFormat]&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  [ServiceContract(Namespace = &lt;a href="http://some.where.com/LegacyService" mce_href="http://some.where.com/LegacyService"&gt;http://some.where.com/LegacyService&lt;/a&gt;)]&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  public interface ILegacyService &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  {&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;    [OperationContract]&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;    Version GetVersion();&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  }&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7221479" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/.NET/default.aspx">.NET</category></item><item><title>To Test or Not To Test: Not a Question!</title><link>http://weblogs.asp.net/sfeldman/archive/2009/09/29/to-test-or-not-to-test-not-a-question.aspx</link><pubDate>Wed, 30 Sep 2009 03:55:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7220294</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7220294</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7220294</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/09/29/to-test-or-not-to-test-not-a-question.aspx#comments</comments><description>&lt;p&gt;&lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_168DD4B9.png" mce_href="http://weblogs.asp.net/blogs/sfeldman/image_168DD4B9.png"&gt;&lt;img src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_3879373D.png" style="border: 0px none ; display: inline; margin-left: 0px; margin-right: 0px;" title="image" alt="image" mce_src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_3879373D.png" align="right" border="0" height="108" width="244"&gt;&lt;/a&gt; &lt;/p&gt;  &lt;p&gt;There was a lot of noise generated by a blog &lt;a href="http://www.joelonsoftware.com/items/2009/09/23.html" mce_href="http://www.joelonsoftware.com/items/2009/09/23.html" target="_blank"&gt;“The Duct Tape Programmer”&lt;/a&gt;. There were lots of responses as well (&lt;a href="http://blog.objectmentor.com/articles/2009/09/24/the-duct-tape-programmer" mce_href="http://blog.objectmentor.com/articles/2009/09/24/the-duct-tape-programmer" target="_blank"&gt;link&lt;/a&gt;, &lt;a href="http://jeffreypalermo.com/blog/debunking-the-duct-tape-programmer/" mce_href="http://jeffreypalermo.com/blog/debunking-the-duct-tape-programmer/" target="_blank"&gt;link&lt;/a&gt;, &lt;a href="http://devlicio.us/blogs/casey/archive/2009/09/25/ship-it-or-ship-out.aspx" mce_href="http://devlicio.us/blogs/casey/archive/2009/09/25/ship-it-or-ship-out.aspx" target="_blank"&gt;link&lt;/a&gt;, &lt;a href="http://www.markhneedham.com/blog/2009/09/26/the-duct-tape-programmer-some-thoughts/" mce_href="http://www.markhneedham.com/blog/2009/09/26/the-duct-tape-programmer-some-thoughts/" target="_blank"&gt;link&lt;/a&gt;, &lt;a href="http://geekswithblogs.net/leesblog/archive/2009/09/26/the-backyard-mechanic.aspx" mce_href="http://geekswithblogs.net/leesblog/archive/2009/09/26/the-backyard-mechanic.aspx" target="_blank"&gt;link&lt;/a&gt;, &lt;a href="http://www.rgoarchitects.com/nblog/2009/09/25/TheDuctTapeProgrammer.aspx" mce_href="http://www.rgoarchitects.com/nblog/2009/09/25/TheDuctTapeProgrammer.aspx" target="_blank"&gt;link&lt;/a&gt;, &lt;a href="http://codebetter.com/blogs/ian_cooper/archive/2009/09/28/beating-the-duct-programmer-with-generic-domains-subdomains-and-core-domains.aspx" mce_href="http://codebetter.com/blogs/ian_cooper/archive/2009/09/28/beating-the-duct-programmer-with-generic-domains-subdomains-and-core-domains.aspx" target="_blank"&gt;link,&lt;/a&gt; &lt;a href="http://www.lostechies.com/blogs/scottcreynolds/archive/2009/09/29/smart-and-gets-things-done-right.aspx" target="_blank" mce_href="http://www.lostechies.com/blogs/scottcreynolds/archive/2009/09/29/smart-and-gets-things-done-right.aspx"&gt;link&lt;/a&gt;…). The last one I read was from &lt;a href="http://ayende.com/Blog/archive/2009/09/30/duct-tape-programmers.aspx" mce_href="http://ayende.com/Blog/archive/2009/09/30/duct-tape-programmers.aspx" target="_blank"&gt;Oren&lt;/a&gt;, where he puts it plain – just don’t do it. &lt;/p&gt;  &lt;p&gt;I have my reasons to disagree with the statement(s) Joel wrote in his blog, but probably the most important one is about testing. Probably the reason for that is because &lt;b&gt;I was&lt;/b&gt; developing without TDD for quiet a while, and I saw the difference. To me tests are design, and if you drop them, well, hell with design. A good project has to have a good design, and design starts from code, expressed first in tests, and after that in production code.&lt;/p&gt;  &lt;p&gt;PS: if you disagree, the trash bin in on your desktop, not at my blog comments. 10x&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7220294" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/TDD/default.aspx">TDD</category></item><item><title>Dynamic WCF Proxy</title><link>http://weblogs.asp.net/sfeldman/archive/2009/09/22/dynamic-wcf-proxy.aspx</link><pubDate>Wed, 23 Sep 2009 01:22:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7214438</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>5</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7214438</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7214438</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/09/22/dynamic-wcf-proxy.aspx#comments</comments><description>&lt;p&gt;Our new system is entirely based of services (SOA solution). From the day one we had an issue with Visual Studio auto-magically generated proxies and management of those as system grew. Solution at that time was to create clients of the services dynamically, but the knowledge of WCF we had was a minimal. Now, 6+ months later, we finally getting to the point where I am comfortable and pleased with the solution. The interesting part is that WCF had that option all the time, we were not just educated enough to see it. Now we are.&lt;/p&gt;  &lt;p&gt;The solution is to leverage &lt;i&gt;ChannelFactory &lt;/i&gt;provided by WCF and create a client proxy from an end point defined in configuration file. Let me show the process from the client perspective:&lt;/p&gt;  &lt;div style="border: 1px solid silver; margin: 20px 0px 10px; padding: 4px; overflow: auto; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 97.5%; font-family: 'Courier New',courier,monospace; direction: ltr; max-height: 200px; font-size: 8pt; cursor: text;" id="codeSnippetWrapper"&gt;   &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;     &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;var channel = &lt;span style="color: rgb(0, 0, 255);"&gt;new&lt;/span&gt; ChannelFactory&amp;lt;IWcfAppenderService&amp;gt;("WcfAppenderServiceEP").CreateChannel();&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;&lt;i&gt;channel&lt;/i&gt; is our proxy. Reading carefully &lt;a href="http://www.amazon.ca/Programming-WCF-Services-Juval-Lowy/dp/0596521308" mce_href="http://www.amazon.ca/Programming-WCF-Services-Juval-Lowy/dp/0596521308" target="_blank"&gt;Programming WCF Services&lt;/a&gt; book from Yuval Lowy (page 48), it is clear that a channel has to be closed, regardless of the state it’s found in after invocation (faulted or not).&lt;/p&gt;

&lt;div style="border: 1px solid silver; margin: 20px 0px 10px; padding: 4px; overflow: auto; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 97.5%; font-family: 'Courier New',courier,monospace; direction: ltr; max-height: 200px; font-size: 8pt; cursor: text;" id="codeSnippetWrapper"&gt;
  &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;
    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;using&lt;/span&gt;(channel &lt;span style="color: rgb(0, 0, 255);"&gt;as&lt;/span&gt; IDisposable)&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;          channel.Append(loggingEventDataDto);&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;.NET &lt;i&gt;using&lt;/i&gt; statement does the work.&lt;/p&gt;

&lt;p&gt;&amp;nbsp;&lt;/p&gt;

&lt;p&gt;This is it. To simplify the whole thing, we could intercept method calls on channel with a transparent proxy of ours and wrap with &lt;i&gt;using&lt;/i&gt; statements – that way a user does not have to remember to do it each time.&lt;/p&gt;

&lt;p&gt;Configuration file for a client would contain the minimal required information:&lt;/p&gt;

&lt;div style="border: 1px solid silver; margin: 20px 0px 10px; padding: 4px; overflow: auto; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 97.5%; font-family: 'Courier New',courier,monospace; direction: ltr; max-height: 200px; font-size: 8pt; cursor: text;" id="codeSnippetWrapper"&gt;
  &lt;div style="border-style: none; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;" id="codeSnippet"&gt;
    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;system.serviceModel&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;client&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;    &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;endpoint&lt;/span&gt; &lt;span style="color: rgb(255, 0, 0);"&gt;address&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="http://localhost:4268/WcfAppenderService.svc"&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;        &lt;span style="color: rgb(255, 0, 0);"&gt;binding&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="wsHttpBinding"&lt;/span&gt; &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;        &lt;span style="color: rgb(255, 0, 0);"&gt;contract&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="WcfAppender.Contracts.IWcfAppenderService"&lt;/span&gt; &lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;        &lt;span style="color: rgb(255, 0, 0);"&gt;name&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;="WcfAppenderServiceEP"&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;    &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;endpoint&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: rgb(244, 244, 244); width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;  &lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;client&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;

    &lt;pre style="border-style: none; margin: 0em; padding: 0px; overflow: visible; text-align: left; line-height: 12pt; background-color: white; width: 100%; font-family: 'Courier New',courier,monospace; direction: ltr; color: black; font-size: 8pt;"&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: rgb(128, 0, 0);"&gt;system.serviceModel&lt;/span&gt;&lt;span style="color: rgb(0, 0, 255);"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;
&lt;!--CRLF--&gt;&lt;/div&gt;
&lt;/div&gt;

&lt;p&gt;And the last missing part – contracts. A shared assembly with contracts would define all the service and data contracts. This is the only coupling between client and the server, which is logical, because contracts are coupling. &lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_000B2BE4.png" mce_href="http://weblogs.asp.net/blogs/sfeldman/image_000B2BE4.png"&gt;&lt;img src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_4B012D64.png" style="border: 0px none ; display: inline; margin-left: 0px; margin-right: 0px;" title="image" alt="image" mce_src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_4B012D64.png" align="right" border="0" height="207" width="159"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;I am not done with my WCF adventures, but I can definitely point to a great book by Yuval Lowy as a reference for WCF.&amp;nbsp; &lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7214438" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/.NET/default.aspx">.NET</category></item><item><title>Goodbye Launcy, Hello Executor</title><link>http://weblogs.asp.net/sfeldman/archive/2009/09/22/goodbye-launcy-hello-executor.aspx</link><pubDate>Tue, 22 Sep 2009 16:44:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7214103</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7214103</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7214103</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/09/22/goodbye-launcy-hello-executor.aspx#comments</comments><description>&lt;p&gt;I have recently switched from &lt;a href="http://www.launchy.net/" target="_blank"&gt;Launchy&lt;/a&gt; to &lt;a href="http://www.1space.dk/executor" target="_blank"&gt;Executor&lt;/a&gt; after &lt;a href="http://www.connicus.com/" target="_blank"&gt;Terry&lt;/a&gt; told me about it. I test drove it for a while and find it better than Launcy, which was a great tool. Time for myself to move on to a better tool.&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7214103" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/Other/default.aspx">Other</category></item><item><title>Pair-Programming Article</title><link>http://weblogs.asp.net/sfeldman/archive/2009/09/21/pair-programming-article.aspx</link><pubDate>Mon, 21 Sep 2009 21:11:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7213508</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>1</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7213508</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7213508</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/09/21/pair-programming-article.aspx#comments</comments><description>&lt;p&gt;While reading blogs during today morning, I read an interesting &lt;a href="http://www.nytimes.com/2009/09/20/jobs/20pre.html?_r=3" target="_blank"&gt;one&lt;/a&gt;, which captures the way I feel about Pair-Programming. I have my opinion before (old posts), and it’s slightly updated since then, but at the end I still think it’s a great way and not just to develop.&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7213508" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/Agile/default.aspx">Agile</category></item><item><title>TODOs are not forgotten</title><link>http://weblogs.asp.net/sfeldman/archive/2009/09/17/todos-are-not-forgotten.aspx</link><pubDate>Thu, 17 Sep 2009 17:13:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7209479</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>3</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7209479</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7209479</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/09/17/todos-are-not-forgotten.aspx#comments</comments><description>&lt;p&gt;We are using Hudson as a build server, and one of the lasts steps that were taken is to mark a build as ‘unstable’ when we pass a certain number of TODO comments in our code (an arbitrary number). While I am not a 100% sold on a number, I think it’s a good way of insuring things are not just marked and forgotten. Actually, we are not even tracking TODOs, but BROKEN_WINDOW comments, as those are definitely bad. Failing on HACK is another possibility. Visualization plays a significant role in my case (interpretation of things based on visualization), and here how it looks (green is all good, yellow is all passed, but number of comments has exceeded the limit).&lt;/p&gt;  &lt;p&gt;&lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_1C7946A4.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="image" border="0" alt="image" src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_3ED0DC1D.png" width="227" height="51" /&gt;&lt;/a&gt;&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7209479" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/Agile/default.aspx">Agile</category></item><item><title>Gallio Warning Output</title><link>http://weblogs.asp.net/sfeldman/archive/2009/09/14/gallio-warning-output.aspx</link><pubDate>Tue, 15 Sep 2009 00:23:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7205727</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7205727</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7205727</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/09/14/gallio-warning-output.aspx#comments</comments><description>&lt;p&gt;Today I was trying to figure out how to access output Gallio is using to render a warning message. According to &lt;a href="http://blog.bits-in-motion.com/2008/10/announcing-gallio-and-mbunit-v304.html" target="_blank"&gt;this&lt;/a&gt;, the Assert.Warning was replaced by TestLog.Warning.WriteLine. But for some reason that is not doing the job. Has anyone encountered similar problem?&lt;/p&gt;  &lt;p&gt;We run today into this problem, while trying to update our spec-based testing framework. We got the required details from with-in the base specification (test) leveraging TestContext.CurrentContext.LogWriter.Warnings, but with no success. Anyone, ideas?&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7205727" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/TDD/default.aspx">TDD</category></item><item><title>NHibernate Profiler</title><link>http://weblogs.asp.net/sfeldman/archive/2009/09/12/nhibernate-profiler.aspx</link><pubDate>Sat, 12 Sep 2009 06:30:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7201963</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>0</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7201963</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7201963</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/09/12/nhibernate-profiler.aspx#comments</comments><description>&lt;p&gt;Recently I had to update our domain model and it required some NHibernate profiling. I have installed trial version of &lt;a href="http://nhprof.com/" target="_blank"&gt;NHibernate Profiler&lt;/a&gt;, and it rocked. The fact that it was not only able to show what was going on, but also give suggestions how to improve NHibernate usage just rocked (unlimited records returned).&lt;/p&gt;  &lt;p&gt;I also loved straight, cut-the-bullshit communication with &lt;a href="http://ayende.com/Blog/" target="_blank"&gt;Oren&lt;/a&gt;, who has responded quickly (to the bug that I found). Worked for me, and we are going to purchase a few licenses.&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7201963" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/NHibernate/default.aspx">NHibernate</category></item><item><title>Wix Product Version with Build Script</title><link>http://weblogs.asp.net/sfeldman/archive/2009/09/01/wix-product-version-with-build-script.aspx</link><pubDate>Wed, 02 Sep 2009 04:49:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:7188787</guid><dc:creator>Sean Feldman</dc:creator><slash:comments>4</slash:comments><wfw:commentRss>http://weblogs.asp.net/sfeldman/rsscomments.aspx?PostID=7188787</wfw:commentRss><wfw:comment>http://weblogs.asp.net/sfeldman/commentapi.aspx?PostID=7188787</wfw:comment><comments>http://weblogs.asp.net/sfeldman/archive/2009/09/01/wix-product-version-with-build-script.aspx#comments</comments><description>&lt;p&gt;Our projects are deployed with MSIs. Each MSI file is appended with the product version number (regular staff – major, minor, build number, revision number). &lt;/p&gt;  &lt;p&gt;While this is enough for deployment, in production, it is hard to determine what product version is installed without either searching for assemblies to see the version, or some other piece of evidence. Today I decided to leverage Wix to generate the Product Version number, based on our NAnt script.&lt;/p&gt;  &lt;p&gt;Nant script has all parts of product version defined as follow:&lt;/p&gt;  &lt;pre style="border-bottom: #cecece 1px solid; border-left: #cecece 1px solid; padding-bottom: 5px; background-color: #fbfbfb; min-height: 40px; padding-left: 5px; width: 650px; padding-right: 5px; overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; padding-top: 5px"&gt;&lt;pre style="background-color: #fbfbfb; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  1: &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;property&lt;/span&gt; &lt;span style="color: #ff0000"&gt;name&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;version.major&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;value&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;1&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #fbfbfb; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  2: &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;property&lt;/span&gt; &lt;span style="color: #ff0000"&gt;name&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;version.minor&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;value&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;7&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #fbfbfb; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  3: &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;property&lt;/span&gt; &lt;span style="color: #ff0000"&gt;name&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;build.number&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;value&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;0&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;readonly&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;false&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #fbfbfb; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  4: &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;property&lt;/span&gt; &lt;span style="color: #ff0000"&gt;name&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;svn.revision&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;value&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;0&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;readonly&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;false&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #fbfbfb; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  5: 
&lt;/pre&gt;&lt;pre style="background-color: #ffff00; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  6: &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;property&lt;/span&gt; &lt;span style="color: #ff0000"&gt;name&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;project.version.full&amp;quot;&lt;/span&gt; 
&lt;/pre&gt;&lt;pre style="background-color: #ffff00; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  7:           &lt;span style="color: #ff0000"&gt;value&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;${version.major}.${version.minor}.${build.number}.${svn.revision}&amp;quot;&lt;/span&gt; 
&lt;/pre&gt;&lt;pre style="background-color: #ffff00; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  8:           &lt;span style="color: #ff0000"&gt;dynamic&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;true&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;readonly&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;false&amp;quot;&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;/pre&gt;

&lt;p&gt;Next step was updating Wix installer project file to include an external include file with a defined variable for product version, called ProductVersion, and apply that to project. Here’s partial Wix installer file:&lt;/p&gt;

&lt;pre style="border-bottom: #cecece 1px solid; border-left: #cecece 1px solid; padding-bottom: 5px; background-color: #ffffff; min-height: 40px; padding-left: 5px; width: 650px; padding-right: 5px; overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; padding-top: 5px"&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  1: &lt;span style="color: #0000ff"&gt;&amp;lt;?&lt;/span&gt;xml version=&amp;quot;1.0&amp;quot; encoding=&amp;quot;UTF-8&amp;quot;&lt;span style="color: #0000ff"&gt;?&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  2: &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Wix&lt;/span&gt; &lt;span style="color: #ff0000"&gt;xmlns&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;http://schemas.microsoft.com/wix/2006/wi&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;xmlns&lt;/span&gt;:&lt;span style="color: #ff0000"&gt;iis&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;http://schemas.microsoft.com/wix/IIsExtension&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  3: 
&lt;/pre&gt;&lt;pre style="background-color: #ffff00; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  4:   &lt;span style="color: #0000ff"&gt;&amp;lt;?&lt;/span&gt;define build_dir = &amp;quot;$(var.ProjectDir)..\..\build\compile&amp;quot;&lt;span style="color: #0000ff"&gt;?&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffff00; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  5:   &lt;span style="color: #0000ff"&gt;&amp;lt;?&lt;/span&gt;define documentation_dir = &amp;quot;$(var.ProjectDir)..\..\docs&amp;quot;&lt;span style="color: #0000ff"&gt;?&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffff00; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  6: 
&lt;/pre&gt;&lt;pre style="background-color: #ffff00; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  7:   &lt;span style="color: #0000ff"&gt;&amp;lt;?&lt;/span&gt;include $(var.build_dir)\ProductVersion.wxi &lt;span style="color: #0000ff"&gt;?&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  8: 
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  9:   &lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Product&lt;/span&gt; &lt;span style="color: #ff0000"&gt;Id&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;5646ced5-d897-4978-b1d6-338e5baadbe9&amp;quot;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt; 10:        &lt;span style="color: #ff0000"&gt;Name&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;Cortex Central Business System $(var.ProductVersion)&amp;quot;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt; 11:        &lt;span style="color: #ff0000"&gt;Language&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;1033&amp;quot;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt; 12:        &lt;span style="color: #ff0000"&gt;Version&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;$(var.ProductVersion)&amp;quot;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt; 13:        &lt;span style="color: #ff0000"&gt;Manufacturer&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;Cortex Business Solutions&amp;quot;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt; 14:        &lt;span style="color: #ff0000"&gt;UpgradeCode&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;790b1905-c843-4973-a078-79874a7f30f2&amp;quot;&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt; 15: &lt;/pre&gt;&lt;/pre&gt;

&lt;p&gt;Include file, ProductVersion.wxi is the one that should contain variable &lt;em&gt;ProductVersion&lt;/em&gt;. This include is generated by nant script, injecting nant &lt;em&gt;project.version.full &lt;/em&gt;variable.&lt;/p&gt;

&lt;p&gt;Nant script to generate Wix include file:&lt;/p&gt;

&lt;pre style="border-bottom: #cecece 1px solid; border-left: #cecece 1px solid; padding-bottom: 5px; background-color: #ffffff; min-height: 40px; padding-left: 5px; width: 650px; padding-right: 5px; overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; padding-top: 5px"&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;&lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;echo&lt;/span&gt; &lt;span style="color: #ff0000"&gt;file&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;&amp;quot;${build.compile.dir}\ProductVersion.wxi&amp;quot;&lt;/span&gt; &lt;span style="color: #ff0000"&gt;message&lt;/span&gt;=&lt;span style="color: #0000ff"&gt;'&amp;amp;lt;?xml version=&amp;quot;1.0&amp;quot; encoding=&amp;quot;utf-8&amp;quot;?&amp;amp;gt;&amp;amp;#xA;&amp;amp;#xD;&amp;amp;lt;Include&amp;amp;gt;&amp;amp;#xA;&amp;amp;#xD;&amp;amp;lt;?define ProductVersion=&amp;quot;${project.version.full}&amp;quot;?&amp;amp;gt;&amp;amp;#xA;&amp;amp;#xD;&amp;amp;lt;/Include&amp;amp;gt;'&lt;/span&gt; &lt;span style="color: #0000ff"&gt;/&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;&lt;/pre&gt;&lt;/pre&gt;

&lt;p&gt;Which results in a file, that contains the required product version variable for Wix installer:&lt;/p&gt;

&lt;pre style="border-bottom: #cecece 1px solid; border-left: #cecece 1px solid; padding-bottom: 5px; background-color: #ffffff; min-height: 40px; padding-left: 5px; width: 650px; padding-right: 5px; overflow: auto; border-top: #cecece 1px solid; border-right: #cecece 1px solid; padding-top: 5px"&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;&lt;span style="color: #0000ff"&gt;&amp;lt;?&lt;/span&gt;xml version=&amp;quot;1.0&amp;quot; encoding=&amp;quot;utf-8&amp;quot;&lt;span style="color: #0000ff"&gt;?&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;&lt;span style="color: #0000ff"&gt;&amp;lt;&lt;/span&gt;&lt;span style="color: #800000"&gt;Include&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;  &lt;span style="color: #0000ff"&gt;&amp;lt;?&lt;/span&gt;define ProductVersion=&amp;quot;1.7.1234.4321&amp;quot;&lt;span style="color: #0000ff"&gt;?&amp;gt;&lt;/span&gt;&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;&lt;span style="color: #0000ff"&gt;&amp;lt;/&lt;/span&gt;&lt;span style="color: #800000"&gt;Include&lt;/span&gt;&lt;span style="color: #0000ff"&gt;&amp;gt;&lt;/span&gt;
&lt;/pre&gt;&lt;pre style="background-color: #ffffff; margin: 0em; width: 100%; font-family: consolas,&amp;#39;Courier New&amp;#39;,courier,monospace; font-size: 12px"&gt;&lt;/pre&gt;&lt;/pre&gt;

&lt;p&gt;Once MSI is installed, Add/Remove programs contains the name with the version:&lt;/p&gt;

&lt;p&gt;&lt;a href="http://weblogs.asp.net/blogs/sfeldman/image_02299A23.png"&gt;&lt;img style="border-bottom: 0px; border-left: 0px; display: inline; border-top: 0px; border-right: 0px" title="image" border="0" alt="image" src="http://weblogs.asp.net/blogs/sfeldman/image_thumb_0D55B51E.png" width="733" height="136" /&gt;&lt;/a&gt;&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=7188787" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/sfeldman/archive/tags/.NET/default.aspx">.NET</category></item></channel></rss>
