Recently I saw some postings in the BizTalk newsgroup asking how we can handle web service operation that returns a byte. Even though it’s a trivial task, you need to be aware of certain things.
Below is my simple web service operation, which returns a byte. For simplicity, I just got this one operation which can return either a simple string, or some form of xml
or some binary data .
When you invoke your web service from Internet explorer, you’ll get the result something similar to the one shown below (This is the data you’ll get inside your orchestration as well).
Adding a web reference to the above service inside your orchestration project, will create a schema (Reference.xsd
) with a single root element called “base64Binary” of xsd type “base64Binary” as shown below.
<xs:element name="base64Binary" nillable="true" type="xs:base64Binary" />
The sample orchestration used for this demonstration is shown below:
Scenario #1: byte contains some string data:
There are a couple of ways you can deal with this scenario.
Option 1: Using map:
In this approach, you can use the scripting functoid and write an inline script as shown below. It important you use the correct encoding methods to parse the string. In this case it was encoded using UTF8 on the web service.
1: public string GetString(string param1)
3: byte b = System.Convert.FromBase64String(param1);
4: return System.Text.Encoding.UTF8.GetString(b);
Option 2: Using xpath function and helper class:
In this approach we use the orchestrations xpath
function to get hold of the binary base64 data as shown below and pass it to a helper method to get the corresponding data.
1: base64Data = xpath(WS_GetBinary_RESP.GetBinaryResult, "string(/*[local-name()='base64Binary' and namespace-uri()='http://9b957340-adba-3234-91ea-46a5c9bff530/'])");
2: text = Helper.Utility.GetString(base64Data);
base64Data is a variable of type string
Scenario #2: byte contains some xml data:
This scenario is similar to our previous simple text scenario, only difference here is we modified our helper method to parse and load the xml
data into XmlDocument
object as shown below.
Scenario #3: byte contains some binary data:
Dealing with binary data is bit interesting. You need to understand some of the basic points here.
- The parts in the multi-part orchestration message can hold any data; there is no restriction to put only xml data in the message parts.
- If you define a message variable of type System.Xml.XmlDocument, you can assign an XLANGMessage, which in turn can be a multi-part message with or without xml data in any of the parts. As long as you are not trying to validate it or use any xpath syntax on it, there won’t be any errors.
- When constructing an XLANGMessage with a stream, the stream type must either implement IStreamFactory or be a MemoryStream (http://msdn.microsoft.com/en-us/library/aa995576.aspx ).
In this approach we are going to make use of all the above mentioned points. First in our helper dll
, we’ll create a class called CustomStreamFactory
which inherits from IStreamFactory
and implement the interface method CreateStream
as shown below.
As you can see its a very simple implementation, the class constructor take a byte and assign it to a member variable. CreateStream
interface method creates and returns a new MemoryStream
using the data in member variable.
We create a helper method as shown below to populate the content of the first part with our binary data using XLANGPart
The syntax here is bit strange, we are not passing the XLANGMessage
as ref or out parameter. But that’s how its been documented and it works!!
Now within the orchestration expression shape you can assign the message as shown below:
MSG_XMLDOC = new System.Xml.XmlDocument();
If you send the above message(MSG_XMLDOC) to a file drop location with .jpg extension, you will see the image returned from the web service.
TIP: The above syntax in an expression shape is equivalent to putting the code inside a message assignment shape within a Construct shape.
In fact you could have just used our scenario 3 to handle simple text(scenario 1) and xml data (scenario 2).