class YahooWeatherInCityInUnits
{
string City; string Units; string AppID;
services such as query optimization,
which implement rewrite rules such as
xs.Union(ys).Where(p) = xs.Where(p).
Union(ys.Where(p)) that can be reused across many LINQ providers.
TaskAwaiter<ForeCast> GetAwaiter()
{
var www = new WebClient();
var response =
from xml in www.DownloadStringTaskAsync(…City, AppID…)
let woeid = …fish WOEID from result…
from rss in www.DownloadStringTaskAsync(…woeid…)
let forecast = …deserialize forecast from rss…
select forecast;
the city as a WOEID (where on earth
ID), we need to make two service calls
under the hood in order to retrieve the
weather forecast. The first service call
retrieves the WOEID of a requested city
via http://where.yahooapis.com/v1/
places.q(city)?appid=XXXX. If that successfully returns, then a second call is
made to retrieve the weather forecast
for that location. The calls to the Web
server are performed asynchronously
and both return a Task<T> (in Java you
would use
java.util.concurrent.
Future<T> to represent the result of
an asynchronous operation). Since we
can consider a Task<T> as a kind of
collection that contains (at most) one
element, it also supports the LINQ
query operators, and we have turtles
all the way down; the LINQ implementation for Weather is defined using
the LINQ implementation of Task<T>
(see Figure 5).
Though this is an extremely small
and limited example, it clearly illustrates many of the techniques used to
create real-world LINQ providers such
as LINQ to Objects, LINQ to SharePoint,
LINQ to Active Directory, LINQ to Twitter, LINQ to Netflix, and many more.
LinQ-friendly aPis
All examples so far have dealt with
implementing particular LINQ providers. An orthogonal aspect of LINQ
is APIs that leverage particular LINQ
implementations, often LINQ to Objects. For example, LINQ to XML is an
API for manipulating XML documents
that has been designed specifically
with LINQ in mind, which eliminates
the need for a DSL such as XQuery or
XPath to query and transform XML.
The Google Chart API is a Web
service that lets you dynamically cre-
ate attractive-looking charts, using a
simple URI (Uniform Resource iden-
tifier) scheme. The URI syntax for
Google charts, however, is not very
sequence friendly. For example, the
URI for the earlier sample pie chart
looks like this:
http://chart.apis.google.com/chart
?cht=p3&chtt=Top+ 5+words&chs=
500x200
Generic Query Providers
The weather service query provider ex-
ample is structured as an internal DSL.
While this provides a great user experi-
ence with maximum static typing, it al-
lows little room for reusing the actual
implementation of the provider. It is
custom built for the particular target
top-to-bottom. At the other end of the
spectrum we can create a completely
generic query provider that records a
complete query “as is,” using a little bit
of meta-programming magic.