The new System.Net.Http classes: message content

The 4.5 version of the .NET platform introduces the new System.Net.Http namespace with several HTTP related classes. These classes are also available for .NET 4.0, via the Web API Preview 6 distribution (both source code and NuGet package).

A previous post introduced the HTTP core classes (HttpRequestMessage, HttpResponseMessage and HttpMessageHandler) and described the HttpClient class in detail.

This post addresses HTTP message’s content manipulation , and is based on the Web API Preview 6 distribution. Some links point to the MSDN preliminary 4.5 documentation, while others point to the Web API Preview 6 source code; so expect discrepancies. Notice that this post is based on preview code and documentation; the final .NET 4.5 classes may be different of what is described here.

The HttpContent class

The content of both request and response messages is access via the Content property, of type HttpContent.
HttpContent.2

The HttpContent class contains a Headers property, with the content related HTTP headers (e.g. Content-Language, Content-Type, Last-Modified).

It also contains a set of ReadAsXxx methods for asynchronously accessing the content body:

  • Task<Stream> ReadAsStreamAsync()
  • Task<byte[]> ReadAsByteArrayAsync()
  • Task<string> ReadAsStringAsync()

 

Creating new content

Reading the message raw content, as a byte sequence or as a string, is accomplished using one of the above methods. However, creating new content involves a hierarchy of concrete classes, rooted at the abstract HttpContent class.

 

HttpContent.untyped.hierarchy

Each one of those classes support a specific type of content or content source. For instance, producing a string based content is accomplished by creating a StringContent instance, parameterized with the string content, the character encoding, and the media type.

Typed Content

The System.Net.Http namespace also contains a ObjectContent class for representing strongly typed content, i.e., content based on a strongly typed object.

As depicted in the following diagram, the ObjectContent derives from HttpContent.  There is also a ObjectContent<T> deriving from ObjectContent, which uses a generic parameter instead of a Type instance to represent the content’s type.

TypedContent

 

The ObjectContent is used differently when reading content or producing content.

Reading strongly typed content

When reading strongly typed content, an ObjectContent instance is created from a HttpContent and a MediaTypeFormatter is used to convert the HttpContent’s stream into the ObjectContent’s object.

Stream.formatter.T

The HttpContentExtensionMethods class contains extension methods to do this

ContentExtensions

For instance, the ReadAsAsync method performs the following

public static Task ReadAsAsync(this HttpContent content)
{
    if (content == null)
    {
        throw new ArgumentNullException("content");
    }
    return BuildObjectContent(content).ReadAsAsync();
}

private static ObjectContent BuildObjectContent(HttpContent content)
{
    ObjectContent objectContent = content as ObjectContent;
    if (objectContent == null)
    {
        objectContent = new ObjectContent(content);
    }
    return objectContent;
}

Note that reading strongly typed content involves two contents:

  • The original message content, exposed as a byte stream.
  • The object content, containing an object obtained from the above stream.

 

Producing strongly typed content

Producing strongly typed content is simpler: just create a ObjectContent (or ObjectContent<T>) instance, passing in the object. Since, ObjectContent derives from HttpContent, this new instance can be directly used as a message content. Internally, a MediaTypeFormatter is used to convert from the typed object into a stream (e.g. when a request message is serialized “to the wire”).

 

T.Formatter.stream

Notice that the MediaTypeFormatter class is used for bidirectional conversion:

  • From a byte stream into a typed object.
  • From a typed object into a byte stream.

This class will be the subject of a future post.

Final remarks

  • Abstract HttpContent base class for representing HTTP message content. Contains a set of methods for reading the content’s body as a byte sequence or a string.
  • Concrete HttpContent-derived classes for creating content.
  • ObjectContent and ObjectContent<T> classes for reading and creating HTTP message body content from strongly typed objects.

2 thoughts on “The new System.Net.Http classes: message content

  1. Glenn Block

    Nice post Pedro!

    One additional thing to point out is that when writing the response web api uses a selection algorithm based on content negotiation to determine the correct formatter. I am guessing you’ll do a follow up post on that 🙂

    Reply

Leave a Reply

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

WordPress.com Logo

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

Twitter picture

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

Facebook photo

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

Google+ photo

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

Connecting to %s