Adapters, BizTalk, BizTalk Server 2010, Pipeline Components

Threading issues in WCF-Adapter Body Path

(I originally wrote this the 5th of May 2014 but did not publish it. I only sent it as internal feedback at the time. I am now choosing to publish it anyway since there has now been ample time for Microsoft to fix the problem)

The scenario

I am using the BizTalk Server WCF adapters in a solicit-response send port and I am getting the response using the Body Path configuration option.

The problem

Main issues that using the WCF Adapter – Messages tab – Inbound BizTalk message body – Path, configured with an XPath and String Node Encoding configuration options produces under load:

  • Deserialization fails producing random and irregular errors seemingly caused by the stream position jumping to an erroneous location.
  • The adapter returns the wrong mismatched response (!!!) back to the pipeline

For the first issue, the following is the error message (or an example of):

System.Xml.XmlException: Start element ‘To s:mustUndersta’ does not match end element ‘sendMessageResult’. Line 1, position 951.

If you catch it and look at the XmlExceptions call stack, you will find this:

at System.Xml.XmlExceptionHelper.ThrowXmlException(XmlDictionaryReader reader, String res, String arg1, String arg2, String arg3)
at System.Xml.XmlUTF8TextReader.ReadEndElement()
at System.Xml.XmlUTF8TextReader.Read()
at System.Xml.XmlSubtreeReader.Read()
at Microsoft.BizTalk.Adapter.Wcf.Runtime.BinaryReaderStream.ReadContentAsString(Byte[] buffer, Int32 offset, Int32 count)
… (call stack continues with custom code)

For the second issue, you will NOT find anything wrong in BizTalk. It will simply associate the wrong response with the wrong request and return the wrong message! This is far worse than the first exception in my opinion since it effectively, successfully and quietly sends back someone else’s response to a caller. When examining it closer it does not appear to swap responses, it just hands one response back to more then one caller, and the other responses simply disappear and are never used. BizTalk will not discover this (at least not in my case where I am always getting the same response MessageType back from the port), only whatever application logic that are either built into BizTalk by you or the system or application calling BizTalk or human intervention might discover what has happened. Perhaps when getting the wrong data back.

Guide to reproduce

