« Martyn Lovell on the Secure CRT | Main | Choosing an Scheduler Service for Workfl... »
Continuing from part 1, we'll now see how to handle schemas and execute receive and send pipelines with the pipeline testing library.
Configuring Known Document Specifications
If you want to use an assembler or disassembler on your pipeline, you'll need to make sure that it can resolve the necessary schemas based on the fully qualified schema type, or the root element name (namespace#root). To accomplish this, you'll need to make sure that the pipeline is aware of "known" document specifications before you execute them, so that the mock pipeline context can return the correct value when IPipelineContext.GetDocumentSpecByName() or IPipelineContext.GetDocumentSpecByType() is invoked by the assembler/disassembler component.
The library supports this through the AddDocSpec() method on the ReceivePipelineWrapper and SendPipelineWrapper classes. AddDocSpec() takes as an argument a Type handle referencing the strongly-typed, SchemaBase-derived class generated by the BizTalk project system when you compile an schema into a BizTalk Assembly. Here's an example:
ReceivePipelineWrapper pipeline =
PipelineFactory.CreateEmptyReceivePipeline();
pipeline.AddDocSpec(typeof(Schema2_WPP));
AddDocSpec() will automatically handle multi-root schemas and make all roots in the schema known to the pipeline context, so you don't have to worry about that. You can also add as many document specifications as needed, as long as there are no conflicts among them (i.e. don't add two schemas with the conflicting namespace#root names).
Executing Pipelines
Now that we can configure the necessary components and schemas into our pipelines, we are ready to execute them. For both receive and send pipelines, you execute them using the Execute() method. However, it is defined with a different signature in both the ReceivePipelineWrapper and SendPipelineWrapper classes: Receive pipelines take a single IBaseMessage argument and return multiple messages in a MessageCollection object. Send pipelines, on the other hand, take multiple messages in a MessageCollection object as input and return a single IBaseMessage object as ouput.
Here's a complete example of configuring and executing a receive pipeline:
PipelineFactory.CreateReceivePipeline(typeof(ReceivePipeline1));
// Create the input message to pass through the pipeline
Stream stream = DocLoader.LoadStream("SampleDocument.xml");
IBaseMessage inputMessage = MessageHelper.CreateFromStream(stream);
// Add the necessary schemas to the pipeline, so that
// disassembling works
pipeline.AddDocSpec(typeof(Schema1_NPP));
// Execute the pipeline, and check the output
MessageCollection outputMessages = pipeline.Execute(inputMessage);
Here's a complete example of executing a send pipeline, with multiple inputs:
SendPipelineWrapper pipeline =
PipelineFactory.CreateSendPipeline(typeof(Env_SendPipeline));
string body =
@"<o:Body xmlns:o='http://SampleSchemas.SimpleBody'>
this is a body</o:Body>";
MessageCollection inputMessages = new MessageCollection();
inputMessages.Add(MessageHelper.CreateFromString(body));
// assembling works
pipeline.AddDocSpec(typeof(SimpleBody));
pipeline.AddDocSpec(typeof(SimpleEnv));
// we get a single message batched with all the
// messages grouped into the envelope's body
IBaseMessage outputMessage = pipeline.Execute(inputMessages);
Tomas Restrepo is a software developer located in Colombia, South America. His interests include .NET, Connected Systems, PowerShell and lately dynamic programming languages. More...
email: tomas@winterdom.com msn: tomasr@passport.com
Copyright © 2002-2008, Tomas Restrepo.
Powered by: newtelligence dasBlog 2.2.8279.16125