I'm trying to learn some WCF on my own. I have C#/ASP.net knowledge but I am new to WCF. I am using Visual Studio 2010 to develop some apps while I learn.
I developed a small web service which acts as the backend for a TODO/Task manager where a user can create/delete/edit new events; it's all very simple and basic.
My questions are the following:
- Is there a way to let the client choose the return format he wants (e.g. xml/json/rdf) without writing new operation contracts?
- How can I see on the client the exact message the Web Service sends to me (so that I can check if it's for instance a json representation or an xml message).
The way web browsers choose response formats from web sites is via content negotiation, and in particular through the use of the Accept and Content-Type HTTP headers.
For example, if your client requires a JSON-formatted response, it would send the server an HTTP request that looks something like this:
GET /resource HTTP/1.0
User-Agent: YourClient 1.0
Accept: application/json
The server, in turn, would respond with an HTTP packet like this:
HTTP/1.0 200 OK
Content-Type: application/json
Content-Length: 20
{ "type" : "json" }
WCF is unfortunately not equipped to handle content negotiation out of the box, but there is a really nice third-party library that enables it without too much work called WcfRestContrib. Their documentation describes the (quite simple) steps you have to take to make it work. To sum it up, you have to
- decorate your service class according to the content types you wish to support,
- decorate the methods you wish to be content negotiation-aware, and
- return a serializable business object from that method.
As for your second question, Fiddler is a fine choice for testing both the client and the server.
When you create a REST service with WCF, content negotiation is supported.
You simply need to set automaticFormatSelectionEnabled
to true
on the endpoint.
See also: WCF Web HTTP Formatting
My experience is that WCF isn't great in this area. MVC is a big improvement with its concept of "Action Results" which let you return whatever you want for a given endpoint. (And supposedly the new "Web API" will be a marriage of WCF and MVC features.)
That said, the easiest WCF way to let the client choose the response format, is to specify a Stream return type, and serialize the result according to the requirement.
So declare the method like this, and use the your serializer(s) of choice for JSON and XML.
[OperationBehavior]
[WebGet()]
public Stream SomeOperation(string format)
{
string test = "Hello world";
string encodedResult;
if (format.ToLower() == "xml") {
// serialize as XML (eg, XML Serializer)
HttpContext.Current.Response.ContentType = "text/xml";
}
else if (format.ToLower() == "json") {
// serialize as JSON (eg, Newtonsoft Json)
HttpContext.Current.Response.ContentType = "application/json";
}
var ms = new MemoryStream(Encoding.UTF8.GetBytes(encodedResults));
return ms;
}
For your second question, I'd recommend using a free tool like Fiddler to inspect the raw HTTP response from the server.
Instead of going for a SOAP based service you can try REST model. The new way of creating REST or HTTP services using MS technologies is using Web API that will be available ASP.NET MVC 4.
Advantages of REST:
Content Negotiation - The client can specify the data-type(JSON, XML..) through the Accept-Type
parameter in the Request
header.
Use HTTP methods explicitly
Directory structure-like URIs
and more..