I have been playing with this System.ServiceModel.Web for about a week now trying to get real world prototypes together and, in addition to having a hard time understanding some of their design choices with regards to how/where they plug into WCF, I have come across at least two major limitations. I’ll start with brief descriptions of limitations and then elaborate below:
- You cannot mix WebInvoke decorated methods that specify a UriTemplate with the enableWebScript behavior that is meant to provide compatibility with the JSON protocol (i.e. application/json) that ASP.NET AJAX uses. See my post here on WCF forums.
- You cannot use DataContract types as parameters for UriTemplated methods because the UriTemplate parsing engine doesn’t have an understanding of assigning portions of the URI to properties/fields of your DataContract instance. See my post here on WCF forums.
What this means is that you cannot expose the same WebInvoke decorated ServiceContract via different webHttpBinding based endpoints the way you would like. So, for example, I want my service to be accessible not only via application/json requests, but also simple REST requests that return POX. Because of this limitation, I cannot do that.
This basically flies in the face of everything that is good about WCF by tying your operations to a particular message serialization/addressing implementation. The saddest thing is, I don’t see why this has to be broken. The enableWebScript behavior should just cause the UriTemplate functionality to be ignored.
What this means is that you can use strings, ints and all the other intrinsic .NET value types for your operation parameters, but if you want to use your own custom DataContract based type, you’re SOL. Imagine the case where you want to pass in some paging information to various operations. So you design a data contract called PagingDetails that has properties like PageSize, PageNumber, etc. Now you want to make this operation accessible via a simple REST URL. You would expect you might be able to define an operation like this:
public List<string> MyOperation(string searchText, PagingDetails pagingDetails);
You would hope that the UriTemplate infrastructure would understand the dot-notation in the named variables and map those values to the pagingDetails parameters instance’s properties, but alas it does not and instead just complains it can’t find a parameter named “pagingDetails.PageSize”. Again this limitation seems to fly in the face of the very basis of WCF where DataContract is very much a first class citizen.
In conclusion, I’m sad to see that some of the design decisions behind System.ServiceModel.Web have crippled it in this way. Essentially the only way I can think of to work around these limitations is to design completely separate service contracts with the same method names/signatures so that your implementation class can fulfill both service contracts operations with a single implementation of a method and then you still need to expose separate endpoints with the proper configurations. The other option is to forgo using UriTemplate at all and just settle for XML POST requests to your POX services.
What did the gentleman who responded to your post mean when he said: “DataContracts are supported with an HTTP Post (WebInvoke attribute). Strings are the only thing that seem to work well in UriTemplate. I find that it’s beneficial to think of UriTemplate as a ‘path’ mechanism”It seems that he is suggesting that you can use WebInvoke and with Data Contracts (assuming you are POSTing your request), but you just cannot name the parameters. That does not sound right.