Sending Soap with Attachments (SwA) using BizTalk – Part 1

This is a continuation to my previous article. Please have a look if you hadn’t seen it.

Sending Soap with Attachments (SwA) using BizTalk

Below are the steps that we have to follow for this exercise.

1. Create a custom message encoder which can send XML as an attachment in the SOAP envelope message.

2. Create a WCF service which can send the SOAP message with attachment.

3. Create the BizTalk application which can consume the custom WCF service.

Steps are easy isn’t. In this post we will only cover Step 1.

As I have told in the previous post, this custom encoder has been developed by Austrin interoperablity council and they have published the code in Codeplex. I have taken this code and removed some hard coded stuff and placed it in configurable properties.

I have uploaded the full source code below.

http://code.msdn.microsoft.com/Send-Soap-with-Attachments-3784e5f6

Shankar

Advertisements

Sending Soap with Attachments (SwA) using BizTalk

Soap With attachments is a very old technique and is still used in lot of legacy systems. More new technologies has emerged like MTOM which is widely used within the WCF arena. That said, there is no out of the box support within WCF to send a SOAP message with attachments.

An Austrian Microsoft Interoperability Council had a challenge to consume a webservice which expects to send a SOAP message with attachments.

http://blogs.msdn.com/b/mszcool/archive/2009/10/19/windows-communication-foundation-and-soap-with-attachments-message-encoder-built-in-interop-lab-with-svc-sozialversicherungs-chipkarten-betriebs-und-errichtungsgesellschaft-m-b-h.aspx

They have developed a custom encoder which can add the zip message as an attachment in the outgoinh SOAP envelope.

However I had a different challenge in consuming a webservice which requires me to send a soap payload which has an XML attachment. So I had to modify the custom encoder in such a way that I can attach a XML document. I had lot more challenges. The webservice which I had to consume was written in Java and the field appears as xsd:hexBinary in the WSDL file. So there is no way I can add a service reference / web reference to my project. I did tried that, but when I tried to send the message, the server was rejecting the message. The reason for this is Visual studio when generating the client code for the service, puts the type as xsd:base64binary.

So, I had to code the datacontracts, messagecontracts and servicecontracts based on the WSDL. Then I plugged in the code to use the encoder to attach the XML message. There is no direct way to do this from BizTalk. I wrote this entire logic in a WCF Service which acts as a client to the Target web service and acts as a Server for BizTalk. BizTalk application will consume this WCF service and send the SOAP message with attachment.

I am going to present an article with walkthrough in the next post.

Shankar

My contribution(BizTalk custom pipeline components) in technet website

I am happy to see that my contribution – BizTalk custom pipeline component has made it to list.

http://social.technet.microsoft.com/wiki/contents/articles/11679.biztalk-list-of-custom-pipeline-components-en-us.aspx

My component is listed in the Transformation section

Mapper Pipeline Component

This gave me an idea of developing the tranform concept in a pipeline component, wherein you don’t have to actually create a map for transforming the message.

http://www.codeproject.com/Articles/19228/Mapper-Pipeline-Component

Shankar

Build and Deploy Manager using BTDF

Fancy a build and deploy manager for BizTalk which uses BTDF in the background?

We use BTDF for building the BizTalk projects and most people now would have used TFS to do continuous integration which can utilize BTDF do build and deploy the projects.

However this is perfectly fine for automating the continuous integration process. When BizTalk projects has to be moved from development to test and production environments, manual installation steps are followed by deployment teams. For companies having a large number of projects and having the headache of following with the deployment team for the list of projects and release notes is inevitable. It sometimes require people from the dev team to sit with the deployment team to deploy the BizTalk applications.

I have developed a tool to assist with this issue. I have just started off with that tool. I will be constantly updating this tool to make it more generic.

Tool Background
Ideally this tool can be used by a build and release manager who can prepare the BizTalk MSI and deploy the applications in the respective environment without any BizTalk or BTDF knowledge

I have uploaded the project in codeplex. Its open source. So if you have any thoughts, pls share … shankar.sekar@gmail.com

http://buildanddeploybtdf.codeplex.com/

Thanks
Shankar

How to: Select an Itinerary Using a Business Rules Policy (Original MS Article NOT WORKING)

I have been trying out the samples in the ESB Tooklit samples section
http://msdn.microsoft.com/en-us/library/ee236723(v=BTS.10).aspx

