Monday, November 23, 2009

Project Creation Failed - BizTalk 2009 in Visual Studio 2008

I came across a problem today regarding the creation of a new BizTalk project in VS2008.

The symptom of the problem is when you try to create a project using the "Empty BizTalk Project" template, Visual Studio barfs on you and presents a "project creation failed' message in the message bar at the bottom of the screen. This behavior will occur when a patch is installed in Visual Studio. The patch installation process removes the .btproj type from the list of possible projects in the registry, causing this error to happen. So if you patch or apply a service pack to Visual Studio, be sure to check that you can still create BTS projects.

The solution is simple: update the registry entry to include the .btproj project type. The key is at:

[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\VisualStudio\9.0\Projects\{FAE04EC0-301F-11d3-BF4B-00C04F79EFBC}]

The entry is "PossibleProjectExtensions". Just change the value to add ";btproj" at the end and that will fix the problem.

Many articles out there recommend doing a Repair install of BizTalk to solve this problem. That would be big time over-kill as the only helpful thing that it would do is to update the registry entry as mentioned above. May as well go straight to the source of the problem and save yourself a little time and frustration. Of course, if you don't have the guts to touch the registry (and really, who doesn't?) then repair away...

Here's an article I found that presents this solution:

http://blogs.msdn.com/biztalkcrt/archive/2009/08/21/visual-studio-2008-fails-to-create-open-biztalk-projects.aspx

Don't Forget to use the Correct XPath Selector!

Working with the Business Rules Engine in BizTalk is more than just a little challenging at times. The tool is incredible in terms of what it can do and it is fast. The problem is that it isn't always the most intuitive thing to work with. I've been struggling with it a bit lately and found a very basic but simple truth--when having the BRE analyze a document for you, make sure you apply the correct XPath Selector when selecting nodes or creating Vocabularies.

In my most recent project, I have a document that contains a quantity node. What I wanted the BRE to do was to calculate the sum of all the quantities beneath a parent node and put the result in yet another node. The format was something like this:


<shipments>
<batch>
<shipment>
<quantityX>3</quantityX>
<quantityY>4</quantityY>
<shipment>
<shipment>
...Another shipment
<shipment>
<quantities>
<totalx>5</totalX>
<totaly>6</totalY>
<quantities>
</batch>
<batch>
...Another batch
</batch>
</shipments>


The rule followed this logic:

IF
/shipments/batch/quantities/totalX is equal to '0'

THEN
/shipments/batch/quantities/totalX = CalculateSum(
"/shipments/batch",
"./shipment/quantityX")

The CalculateSum function was simply .NET code that accepted a reference node and calculated the sum of all the items that matched an XPath expression beneath that node.

The problem here was the selector used for a quantityX node vs. the totalX node. If you simply "drag-and-drop" fields from a schema into the rules it will give you something like that above. However, you'll get an incorrect total because the rules engine creates an object in memory based on the selector. You can easily see which selector is being used by looking at the XPath Selector property when you select a node (lower left portion of the screen in the Business Rules Composer). If the Selector is different between parts of your IF/THEN work, you'll find that things won't always match up.

What had happened here was that the sum was being built on a selector of "/shipments/batch" with an XPath field of "quantityX". The rules engine was referencing a selector of "/shipments/batch/quantities". Since these were different, not all the quantities where added correctly. The rules engine wasn't passing the correct data into our CalculateSum function.

The solution is pretty simple, but not intuitive. You simply need to structure your XPath Selector and XPath Fields so that the selectors are holding the same reference point.
In the above example the Selector would be "/shipments/batch" for both items. The XPath fields would then be altered to reference from that point. For the total line, the XPath field would be "quantities/totalX". For the quantity line to be added the XPath field would be "/shipment/quantityX". But most importantly, both fields use the SAME XPATH SELECTOR!