This article describes how to implement the single-instance
correlation that is used in the XLANG correlation sample that is included with
BizTalk Server 2002 Software Development Kit (SDK).
Introduction
Many business processes involve sending a document and waiting
for a receipt document. You can use the BizTalk Orchestration Designer to
design such a business process and compile it in an XLANG schedule. After you
deploy the schedule, several instances of the schedule are likely to be running
simultaneously. To make sure that a receipt document is passed back to the
schedule instance that sent the original document, you can use XLANG
correlation. XLANG correlation is the process of returning a message to a
specific instance of a running schedule, or
correlating a receipt document back to its originating schedule instance.
In BizTalk Server 2000, you perform XLANG correlation by using what
is known as
per-instance correlation, where a separate correlation Message Queuing (also
known as MSMQ) queue is created for each running XLANG schedule instance.
Per-instance correlation has the disadvantage of the overhead that is required
to create and maintain a separate Message Queuing queue for each instance of a
running XLANG schedule.
In BizTalk Server 2002, you can perform
single-instance XLANG correlation, where you only need a single Message Queuing
queue to facilitate XLANG correlation.
This article describes the
implementation of single-instance correlation as used in the BizTalk Server
2002 Software Development Kit (SDK) XLANG correlation sample. Each
orchestration schedule instance is identified with a GUID that is stored in the
InstanceID property of the schedule. When you implement XLANG correlation,
the GUID that is stored in the
InstanceID property is copied in every document that is sent from XLANG. The
receiving application then copies this
InstanceID in the return receipt document and sends the receipt document
back to BizTalk Server. When BizTalk Server receives the receipt document, it
sends the document to the single-instance Message Queuing correlation queue
with a message label of the
InstanceID.
The receive action port for the XLANG schedule is
configured in such a way that it picks up messages from the correlation queue
whose label matches its own
InstanceID and continues processing the document.
There are
several variations of this implementation. This article focuses on the XLANG
correlation sample that is included with BizTalk Server 2002. This sample uses
an encoding pipeline component to copy the XLANG
InstanceID property in documents and to retrieve the XLANG
InstanceID from the receipt document. This article also illustrates how to
modify this sample to perform single-queue correlation without using the
encoding pipeline component.
Set Up the XLANG Correlation SDK Sample
The XLANG correlation sample is in the XLANG Correlation
directory of the BizTalk Server 2002 CD.
To set up this sample, copy
the XLANG Correlation directory from the BizTalk Server 2002 CD to drive C of
your BizTalk server, remove the Read Only attribute from the C:\XLANG
Correlation directory and its directories, and then run Setup.cmd from the
C:\XLANG Correlation\Setup directory.
NOTE: This sample is designed to be copied to and run from the C:\XLANG
Correlation directory. If the sample is copied to and run from another
location, several scripts must be modified and the XLANG schedules must be
changed to reflect the new location.
After you copy and install the
XLANG correlation sample, run the sample by copying Po_instance_1.xml from the
C:\XLANG Correlation directory to the C:\XLANG Correlation\Store_drop
directory. A file receive function picks up the document and hands it off to
BizTalk Server for processing. After the document is processed, you see three
files under the C:\XLANG Correlation\Store_docs directory.
The XLANG Correlation SDK Sample Schedules
To better understand the business logic used in the XLANG
correlation sample, open the Store_instance.skv and Warehouse.skv files that
are located in C:\XLANG Correlation\Schedules with the BizTalk Orchestration
Designer. These schedules contain workflows for a Store business unit and a
Warehouse business unit.
The workflow for the Store_instance.skv
schedule is as follows:
- Receive PO: Receives a Purchase Order (PO) file. The PO file is the
Po_instance_1.xml file that you placed in the C:\XLANG Correlation\store_drop
directory.
- PO to File: Writes a copy of the PO to a file in the C:\XLANG
Correlation\store_docs directory.
- Create ShipOrder: Creates a ship order by using the CreateShipOrder() function of the ITransformDoc class in the Store_tranform component. The Store_tranform component can be found in C:\XLANG
Correlation\Components\Store\Store_transform.dll.
- ShipOrder to File: Saves a copy of the ship order to a file in C:\XLANG
Correlation\Store_docs directory.
- Send ShipOrder: Sends the ship order to the warehouse.
- Get Receipt: Waits for a receipt from the warehouse.
- Receipt to File: Saves a copy of the receipt to a file in the C:\XLANG
Correlation\store_docs directory.
The workflow for the Warehouse.skv schedule is as follows:
- Receive ShipOrder: Receives the PO file from the Supplier business unit.
- ShipOrder to File: Stores a copy of the ship order to the C:\XLANG
Correlation\Store_docs directory.
- Create Receipt: Creates a receipt by using the CreateReceipt() function of the ITransformDoc class in the WarehouseTransform component. The WarehouseTransform component can be found in C:\XLANG
Correlation\Components\Warehouse\WarehouseTransform.dll.
- Send Receipt: Sends the receipt document to the
/Fruitstorereceipts/Biztalkhttpreceive.dll virtual directory of the BizTalk
server, which is monitored by an HTTP receive function by the Store business
unit.
- Receipt to File: Copies the receipt document to a file.
Description of Outbound and Inbound Correlation
XLANG correlation can be broken down in two distinct parts:
- Outbound adds the InstanceID or GUID to the outbound document and sends the document out to
the trading partner.
- Inbound adds the InstanceID of the original document to the receipt document, sends the
receipt document back to the originating trading partner, and processes the
receipt document in the originating XLANG schedule.
Both the inbound and outbound correlation processes are
discussed in greater detail in this article.
The Outbound Correlation Process in Detail
To more closely examine how the schedule in this sample writes
the
InstanceID property (which contains the schedule GUID) in the outbound
document, double-click the
SendShipOrder message in the SendShipOrder port of the Store_instance.skv
schedule to start the XML Communication Wizard. In the message type
information, you will see that
Use Instance ID as Message Label is selected and the message type is
__Instance_Id__. This causes the XLANG Scheduler Engine to write the GUID of the
running schedule in the
SRC_XLANG_InstanceID dictionary key of the outbound message. Then, after the Scheduler
Engine hands this document off to the BizTalk Messaging Engine, the value in
this dictionary key is written in the outgoing document in the
FruitStoreSendShipOrder messaging port as explained below.
After the
InstanceID is stored in the
SRC_XLANG_InstanceID dictionary key of the outbound document, the document is handed
off to BizTalk Messaging and processed by the FruitStoreSendShipOrder channel.
The FruitStoreSendShipOrder channel is bound to the FruitStoreSendShipOrder
port. The FruitStoreShipOrder port copies the
SRC_XLANG_InstanceID dictionary key value in the outbound document by calling the
InsertCorrelation() function of the
IGetCorrelation class in the
FruitCorrelation component. The
FruitCorrelation component can be found in C:\XLANG
Correlation\Components\Store_correlate\FruitCorrelation.dll. The
FruitCorrelation component is called because the FruitStoreShipOrder port
specifies an encoding type of
Custom, which was specified when the port was created. This detail is
not easily seen when you view the user interface. All that you can see in the
user interface is that an encoding type of
Custom is being used. To see how an encoding type of
Custom causes the dictionary value that contains the
InstanceID to be copied to the outbound document, open the Btsconfig2.vbs
file under the Setup directory that is used to create the messaging objects.
Here you will see following line in the
Create_lPort160110 function:
Port.encodingtype = BIZTALK_ENCODING_TYPE_CUSTOM '3
You also see the following line in the
Create_lChannel180100 function:
channel.SetConfigComponent 3,lPort160110, "{306113A9-48EE-470B-9E8D-C45901FA9D62}"
3 indicates a configuration data type of
Encoding, and {306113A9-48EE-470B-9E8D-C45901FA9D62} is the GUID for the
IGetCorrelation class of the
FruitCorrelation component.
Pipeline components for BizTalk Server can
be one of four component types:
AIC,
Encryption,
Encoding, or
Signing. Marking this as an
Encoding component when you create the port makes it available as the
Custom selection from the
Encoding Type drop-down list in the Messaging Port Properties pages.
Because the FruitStoreSendShipOrder port is configured to call the
IGetCorrelation class of the
FruitCorrelation component (through the
Encoding type of
Custom), when the document reaches the port, the code for this class is
run and it is at this point that the dictionary value that contains the
InstanceID is copied to the
FruitShipReceipt\Tracking\Tracking_ID node of the outbound document. After the
InstanceID of the schedule is copied to the outbound document, the
FruitStoreSendShipOrder posts the PO to the
/Fruitwarehouse/Biztalkhttpreceive.dll virtual directory of the BizTalk server,
which is monitored by an HTTP receive function by the Warehouse business
unit.
The Inbound Correlation Process in Detail
After the schedule
InstanceID has been inserted in the outbound document and the outbound
document has been sent to the trading partner (Warehouse), the receiving
trading partner must process the document and return a receipt document with
the same
InstanceID so that the receipt document is processed by the same originating
XLANG schedule instance.
The XLANG correlation sample does this as
follows:
After the FruitStoreSendShipOrder port copies the schedule
InstanceID in the
FruitShipReceipt\Tracking\Tracking_ID node of the outbound document, it sends the document to the
/Fruitwarehouse/BiztalkHttpreceive.dll virtual directory of the BizTalk server,
which is monitored by an HTTP receive function.
The receive function
passes the document to the FruitWareHouseReceiveShipOrder channel, which is
bound to the FruitWareHouseReceiveShipOrder port.
The
FruitWareHouseReceiveShipOrder port passes the document to the Warehouse.skx
schedule, which calls the
ITransform class of Warehousetransform.dll to create a receipt document that
is basically a copy of the original document. This receipt document contains a
FruitShipReceipt\Tracking\Tracking_ID node with the
InstanceID of the original document.
The Warehouse.skx schedule
file passes the receipt file to the FruitWareHouseSendReceipt channel that is
bound to the FruitWarehouseSendReceipt port. The FruitWarehouseSendReceipt port
then posts the receipt document to the
Fruitstorereceipts/Biztalkhttpreceive.dll virtual directory of the BizTalk
server, which is monitored by an HTTP receive function by the Store business
unit. This receive function passes the receipt document to the
FruitStoreReceiveReceipt channel, which is bound to the
FruitStoreReceiveReceipt port.
The FruitStoreReceiveReceipt port
copies the
InstanceID from the
FruitShipReceipt\Tracking\Tracking_ID node of the receipt document in the
DEST_XLANG_InstanceID dictionary key of the receipt document by calling the
Retrievecorrelation function of the
IRetrievecorrelation class in the
Fruitcorrelation component. This step is similar to the step where you insert the
schedule
InstanceID in the outbound document in the outbound correlation process. The
RetrieveCorrelation function is called because the FruitStoreReceiveReceipt port
specifies an
Encoding type of
Custom, which was specified when the port was created. Again, you cannot
see this clearly in the Messaging Manager user interface. You must open the
Btsconfig2.vbs file to see how the custom encoding type was specified when the
port and associated channel were created. Open the Btsconfig2.vbs file under
the setup directory that is used to create the messaging objects and you see
following line in the
Create_lPort160109 function:
Port.encodingtype = BIZTALK_ENCODING_TYPE_CUSTOM '3
You also see the following line in the
Create_lChannel180099 function:
channel.SetConfigComponent 3,lPort160109, "{195554DF-41AD-48F1-9AB2-DD54B2F89C1E}"
3 indicates a configuration data type of
Encoding, and {195554DF-41AD-48F1-9AB2-DD54B2F89C1E} is the GUID for the
IRetrieveCorrelation class of the
FruitCorrelation component.
After the
InstanceID is copied in the
DEST_XLANG_InstanceID dictionary key of the receipt document, the
FruitStoreReceiveReceipt port writes the receipt document in the
\private$\FruitStoreReceiveReceipt Message Queuing queue with a message label
of Dest_XLANG_InstanceID. The message label is configured as
%Dest_XLANG_InstanceID% in the advanced properties of the
FruitStoreReceiveReceipt channel.
Now, because the receipt document
is written to the \private$\FruitStoreReceiveReceipt Message Queuing queue with
a message label of
Dest_XLANG_InstanceID, the originating XLANG schedule (Store_instance.skx) knows to
pick up this receipt document by using the Receive Receipt schedule port that
is tied to the Get Receipt action and to continue processing the receipt
document. The Receive Receipt action in the Store_instance.skx schedule is
configured to use
single-instance correlation because
Use a known queue for all instances in the Message Queueing Binding Wizard is selected. The Get
Receipt action knows to receive messages that use the
InstanceID as the message label because
Use Instance ID as Message Label was selected when the XML Communication Wizard for the Get
Receipt action was run. The
Use Instance ID as Message Label option is not available in BizTalk Server 2000.
It is
this option in the BizTalk Server 2002 Orchestration Designer that facilitates
single-instance correlation. Without this option, the originating XLANG
schedule cannot distinguish between the different messages that are written to
the queue. With this option enabled, the originating XLANG schedule waits for
messages to be written to the queue with the same GUID as the schedule and
processes those.
Perform XLANG Correlation Without Using Pipeline Components
It is possible to modify the XLANG correlation sample to perform
receipt correlation without using any custom pipeline components. To do this,
follow these steps:
- Configure the Store_instance.skv schedule to save the InstanceID in the sending document. In the original sample, an Application
Integration Component (AIC) is used to save the InstanceID to the Tracking_id fields in the sending document. To configure the
Store_instance.skv schedule to do this instead, follow these steps:
- Load Store_instance.skv.
- Double-click the SendShipOrder message in the SendShipOrder port to launch the XML Communication
Wizard for this port.
- In the Message Type Information dialog box, click to clear Use Instance ID as Message Label, and then type EFruitShipOrder in the Message type box.
- In the Messaging Specification Information dialog box, add /FruitShipOrder/Tracking/Tracking_ID to the message fields.
- Switch to the Data view for the schedule.
- Drag a line from __Instance_ID__ Constant to the SendShipOrder Tracking_ID.
- Save and recompile the schedule.
- Configure the FruitStoreSendShipOrder BizTalk messaging
port to not use the custom encoding component:
- Start the BizTalk Messaging Manager.
- Double-click the FruitStoreSendShipOrder messaging port to view its properties.
- In the Security Information dialog box, click to select None for the Encoding Type.
NOTE: After this step is performed, the only way to add the Custom encoding type back to the port is by re-running the sample setup
scripts. This is because an encoding type of Custom can only be added to a messaging port programmatically through
the BizTalk Object Model. - Click Finish to save changes to the port.
- Configure the FruitStoreReceiveReceipt BizTalk messaging
port to not use the custom encoding component:
- Start the BizTalk Messaging Manager.
- Double-click the FruitStoreReceiveReceipt messaging port to view its properties.
- In the Security Information dialog box, click to select None for the Encoding Type.
- Click Finish to save changes to the port.
- Add the DEST_XLANG_InstanceID to the receipt document to map the tracking ID:
- Start the BizTalk Editor.
- Open Fruitreceipt.xml in the BizTalk
Repository.
- Expand and then click to select FruitShipReceipt/Tracking/Tracking_ID.
- Switch to the Dictionary tab.
- Add a dictionary key with the name DEST_XLANG_InstanceID.
- Click to select the check box in the front of the key
to map it to the FruitShipReceipt/Tracking/Tracking_ID node.
- Store Fruitreceipt.xml to Web Distributed Authoring and
Versioning (WebDAV) to save the changes.
- Refresh the EFruitReceipt document definition:
- Start the BizTalk Messaging Manager.
- Double-click the EFruitReceipt document definition.
- Click OK.
NOTE: Although the name and the path of the schema file have not
changed, you must open the document definition and save it to update the cache.
- Refresh the FruitStoreReceiveReceipt channel:
- Start the BizTalk Messaging Manager.
- Double-click the FruitStoreReceiveReceipt channel.
- In the Advanced Configuration dialog box, make sure that the message label for the primary
transport is configured as %DEST_XLANG_InstanceID%.
- Click Finish to save the changes to the channel.
- Copy one of the Po_instance_x.xml files in the Store_drop
directory and monitor the Store_docs directory for output files to verify that
these changes are successful.