The thid sample How to: Transform a Message and Route the Resulting Message to a File Location Using an Itinerary Routing Slip was not working and I found a post in MSDN blog that there was an error in the sample.

Below is the MSDN post.
http://social.msdn.microsoft.com/Forums/en-US/biztalkesb/thread/48bc3e4d-7227-4d17-9d17-7d4f952da7eb/>

I had a similar problem in the sample How to: Select an Itinerary Using a Business Rules Policy.
I got a routing issue “The published message could not be routed because no subscribers ….”. As I had understood a bit of ESB here, I quickly resolved the issues. For those who would like to see how to resolve the problem.

(After adding the OnRamp)
1. Add a Itinerary service and name it RouteToRecipient. In the Itinerary Service Extender property, choose Messaging. In the container, choose ReceiveNAOrder and receive handlers.
2. Right click the Resolver and choose Add Resolver. Name it as Static Resolver. Choose the Resolver Implementation as Static. In the Transport Name, choose FILE. In the Transport Location, enter the location C:\HowTos\Out\East%MessageID%.xml.
2. Connect the OnRamp and RouteToRecipient itinerary service.
3. In the RouteMessage Itinerary service, remove the StaticResolver which you created before.
4. Connect the RouteToRecipient and RouteMessage itinerary service.

You can now test and you would see the itineray picked up based on the customerName value int the xmlDocument.

Shankar

Replaying failed messages from BizTalk ESB portal Part 3

This post is in continuation with the series “Replaying failed messages from BizTalk ESB Portal”

If you haven’t seen the first post of this series, please use the below link to view the post. Part 2

Until now we have seen how to use BizTalk orchestration/receive port/send port to route failed messages to the ESB. But now we will how to replay the message from within the ESB Management Console. The ESB Portal is a ASP.Net application and the whole source code is made available to us by Microsoft.

The default replaying mechanism requires us to create either HTTP or WCF-HTTP adapters for replaying. I would like to go for a FILE adapter, as I would get an oppurtunity to view the message once it is replayed. To add support for a FILE adapter, we need to customize the ESB.Portal ASP.Net application. When you would have downloaded the ESB toolkit, you would have also got the source code for the ESB Portal and the corresponding web services applications.

