An enterprise SOA service is not just any old web service.  There are specific requirements that it must meet.  These are not optional, yet I have not been able to find many resources on the web describing these requirements.  (Reasons = different post).

In general, if you are developing a service that you want other folks to consume, you must follow these high level principles. 

  1. Your service must be simple to call.  With a coarse-grained service, there can be a lot of data to pass, and that data may need to be fairly complete.  The receiving end may need to perform quite a bit of validation on that data.  One tactic that I’ve seen to ‘optimize’ this is to write a DLL that creates the data and calls the service.  Then you just ship the DLL to your customers.  This is nuts. 
    • You customers still have a call-level interface.  Instead of it being the service, it’s the DLL.  Nothing gained.
    • EAI components now need an adapter to call your service.  Something lost.
    • Your service, if called from an external or cross-platform environment, it is not being called by your DLL.  In fact, you cannot really be sure that the service is called by your DLL even inside your environment… so you will have to validate the data anyway.  This means that the data, when it is called by your DLL, is validated twice.  This is a performance hit.  Do it once… in the service.
  2. Your service must be able to be called directly from EAI components, like Biztalk or your favorite ESB, without engaging an expensive or custom adapter.  EAI components have no trouble reading WSDL.  Requiring an adapter means that you don’t have a truly sharable service.
    Implications:
    • Heavily nested or embedded XML structures are unweildy in most tools.  Therefore, the fact that you can do something in XML, doesn’t mean that you should.  Avoid the creation of the “universal message” that can be extended 1,000 different ways.  Go ahead and create messages for specific business purposes.  Keep the vocabulary of messages from exploding by using optional attributes and structures… that’s fine.  But if you create an XSD that refers to 10 other XSD files, you’ve got a structure that no human can understand, much less code to.
    • Requiring some non-standard encryption to take place or some special mechanism to ‘encode’ the message, to make sure that it is coming from a known source, forces your EAI tool to use an adapter.  It also gets in the way of flexibility.  To remain flexible, you need the message to come from anyone without changing the code.  It is perfectly appropriate to encrypt the message or to sign the message.  There are standards for that.  Use them. 
  3. If you do want to make a DLL available for folks to call your service, perhaps to reduce the barriers to adoption, do so with open source.  If the developers using your code can see the code, and change it, on their side, then you have done them a favor.  If you simply substitute your web service call for an API call, you’ve done nothing positive at all.
  4. Services running at the Enterprise Level must have methods that can be called to validate (a) that the service is running, and (b) that downstream connections are valid.  Therefore, I suggest that every service should have standard methods for “ping” and “check.”  Note that, for services that have no downstream connections, they both do the same thing.  I’d suggest that the return for the call is simple connection information to the service (perhaps the URL of the service itself).
  5. Services running at the Enterprise Level should provide data about what servers, data centers, and support teams they are associated with, live and in real time.  Therefore, I suggest that ever service should have a standard method for “GetSupportData” that returns a structure containing all the info. 
  6. Services running at the Enterprise Level should NORMALLY be asychronous, with a very rapid return of an acknowledgement that indicates that the service itself takes ownership and responsibility for the message. 
  7. The sending side must place a unique id into every call.  For async message exchange, the receiving side must send back the caller’s unique id, along with any unique id it has created for it’s work.  This allows message correlation. 
  8. The call-back structure, for calls that require a later return, must be standard, allowing any caller to easily construct the data needed for the receiving system to understand how to call the sender back with the response package. 

Of course, putting requirements like this on Enterprise Services means that not every service can partake.  On the other hand, it means that every service in the Enterprise catalog can be verified automatically, and basic information can be collected and reported.  You can go further, of course, and place a great deal of stuff in a standard interface, but this is the basic set that I would start with.