Trying *Real* Contract First Development With BizTalk Server

A while back on my old MSDN blog, I demonstrated the concept of “contract first” development in BizTalk through the publishing of schema-only web services using the Web Services Publishing Wizard.  However, Paul Petrov rightly pointed out later that my summary didn’t truly reflect a contract-first development style.

Recently my manager had asked me about contract-first development in WCF, and casually asked if we had ever identified that pattern for BizTalk-based development.  So, I thought I’d revisit this topic, but start with the WSDL this time.  I’m in the UK this week on business, so what better use of my depressing awake-way-to-early mornings than writing BizTalk posts?

So like Paul had mentioned in his post, a true service contract isn’t just the schema, but contains all sort of characteristics that may often be found in a WSDL file.  In many cases (including my company), a service is designed first using tools that generate WSDLs and XSDs. Then, those artifacts are shared with service developers who build services that either conform to that service (if exposing an endpoint) or consume it from other applications.

I’ll start with a simple WSDL file that contains a schema definition and a request/response operation called HelloWorld.  The schema contains a few constraints such as maxOccurs and minOccurs, and a length restriction on one of the fields.

What I’d like to do is have BizTalk consume the WSDL, and then generate a service that respects that WSDL.  How does BizTalk eat a WSDL?  Through the use of the dark and mysterious BPEL Import BizTalk project type.

After choosing this project type, a wizard pops up and asks you for the artifacts that make up the service.  In my case, I just pointed it to the WSDL which had an embedded schema definition.

After an “import succeeded” message, I’m left with a new project and three files which represent my schema (and base types), and an orchestration that includes the auto-generated port types and schemas.

For simplicity’s sake, I’ll just build out the provided orchestration, with the goal of exposing it as a web service.  First, I add a new configured port to the orchestration design surface, careful to choose the generated port type provided to me.

I’m not sure why, but my generated multi-part message isn’t configured right, and I had to manually choose the correct schema type for the message part.

Next, I built two messages (request and response) which used the generated multi-part message types.

Finally, I added send/receive shapes (and a construct) in order to complete the simple orchestration.

I’ll show what happens when using the ASMX Web Publishing Wizard, but first, let’s be forward thinking and use the WCF Service Publishing Wizard.  I chose a WCF-BasicHTTP endpoint with metadata so that I can inspect the WSDL generated by my service and compare it against the original.  You’ll notice that the “service name” of the service is a combination of the orchestration type name and namespace, and, the “service port” is the name of the orchestration port.  Feel free to change those.

I then had to change the target namespace value to reflect the target namespace I used in the original WSDL file.

After completing the wizard (and build a receive location so that my service could be hosted and activated), I compared the WSDL generated by BizTalk with my original one.  While all of the schema attributes were successfully preserved (including original restrictions), the rest of the base WSDL attributes did not transfer.  Specifically, things like the SOAP action and service name were different, not to mention all the other attribute names.

I went back and repeated this process with the ASMX Web Publishing Wizard, and there were differences.  First, the wizard actually kept my original target namespace (probably by reading the Module XML Target Namespace property of the generated orchestration) and also allowed manual choice of “bare” or “wrapped” services.  The actual generated WSDL wasn’t much better than the WCF wizard (SOAPAction still not right), and worse, the schema definition was stripped of important restriction characteristics.  This is a known problem, but, annoying nonetheless.

At this point, you can argue that this is a moo point since I can take advantage of the ExternalMetadataLocation property on the Metadata Behavior in my generated configuration file.  What this does is allow me to point to any WSDL and use IT as the external facing contract definition.  This doesn’t change my service implementation, but, would allow me to use the original WSDL file.  If I set that configuration attribute, then browsing my BizTalk-generated service’s metadata returns the base WSDL.

One of the key things to remember here is that the SOAPAction value you use is the value set in the BizTalk “MethodName” context attribute.  This value is used to match inbound messages to their orchestration subscription (when bound to a SOAP port).  If these don’t line up, you get “subscription not found” errors when you call this service.  So, if I generate my WCF contract using the original WSDL, and submit that message to my WCF endpoint, the message context looks like this:

And remember that my orchestration port’s generated “operation” property was “HelloWorld” and thus my MessageBox subscription is:

So, if you plan on using an external WSDL, make sure you line these values up.  Also note that the orchestration port’s “operation” property doesn’t accept an “http://xxx” style value, so pick something else 😉

I plan on including this topic in the upcoming book, but didn’t feel like squirreling it away until then.   It’s an interesting topic, and I’d be curious as to other’s attempts and getting BizTalk to conform to existing service contracts.

Technorati Tags: , BizTalk

Author: Richard Seroter

Richard Seroter is Director of Developer Relations and Outbound Product Management at Google Cloud. He’s also an instructor at Pluralsight, a frequent public speaker, the author of multiple books on software design and development, and a former editor plus former 12-time Microsoft MVP for cloud. As Director of Developer Relations and Outbound Product Management, Richard leads an organization of Google Cloud developer advocates, engineers, platform builders, and outbound product managers that help customers find success in their cloud journey. Richard maintains a regularly updated blog on topics of architecture and solution design and can be found on Twitter as @rseroter.

9 thoughts

  1. Our public services (versus our mediation services) are created using a contract-first approach. A wsdl, xsd’s and a wiki are the initials artifacts provided. After trying different approach with Biztalk (all of which failed, or were to complicated in our view), we decided to implement our services using a facade pattern. The facade is implementing the contact and posting the message in a queue. An orchestration is subscribing to the message and sending the response to another queue which the facade is peeking. The facade then returns the message to the client based on the contract.

    There is an overhead, but for our needs so far it works and we’re able to keep our contract-first approach with a simpler (in our mind) implementation. We could probably look at creating a custom adapter to post to the message box directly, but the thing we like in our design is that we can scale-out without needing additionnal Biztalk licences…

  2. Hello Richard,

    Thanks for the article. Quick comment, I get diferent results between the my original schema (suing restrictions) and the one schema generated in the WSDL using BizTalk Web Services wizard.
    Do you know if this is the same known behavior if I use the Biztalk Web Services Publishing wizard that it removes the XSD restrictions like maxLength, patterns etc?



  3. I tried this sererval times. The result is not as expected. Because the schema created by BPEL import project inculdes the Mehtod name as root node. when publish this schema, another method name will be added to the schema which has the original method name. Did you do anything to solve this? Thanks!

      1. How did you make the root named after the method name? In my case, the root is the method name? Thanks!

Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

Connecting to %s

This site uses Akismet to reduce spam. Learn how your comment data is processed.