Once you have loaded the solution, follow the below steps.

  1. In the ESB.Portal project, expand Faults and click MessageViewer.ascx file. Right click to view code or press F7.
  2. Navigate to the method PopulateReceiveLocationList().
  3. foreach (BizTalkOperationsService.BTReceiveLocation rcvLoc in sysStatus.ReceiveLocations)
                {
                    if (rcvLoc.Handler.ProtocolName.ToUpper().Equals("HTTP"))
                    {
                        rcvLoc.Address = "http://" + rcvLoc.Handler.Host.HostInstances[0].ServerName + rcvLoc.Address;
                        httpRcvLocs.Add(rcvLoc);
                        i++;
                    }
               }
    

    Replace the above code with

    foreach (BizTalkOperationsService.BTReceiveLocation rcvLoc in sysStatus.ReceiveLocations)
                {
                    if (rcvLoc.Handler.ProtocolName.ToUpper().Equals("HTTP"))
                    {
                        rcvLoc.Address = "http://" + rcvLoc.Handler.Host.HostInstances[0].ServerName + rcvLoc.Address;
                        httpRcvLocs.Add(rcvLoc);
                        i++;
                    }
                    else if (rcvLoc.Handler.ProtocolName.ToUpper().Equals("FILE"))
                    {
                        httpRcvLocs.Add(rcvLoc);
                        i++;
                    }
                }
    
  4. The above lines of code will include the FILE receive locations to appear in the ESB Management console.
    Now we need to navigate to the ResubmitMessage() method and add the below code

    else if (resubmitUrl.Contains("*.xml"))
                {
                    string url = resubmitUrl.Replace("\\", @"\");
                    url = url.Substring(0, url.IndexOf('*'));
    
                    System.Xml.XmlDocument doc = new System.Xml.XmlDocument();
                    StringBuilder envelopeMessage = new StringBuilder();
                    envelopeMessage.Append(((TextBox)this.MessageView.FindControl("messageBodyBox")).Text);
                    doc.LoadXml(envelopeMessage.ToString());
    
                    doc.Save(url + @"\" + System.Guid.NewGuid().ToString() + ".xml");
    
                    responseCode = "202";
                    responseMessage = "Successfully sumbitted to FILE Adapter";
    
                    result = true;
    
                }
    

    The above lines of code creates a xml document and drops it into the receive location URI that you have chosen. You will understand it better when you see everything in action.

  5. compile and project. If the project location is the same as the IIS directory location for this application, then you dont need to copy anything. If you are developing in a differnt location, then you can run the setup file that is also there in the solution to get your changes into the web application.
  6. We are all done and we can ahead and do our testing. Click the fault message in the Fault viewer and go to the message details. In the message viewer, click the edit link and the Text View control will now be enabled for you to edit the message. Go ahead and add the value 1 in the Count field and click Resubmit link.
  7. You will see a confirmation status in the ReSubmission status field. Go to Biztalk administration console and you could see that our orchestration would have completed without raising any exception. If you can enable tracking on the orchestration, you could now see the altered message.
  8. Have a look at the below picture for resubmitting a message

We have now completed replaying failed message from the ESB Management console without any context properties. If you observe the context message of the new one that you received, they would have lost its original context properties. In some circumnstance, you might need to replay a message with its original context property.

We will cover that in the next post.

Shankar

Replaying failed messages from BizTalk ESB portal Part 2

This post is in continuation with the series “Replaying failed messages from BizTalk ESB Portal”

If you haven’t seen the first post of this series, please use the below link to view the post. Part 1

In this Post, we will see a sample application. This solution will comprise a schema and an orchestration. We will see how we can route messages to the ESB from an orchestration. After doing this excercise we will also see how we can route failed messages from receive port and send port to the ESB.

So, lets first see how we can route messages from Orchestration.

  1. I created a sample application to demonstrate this. I have a xml schema which will be my source schema. The schema structure looks like this.


    See the Count element promoted in the schema.

  2. I added the below dll’s as reference to the project.
    C:\Program Files (x86)\Microsoft BizTalk ESB Toolkit 2.1\Bin\Microsoft.Practices.ESB.ExceptionHandling.dll
    C:\Program Files (x86)\Microsoft BizTalk ESB Toolkit 2.1\Bin\Microsoft.Practices.ESB.ExceptionHandling.Schemas.Faults.dll
  3. Added an orchestration which will process the xml message. It receives the xml message using a receive shape and tries to assign the promoted value(Count) into a variable.
  4. As I explained in my previous post, I have added a scope that will have all my shapes. Currently there is only one shape in our business process. 7.Create a message in orchestration view and name it msgFaultMessage. Select the type as
    Microsoft.Practices.ESB.ExceptionHandling.Schemas.Faults.FaultMessage
  5. Add a construct shape and select the message that we have just added. Add a message assignment shape and the below code.
     msgFaultMessage = Microsoft.Practices.ESB.ExceptionHandling.ExceptionMgmt.CreateFaultMessage();
     msgFaultMessage.FailureCategory = “Process Questions”;
     msgFaultMessage.FaultCode = “”;
     msgFaultMessage.FaultDescription = ex.Message;
     msgFaultMessage.FaultSeverity = Microsoft.Practices.ESB.ExceptionHandling.FaultSeverity.Critical;
    Microsoft.Practices.ESB.ExceptionHandling.ExceptionMgmt.AddMessage(msgFaultMessage,msgQuestion);
    
  6. Add a send shape to send the fault message. Add a Logical send port in the orchestration and configure the binding as Direct with “Routing between ports…” option selected.
  7. Build the project and deploy the orchestration. Now to see the fault message routed to ESB, we need to create a source file for our orchestration to receive and process. Go ahead and generate an instance of the xml message. Modify the message and remove the value for the Count field. This will make the orchestration engine throw an error. That error which will caught by our exception handler and a fault message will be created. It will then be sent to Message box using direct send port.
  8. This is what you should in the BizTalk administration console.

  9. See how the message is showing up in ESB portal.

  10. You can click on the fault message to show its fault details in the fault viewer.

  11. You can find a grid at the bottom and this is the actual failed message. You can see a link for its messageid and if you click that it will give you a chance to see it message data and its context properties.

    Below is the message data

    Below is the context data

In this post I have explained how to route failed messages to ESB and see the fault messages within ESB Management console.

Messages can also be routed from receive ports and send ports. There is a check box in the properties and we can enable that to route fault messages to the message box.

In the next post, I will show you how to replay messages from the BizTalk ESB console.

Shankar