Workflow Insights: Correlation

Correlation is one of the key concepts in Workflow Foundation to understand when developping workflows. Most of the time people are confused about what correlation exactly is. They can’t really describe it, they can’t really explain it. Unfortunately, when you do not fully grasp this concept, it can lead to some major confusion when developping advanced scenarios and custom activities.

So what is correlation? Correlation is the machanism created to map an inbound message for a specific instance (sent from an external source) to the specific handler within the activity. There are two levels here:

  • specific instance
  • specific handler within the activity

Each level has his own differentiater. The specific instance (known by the external souce in the outside world) is defined by the CorrelationParameter and the specific handler within the activity (note that a workflow is an activity too) by the CorrelationToken.

But how is this implemented? Well, let’s first recap the basic objective: we are trying to establish external communication. The Workflow Foundation achieves this by using interfaces as a “channel”. The implementation of such a “channel” interface is a service which is added to the workflow runtime. This is actually the heart of correlation. As there are many instances (in the outside world) the service can work on, Workflow Foundation needs to know with which instance it must work on. This is why we need to define the CorrelationParameter in our “channel” interface. This is how an interface for external communication can look like.

[ExternalDataExchange]
[CorrelationParameter("taskId")]
public interface ITaskService
{
  [CorrelationInitializer]
  void CreateTask(string taskId, string assignee, string text);
}

In this example we define a CorrelationParameter “taskId” that will help us differentiate tasks – the instances – in the outside world. This name will stand for the correlation paramater throughout the whole interface. So when you use this name in a member (eg. CreateTask) as a parameter, Workflow Foundation considers the parameter as a correlation parameter for that member. Note that a correlation parameter can be a guid, int or whatever.
You also see a CorrelationInitializer attribute in there, which decorates the CreateTask member. When calling a member with this attribute, Workflow Foundation will know that the correlation parameter is initialized with this member. It will then reset internal pointers.

Now that the channel is defined, you can use it within your activity. You can use the channel directly by querying the runtime for the correct service. Workflow Foundation however gives you another possibility to ease working with different instances and handlers for those instances WITHIN your activity. This is where Correlation Tokens come into play. A correlation token encapsulates the correlation parameter and a value, together as a correlation property. For our task example, we could create a correlation token named “taskToken” which encapsulates the correlation property of property parameter “taskId” with the value 25. In other words this correlation token will hold the reference to the task 25.
Workflow Foundation also provides two activities that use this correlation token: CallExternalMethodActivity and HandleExternalEventActivity. A common way to use these activities consists of overriding their methods when developping custom activities (most sharepoint activities are implemented this way). Another method is to use them directly by setting the correct service, member name and parameters. As you probably already figured out, the first activity is able to call external methods. The HandleExternalEventActivity, on the other hand, will wait and listen for a specified event (after which it can trigger methods). Both of those activities use the correlation token to determine which instance they have to work with. It, however, makes most sense with the HandleExternalEventActivity, as an event cannot handle parameters, while the method called from a CallExternalMethodActivity specifies which instance to work on by one of the parameters.
To resume, here is a little schema of how to look at correlation tokens:

Workflow Insights: Correlation Token Overview

I hope this article helped you guys understand correlation a bit more. Untill next time..

Leave a Reply