OData has good support for streams via the ATOM concept of Media Link Entries (MLE) and Media Resources (MR).

A Media Resource is a unstructured piece of data or stream, something like a Document, Image or Video. And the way that you access or learn about a Media Resource is via the associated Media Link Entry, which is just a special type of Entry which links to a Media Resource and includes additional metadata about it.

For example if you wanted to use OData to share Videos, you could model the metadata for the Video as an MLE and create a feed for these MLEs, then the actual video itself would become a Media Resource linked to from the MLE.

So using something like this to retrieve a particular MLE:

GET ~/Service/Videos(123123)

Might return something like this:

<entry m:etag="UVWXYZ">
<id>http://server/Service/Videos(123)</id>
<title>OData Named Resource Streams</title>
<summary>A short video about Named Resource Streams...<summary>
<updated>2010-08-21T08:27:16Z</updated>
<author>
<name />
</author>
<link m:etag="ABCDEF" rel="edit-media" title="Title" href="Videos(123)/$value" />
<content src="... uri to a picture to represent the video ..." />

<m:properties xmlns:m=" http://schemas.microsoft.com/ado/2007/08/dataservices/metadata" xmlns:d="http://schemas.microsoft.com/ado/2007/08/dataservices">
<d:Id>123</d:Id>
<d:Synopsis> A short video about Named Resource Streams...</d:Synopsis>
<d:Name>OData Named Resource Streams </d:Name>
</m:properties>
</entry>

In this example the actual video (or Media Resource) can be found in the 'edit-media' link's href.

So far OData is just using standard ATOM support for media-resource.

Named Resource Streams

But what happens though if you need multiple versions of that video?
For example High and Low bandwidth versions.

Today you could model this with multiple MLEs, but doing so implies you have different metadata for each stream, if note you end up with copies of the same metadata for each version of the stream. Clearly this is not desirable when you have multiple versions of essentially the same video, image or document.

It turns out that this is a very common scenario, common enough that we thought it needed to be supported without forcing people to use multiple MLEs.

Ideally you should be able to have something like this:

<entry m:etag="UVWXYZ">
<id>http://server/Service/Videos(123)</id>
<title>OData Named Resource Streams</title>
<summary>A short video about Named Resource Streams...<summary>
<updated>2010-08-21T08:27:16Z</updated>
<author>
<name />
</author>
<link m:etag="ABCDEF" rel="edit-media" title="Title" href="Videos(123)/$value" />
<link
rel=" http://schemas.microsoft.com/ado/2007/08/dataservices/edit-media/ HighBandwidth"
title="HighBandwidth"
href="Videos(123)/
HighBandwidth/$value" />
<link
rel=" http://schemas.microsoft.com/ado/2007/08/dataservices/edit-media/ LowBandwidth"
title="LowBandwidth"
href="Videos(123)/LowBandwidth/$value" />
<content src="... uri to a picture to represent the video ..." />
<m:properties xmlns:m=" http://schemas.microsoft.com/ado/2007/08/dataservices/metadata" xmlns:d="http://schemas.microsoft.com/ado/2007/08/dataservices">
<d:Id>123</d:Id>
<d:Synopsis> A short video about Named Resource Streams...</d:Synopsis>
<d:Name>OData Named Resource Streams </d:Name>
</m:properties>
</entry>

This says there is some default representation of the video that can be downloaded from Videos(123)/$value (i.e. the standard Media Resource), and there are also High and LowBandwidth streams too.

Note: In the above example the URI's for the Named Resource Streams simply use the URI conventions, i.e. the uri that identifies the Named Stream property with $value appended. However the clients should be payload driven here, so a server should be able to return any uri they want.

To achieve this the metadata would need to look like this:

<EntityType Name="Video" m:HasStream="true">
<Key>
<PropertyRef Name="ID" />
</Key>
<Property Name="ID" Type="Edm.Int32" Nullable="false" />
<Property Name="Name" Type="Edm.String" Nullable="true" />
<Property Name="Synopsis" Type="Edm.String" Nullable="true" />
<Property Name="HighBandwidth" Type="Edm.Stream" />
<Property Name="LowBandwidth" Type="Edm.Stream" />
</EntityType>

Notice the extra streams are just extra properties on the item of type Edm.Stream. Here Edm.Stream is simply a new built-in complex type, with some explicit structure (MimeType) and an implicit stream.

I think this is a natural next step for OData's stream support.

What do you think?

Alex