Steps (that I took) to build up and test a solution to reproduce the error:

  1. Download the Windows Communication Foundation (WCF) and Windows Workflow Foundation (WF) Samples for .NET Framework 4, http://www.microsoft.com/en-us/download/details.aspx?id=21459 (this is not required, though it gives us a simple starting point.
  2. Use the Self-Host sample found at …WCFBasicServicesHostingSelfHostCS and described at http://msdn.microsoft.com/en-us/library/vstudio/ms733765%28v=vs.100%29.aspx. Basically this is the Calculator sample hosted in a Console app (this is not required for repro, it is just for simplicity).
  3. Test it to make sure it’s working.
  4. Extend the Client somewhat to get a bit more simultaneous and multi-threaded. I will show this later but essentially I am using the Calculator Add method and from several threads to create some load.
  5. Test it again and see there are no errors.
  6. Create a receive port and receive location, as well as a send port in BizTalk and route the message through so that BizTalk is between the client and the service.
  7. Test it and make sure it’s working (at this point I still have no issues).
  8. Now consume the Calculator service metadata in a BizTalk project to create the schema for the Add, Subtract, etc methods and their responses. Create a simple BizTalk flat file schema (we need something to store the XPath string we extract), create a pipeline with the Flat File Disassembler configured with that schema (we need to disassemble the string we receive from the adapter into that schema), and then a Map mapping from that schema to the original Calculator service schema and the AddResponse message (we want the client to get the correct response back).
  9. Compile, Deploy and wire everything up inside Biztalk (ie re-configure the ports created to use the receive pipeline we created, and the map we created.
  10. Also configure the send ports WCF Adapter – Messages tab – Inbound BizTalk message body – Path,  with an XPath and String Node Encoding.
  11. Run a single message through to make sure everything works. In fact, run it non-multi-threaded with several messages and make sure it works (which for me it did).
  12. Now run multiple threads to create a load on the system.
  13. Watch as the previously described errors appear. At first it works fine, then I begin getting responses I did not expect (2+2 = 8?) and then I run into the ‘Start element ‘…’ does not match end element ‘…’ exception.

An in-depth look

The service

There is nothing to see here really. It’s your most basic WCF service, same as it comes with the sample (slightly abbreviated in the sample below).

Code

namespace Microsoft.ServiceModel.Samples
{
    // Define a service contract.
    [ServiceContract(Namespace="http://Microsoft.ServiceModel.Samples")]
    public interface ICalculator
    {
        [OperationContract]
        double Add(double n1, double n2);
       ...
    }

    // Service class which implements the service contract.
    // Added code to write output to the console window
    public class CalculatorService : ICalculator
    {
        public double Add(double n1, double n2)
        {
            double result = n1 + n2;
            Console.WriteLine("Received Add({0},{1})", n1, n2);
            Console.WriteLine("Return: {0}", result);
            return result;
        }
        ...

        // Host the service within this EXE console application.
        public static void Main()
        {
            // Create a ServiceHost for the CalculatorService type.
            using (ServiceHost serviceHost = new ServiceHost(typeof(CalculatorService)))
            {
                // Open the ServiceHost to create listeners and start listening for messages.
                serviceHost.Open();

                // The service can now be accessed.
                Console.WriteLine("The service is ready.");
                Console.WriteLine("Press <ENTER> to terminate service.");
                Console.WriteLine();
                Console.ReadLine();

            }
        }

    }

}

Config

This is basically the same as the sample, the only exception is that I removed security (simply because that’s what the scenario I was testing had).

    <bindings>
      <wsHttpBinding>
        <binding name="wsConfig">
          <security mode="None" />
        </binding>
      </wsHttpBinding>
    </bindings>
    
    <services>
      <service name="Microsoft.ServiceModel.Samples.CalculatorService" behaviorConfiguration="CalculatorServiceBehavior">
        <host>
          <baseAddresses>
            <add baseAddress="http://localhost:8000/ServiceModelSamples/service"/>
          </baseAddresses>
        </host>
        <!-- this endpoint is exposed at the base address provided by host: http://localhost:8000/ServiceModelSamples/service  -->
        <endpoint address="" binding="wsHttpBinding" contract="Microsoft.ServiceModel.Samples.ICalculator" bindingConfiguration="wsConfig"/>
        <!-- the mex endpoint is exposed at http://localhost:8000/ServiceModelSamples/service/mex -->
        <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/>
      </service>
    </services>

    <!--For debugging purposes set the includeExceptionDetailInFaults attribute to true-->
    <behaviors>
      <serviceBehaviors>
        <behavior name="CalculatorServiceBehavior">
          <serviceMetadata httpGetEnabled="True"/>
          <serviceDebug includeExceptionDetailInFaults="False"/>
        </behavior>
      </serviceBehaviors>
    </behaviors>

The client

Here I have added some multi-threading aspects on top of the sample code.

Code

namespace Microsoft.ServiceModel.Samples
{
    //The service contract is defined in generatedClient.cs, generated from the service by the svcutil tool.

    //Client implementation code.
    class Client
    {
        static void Main()
        {
            Console.WriteLine("Press ENTER to start!");
            Console.ReadLine();

            List<Task> tList = new List<Task>();

            Action a = () =>
            {
                Random random = new Random();
                int mseconds = random.Next(1, 100) * 10;
                System.Threading.Thread.Sleep(mseconds);

                // Create a client
                CalculatorClient client = new CalculatorClient();

                for (int i = 0; i < 10; i++)
                {
                    double result = client.Add(Convert.ToDouble(i), Convert.ToDouble(i));
                    double localResult = Convert.ToDouble(i) + Convert.ToDouble(i);
                    if (result != localResult)
                        Console.WriteLine("{0} !!!!!!!!!!!!!!!!!!! {1}", result, localResult);
                }

                //Closing the client gracefully closes the connection and cleans up resources
                client.Close();
            };

            for (int i = 0; i < 100; i++)
            {
                Task t = new Task(a);
                t.Start();
                tList.Add(t);
            }

            Task.WaitAll(tList.ToArray());

            Console.WriteLine();
            Console.WriteLine("Press <ENTER> to terminate client.");
            Console.ReadLine();
        }
    }
}

As you can see it does not take much, that is – I am not running thousands of threads here, in fact in total I only make a thousand calls, and I get an error every time I have run the app so far.

Let’s examine this a little bit closer. As you can see I am doing the following.

double result = client.Add(Convert.ToDouble(i), Convert.ToDouble(i));
double localResult = Convert.ToDouble(i) + Convert.ToDouble(i);
if (result != localResult)
    Console.WriteLine("{0} !!!!!!!!!!!!!!!!!!! {1}", result, localResult);

That is, I am sending the addition of the two numbers to the service, and the doing the same calculation locally. Then I compare the result I get from the service with my local result. If they do not match, I print the fact.

Config

The clients config (by necessity) matches that of the services. It is available in the download but I am not including a dump of it.

The BizTalk solution

To be able to reproduce the problem in a portable manner I created a simple BizTalk solution.

Visual Studio Solution

At this point I have got three projects in Visual Studio, of which my BizTalk project is the first in the below screenshot.

image

It contains the following artifacts:

  • CalculatorService_microsoft_servicemodel_samples.xsd – the schema for the Calculator service that was automatically generated for me (I removed the other generated artifacts as they were non-essential for the purpose of this repro).
  • FFAddResult.xsd – a simple flat file schema that will act as the temporary carrier of the result after I extract it from the incoming xml response until the Map transforms the message back into an AddResponse message.
  • Map1.btm – a map that transforms from FFAddResult to CalculatorService_microsoft_servicemodel_samples#AddResponse.
  • ReceiveFFAddResultPipeline.btp – a disassemble pipeline that will take the incoming string and create an FFAddResult xml message.

The FFAddResult.xsd is extremely simple.

image

As is the Map1.btm.

image

BizTalk Server configuration

In BizTalk I have a receive port and a receive location with very simple configuration; PassThruReceive and PassThruTransmit pipelines, WCF-Custom WS-Http binding (so I can host it in BizTalk and have fewer moving pieces – not essential to the repro, just easier to move around).

image

Everything is according to default configuration except no security.

image

No behaviors, no special parts of the message extracted here or non of that (the xpath is on the send port receive).

Speaking of which, the send port (in the configuration that give me issues) is a solicit-response port running the WCF-WSHttp adapter (to be frank, I have not tested other adapters/bindings) and running the receive pipeline we created.

image

Receive pipeline has trivial config.

image

We have our inbound map configured.

image

And a filter on the receive port name that I won’t include a screenshot of.

The adapter configuration is set to forward the call to the backend service add method.

image

It also has security set to none (not shown in screenshot) as well as on the Messages tab having the Inbound BizTalk message body – Path,  set to an XPath and String Node Encoding. the xpath in this case is /*[local-name()=’AddResponse’ and namespace-uri()=’http://Microsoft.ServiceModel.Samples’]/*[local-name()=’AddResult’ and namespace-uri()=’http://Microsoft.ServiceModel.Samples’%5D, which will forward the string value inside the AddResult node for the pipeline.

Executing the failing code

Below is a screenshot of the app running, where as you can notice, the response is not as expected.

image

As mentioned before, the app gets a number if these mismatched erroneous responses and then crashes (due to the previously mentioned exception and the sample apps lack of exception handling).

Here is also some sample output from the service (in this case the screenshot is from a test where it has been able to run to completion and what we are seeing are the final tasks/threads doing their last calls).

image

The workaround

Ok, now that we are aware of the failing component. Can we work around it?

Enter the XPathExtractor pipline component, based of some of BizTalks hidden gems.

Essentially, the solution is – don’t use the BizTalk message body – Path option. Instead, just get the body and extract the XPath you want in a pipeline component. Although I have not done any performance comparisons but I am not expecting the code to have any noticeably difference in performance. You might want to think twice before running very large message through it (as will become evident in the source code included later). But I think the same is true for using the adapters Body Path option, which (as we can see from the callstack the exception had) also gets the content of the node as a string.

I created a new port and a new pipeline, getting only he body in the adapter and instead extracting the string in the pipeline. Configuration as follows.

image

The Execute method of the pipeline component does this:

Stream stream = new ReadOnlySeekableStream(pInMsg.BodyPart.GetOriginalDataStream());

XmlTextReader xmlTextReader = new XmlTextReader(stream);
XPathCollection xPathCollection = new XPathCollection();
xPathCollection.Add(this.XPath);
XPathReader xPathReader = new XPathReader(xmlTextReader, xPathCollection);

bool matchFound = false;
while (xPathReader.ReadUntilMatch())
{
    if (xPathReader.Match(0))
    {
        string val = xPathReader.ReadString();
        stream = new VirtualStream(new MemoryStream(System.Text.Encoding.GetEncoding(this.Encoding).GetBytes(val)));
        matchFound = true;
        //break; // don't break, read to end to play nice with other components 
                    // that have a streaming approach and might want to process the full message
    }
}

if (!matchFound)
    throw new Exception("xPathReader.ReadUntilMatch() found no match");

stream.Seek(0, SeekOrigin.Begin);
pInMsg.BodyPart.Data = stream; 
pContext.ResourceTracker.AddResource(xPathReader);

I have run this a number of times and never as of yet gotten the same exception.

Remember that if you have any objections on the code in this component (like why is he adding the xPathReader to the resourceTracker, or whatever else) that this is not used when I get the issues, this is used to get around them.

Quick performance comparison

Quick and dirty indeed. This has no intention to go deep or be thorough. With that out of the way…

Without Adapter Body Path

Red is proc. Blue is message publishing rate. Green is memory (not sure I got the right counter for that one, but I’ll ignore that for putting together this post).

image

With Adapter Body Path

image

It’s not really applicable to performance measures because it fails quite early. The most interesting thing with this graph I would say is that I don’t have to reach higher than 4 simultaneous request to start getting issues.

With XPath extraction in pipeline component

image

Also note that due to the randomness of my Task execution this may not be altogether comparable, so just keep that in mind. I post it mainly to illustrate that I am not running a really massive load, to show how early it fails, and to note that the workaround is not terrible.

My environment

My repro environment is a Hyper-V virtual machine with 4608MB allocated running alone on a 8 core host machine. It’s BizTalk Server 2010 with CU6, Windows Server 2008 R2 fully patched, SQL Server 2008 R2 SP1 (yes, I am aware there is a later service pack, but at the time it was not applied. I would be very surprised if it makes a difference). I have reproduced this error on several environments so it’s not isolated to mine. Although I am running BizTalk Server 2010 I would not be surprised to find this in BizTalk Server 2009, BizTalk Server 2006 R2 or even BizTalk Server 2013. Though I can neither confirm not deny since I have not tried.

Download

The full source code and bindings for everything I have mentioned in this article, including the code for the pipeline component, is available for download here.

BizTalk, BizTalk Server 2013, Licensing

BizTalk Server 2013 Developer Edition arrives

Microsoft BizTalk Server 2013 Developer Edition New SKUs and Changes

Effective November 1, 2013, Microsoft BizTalk Server (BTS) 2013 Developer Edition licenses will be available under the Developer Tools license model in the Open, Select Plus and Worldwide Government Partner programs. Previously offered as a free download in prior BTS versions, the new BTS 2013 Developer Edition offers the full functionality of the
BTS 2013 Enterprise Edition, licensed for development and test use only, and includes the newly released Host Integration Server (HIS) 2013 software.

Source: http://microsoft.also.ch/fileadmin/Dateien/Dokumente/Pricelist/November_2013_Price_List_Guide.pdf, http://www.enpointegov.com/newsletter/october2013

You will also find it if you run the Microsoft License Advisor at http://mla.microsoft.com/.

image

The Developer Tools license model

Previously with BizTalk Server 2010 you have bought BizTalk Server Licenses for servers only (Branch, Standard and Enterprise). The Developer Edition was free. With 2013 you must purchase this license per user, if they do NOT have MSDN. This is a per user license.

You must acquire a license for each user you permit to access or use the software. You may install any number of copies on any number of devices for access and use by one user to design, develop, test and demonstrate programs. Only licensed users may access the software.

Source: https://www.microsoft.com/licensing/about-licensing/product-licensing.aspx

My interpretation of “access the software” (but I am not a license expert!) is that it is ok for BizTalk Server to exist in a test environment where it routes traffic and perform integrations to and from other systems that at their end have users, devs or admins that are not licensed. It is also ok for other users of the same server to access the server where BizTalk is installed to, for example, administer Windows (as long as that in itself is properly licensed). The limiting factor are the users that in some form access the BizTalk Server software itself. Such as deploy, configure, administer or in other ways interact with the BizTalk Server GUIs or services.

Price Lists

https://mspartner.microsoft.com/en/us/pages/licensing/price-lists.aspx

Target prices seems to be around $37 Estimated Retail Price (ERP). https://mspartner.microsoft.com/en/us/Pages/Licensing/Downloads/open-license-estimated-retail-price-list.aspx

image

I have also seen $36 for price level C. https://mspartner.microsoft.com/en/us/Pages/Licensing/Downloads/open-license-level-c-estimated-retail-price-list.aspx

MSDN

To those with an MSDN subscription (http://msdn.microsoft.com/subscriptions) the list of subscription types that has access to this seems to be quite large:

VS Pro with MSDN (VL)
VS Pro with MSDN Premium (Empower)
VS Pro with MSDN Premium (MPN)
VS Test Pro with MSDN (Retail)
VS Test Pro with MSDN (VL)
VS Ultimate with MSDN (MPN)
VS Ultimate with MSDN (NFR FTE)
VS Ultimate with MSDN (Retail)
VS Ultimate with MSDN (VL)
BizSpark
BizSpark Admin
Designer AA
DreamSpark Premium
DreamSpark Standard
MSDN Platforms
VS Premium with MSDN (MPN)
VS Premium with MSDN (Retail)
VS Premium with MSDN (VL)
VS Pro with MSDN (Retail)

See screenshot:

image

How do I get it?

Summarizing from above you would either have an eligible MSDN subscription, or you get it through traditional volume licensing channels.

HTH,
/Johan

BizTalk, WCF

BizTalk Send Ports, WS-Addressing, ClientVia and non-http prefixed To headers, Part 2

In a previous post I explained how we had a need to use the WS-Addressing To header to send a non-http prefixed URI, such as urn:company/path/subpath/Service1, and how that was supported, after a fashion, out of the box in BizTalk Server. It did however come with the limitation of not being able to edit the WCF config in the BizTalk Server Administration Console GUI once you loaded it from a binding file. I don’t like limitations.

In this post I’ll show you how you can create a very simple WCF behavior to help you to set a RemoteAddress EndpointAddress Uri to be able to accomplish the same thing, while still being able to continue to edit the port configuration.

WCF behaviors allows you to intercept and inspect or alter messages or metadata, or in other ways modify the runtime behavior or processing of the same as they are sent or received. In this case we are creating a client behavior.

The behavior is in essence very very simple, it’s only purpose is to alter the endpoint address at runtime. The place where I choose to implement this is in the ApplyClientBehavior method of the IEndpointBehavior interface.

void IEndpointBehavior.ApplyClientBehavior(ServiceEndpoint serviceEndpoint, ClientRuntime behavior)
{
    serviceEndpoint.Address = new System.ServiceModel.EndpointAddress(this.Uri);
}

Incidently, I borrowed this implementation with pride from the ClientVia behavior that comes with the .NET Framework. Apart from the fact that that behaviors sets the ClientRuntime.Via property and this sets the ServiceEndpoint.Address property the implementation is very close to exactly the same.

This allows you to configure BizTalk in the following manner.

The “Address (URI)” property can be set to anything (as long as it is http or https prefixed), since it will later be overridden.

image

In the behaviors section we now have two behaviors, clientVia:

image

and the new one I created, which I called remoteAddress:

image

clientVia is configured as the actual URI of the service we need to call, while the remoteAddress behaviors is configured with the value we want to have in the To header.

The solution contain three files of interest.

image

The App.config file holds a snippet of configuration that needs to be placed in machine.config or in the BizTalk WCF-Custom WCF extension part of the Send Handler of the host that handles the WCF calls being made. It exists to make the behavior available to the BizTalk process and looks like this:

<extensions>
  <behaviorExtensions>
    <add name="remoteAddress" type="bLogical.BizTalk.WSAHelper.RemoteAddressElement, bLogical.BizTalk.WSAHelper, Version=1.0.0.0, Culture=neutral, PublicKeyToken=3672865486d21857"/>
  </behaviorExtensions>
</extensions>

It points to the RemoteAddressElement class, whose responsibility it is to point out the type of the behavior and create new instances.

The RemoteAddressBehavior then in turn does the already above explained logic.

The project and code is available here.

I suppose a custom pipeline component setting the Address, or a Dynamic Send port for easier cases of configuration might also do the trick.

BizTalk, WCF

BizTalk Send Ports, WS-Addressing, ClientVia and non-http prefixed To headers

Through WS-Addressing services can require a certain value in the ws-addressing <wsa:to> SOAP header. WCF has full support for this. This support is inherited by the WCF-Adapters. When using WS-addressing in a BizTalk Server Send Port what you enter in the “Address (URI)” of the WCF adapters configuration will also be the value that ends up in the <to> header.

Like so:

image 

This will produce the following. Other headers and body removed for clarity.

<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope" xmlns:a="http://www.w3.org/2005/08/addressing">
  <s:Header>
    <a:To s:mustUnderstand="1">http://localhost:8990/Service1</a:To>
  </s:Header>
  <s:Body>
    ...
  </s:Body>
</s:Envelope>

If you need to have a different value in the <to> header than the actual address that the service is hosted at it becomes a little bit trickier. You need to use the WCF-Custom adapter and add the ClientVia behavior. The value configured as the “Address (URI)” will still end up as the value in the <to> header, but the actual URI that the call will be made to will be the value you configure in the ClientVia’s viaUri property.

Like so:

image image

This will produce the following (again cleaned for clarity):

<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope" xmlns:a="http://www.w3.org/2005/08/addressing">
  <s:Header>
    <a:To s:mustUnderstand="1">http://somedummyvalue/</a:To>
  </s:Header>
  <s:Body>
    ...
  </s:Body>
</s:Envelope>

Now, as long as the value that you want in the <to> header is http or https (depending on the bindings security settings) then you are fine. However, if you end up needing to have a value in your <to> header that looks for example like this: urn:company/path/subpath/Service1, then you’re in trouble.

You will get an error dialog saying that The specified address is invalid. Invalid address scheme; expecting “http” scheme.

image

Why? Because BizTalk Server in its diligence to help you configure things correctly will force you to enter an URI that is prefixed with either http or https (again, depending on the security setting of the binding). There is no way for you to configure a non-http prefixed port in the adapter GUI (that I know of).

A colleague of mine, Gustav Granlund, experienced this issue and found a solution: you can coup it in through a binding file, and the runtime will accept it. Doing this you can enter a “Address (URI)” like so:

image

And you are then able to send a message that looks like this (to an address of http://localhost:8990/Service1):

<s:Envelope xmlns:s="http://www.w3.org/2003/05/soap-envelope" xmlns:a="http://www.w3.org/2005/08/addressing">
  <s:Header>
    <a:To s:mustUnderstand="1">urn:company/path/subpath/Service1</a:To>
  </s:Header>
  <s:Body>
    ...
  </s:Body>
</s:Envelope>

The caveat is that after having done this you cannot open and change WCF adapter settings in the port through the administration console GUI and keep the urn:company/path/subpath/service1 style URI. But, as mentioned, BizTalk will happily run with it. In a follow up post I examine another option.

HTH,

/Johan

Azure, BizTalk, News, Presentation

BizTalk Server futures–Presentations from TechEd North America

I have already relayed this information to so many, and given the links to more, that I though I’d put them up here for easy access. There is much and more to be written about the content, but I’ll settle for this. Information has been available around BizTalk Server 2010 R2 for some time, but it got much more real and saw some things unveiled not previously mentioned or detailed. In short:

Application Integration Futures: The Road Map and What’s Next on Windows Azure: Video Slides

Building Integration Solutions Using Microsoft BizTalk On-Premises and on Windows Azure: Video Slides

BizTalk, Development, Orchestrations

You do not (always) need a correlation set to promote properties in a message sent from an orchestration

It is common knowledge that you use a Correlation Set to correlate message by creating an instance subscription that subscribes to hopefully unique properties. The subscription is created by pointing out a number of properties that you want to use for the correlation. Then when a message is published to the MessageBox that matches that subscription it is delivered to the orchestration. What most experienced developers knows is that Correlation Sets also promote properties as they are initialized; as the first message is sent by the orchestration. There is no other way to manually select properties to be promoted in a message sent from an orchestration. However, do not think that manual promotion through the use of Correlation Sets is the only way that properties will get promoted when published by an orchestration. It is not.

If the property has a Property Schema Base of MessageDataPropertyBase as below, then you do not need a correlation set. You only need to send the message and promotion will be taken care of automatically.

image

Only if you want to promote a property that has a Property Schema base of context type (MessageContextPropertyBase or PartContextPropertyBase) do you need to manually provide a Correlation Set to make sure promotion happens.

image

By *ContextPropertyBase we mean that its origin cannot be found within the data of the message, but is expected to be promoted to the context by another component, such as the adapter, a pipeline component or something else – in this case an orchestration, do you need to manually take action to make sure it is promoted as you publish a message to the MessageBox from an orchestration. And in this case you need a Correlation Set.

Of course if you were to be actually doing correlation with the Correlation Set and not only using it to promote a property then you would still want to Initialize a Correlation Set containing all properties you want to use regardless if these have their origin in the message data or not.

Azure, BizTalk, Presentation, Sommarkollo

Sommarkollo 2012–The Microsoft Integration Story

Ever updated, The Microsoft Integration Story, in an extended 3h format, joins the lists as one of the available topics in Microsoft Swedens Summercamp (Sommarkollo) 2012. Two stops in Stockholm (27/6, 21/8) and one in Helsingborg (26/6). I hope to see you there.

Enjoy
/Johan

clip_image001

Additional info (in Swedish):

Snart är sommaren här och med den Microsofts uppskattade evenemang Sommarkollo. För tionde året i rad har vi massor av spännande seminarier och produkter att presentera. Delta i så många seminarier du vill – helt utan kostnad! Passa på att träffa oss när vi besöker Stockholm, Göteborg och Helsingborg på vår turné genom Sverige i sommar.

Sommarkollo är ett evenemang för dig som vill bli inspirerad och påläst inför hösten. Du blir väl insatt i nyheter, teknik och annan intressant och användbar information som rör våra senaste och hetaste produkter. Seminarierna riktar sig både till dig som är kund och partner till Microsoft.

Vi kommer bland mycket annat presentera nyheterna System Center 2012, Windows Server 2012 och SQL Server 2012. Vi ger dig även unik inblick på hur Windows 8 kommer se ut och hur du och ditt företag kan arbeta enklare och effektivare med hjälp av Microsofts produktivitetsplattform. Vi bjuder också på flera målgruppsanpassade seminarier för exempelvis utvecklare, it-proffs och säljare.
Välj och kombinera de seminarier som intresserar och passar just dig. Om du bokar både för- och eftermiddagspass bjuder vi på en lättare lunch.

Det här är ett strålande tillfälle att under avslappnade former diskutera, få inspiration och utveckla din kompetens.

Anmäl dig här!