WinRT vs. Silverlight - Part 7 - Making WebRequests

by Morten 5. October 2011 13:35

See intro blogpost here.

In Silverlight and WPF you are probably used to using WebClient to perform downloads. This is a simple class for doing download/upload string or retrieving a response stream from the server. However, in Windows Runtime this client doesn’t exists. Instead we have new a simple “HttpClient” to do much of what WebClient can. However it works very differently by using the new Task framework, and the more you dive into porting code to WinRT, you will see this a lot, and it will make your life porting code cumbersome. On the upside, the Tasks framework is awesome and it’ll often simplify you code a great deal! I talked a bit about this in my previous post, so please read that first, before you continue here, since this will be building on top of that.

Let’s say we have a method in WPF and Silverlight that uses WebClient to downloada and create an image. Since this is working asynchronously, we would have to either use event handlers or action delegates to return the result and/or the error. The method could look something like this:

public void GetContent(Uri uri, Action<string> complete, Action<Exception> error)
{
    WebClient client = new WebClient();
    client.DownloadStringCompleted += (sender, e) =>
    {
        if (e.Error != null)
            error(e.Error);
        else {
            complete(e.Result);
        }
    };
    client.DownloadStringAsync(uri);
}

 

Here’s how a method like that could look in WinRT:

public async Task<string> GetContentI(Uri uri)
{
   System.Net.Http.HttpClient client = new System.Net.Http.HttpClient();
   var result = await client.GetAsync(uri);
   return result.Content.ReadAsString();
}

Simple right? Well it' gets even simpler when we have to start consuming that method.

From SL and WPF you would consume the method something like this:

GetContent(uri, (text) => {
          TextBlock tb = new TextBlock() { Source = text };
          LayoutRoot.Children.Add(tb);
      },
      (error) => { /*TODO: handle error*/ }
);

And the same using the Task framework:

try {
   TextBlock tb = new TextBlock() { Source = await GetContent(uri) };
   LayoutRoot.Children.Add(tb);
catch { /*TODO: handle error */ }

You tell me what’s more elegant and readable? Smile

My point here is that Tasks are awesome, so rather than trying to reuse your existing code in WinRT, consider rewriting your existing code to use Tasks and it will work much smoother.

There’s lets create a method for downloading a string over the network that works the same way across the board. (I’ll assume you are using the Async Task CTP for Silverlight or WPF for this).

public async Task<string> GetContent(Uri uri)
{
#if NETFX_CORE
    System.Net.Http.HttpClient client = new System.Net.Http.HttpClient();
    var reqResult = await client.GetAsync(uri);
    return reqResult.Content.ReadAsString();
#else
    WebClient client = new WebClient();
    TaskCompletionSource<string> tcs = new TaskCompletionSource<string>();
    client.DownloadStringCompleted += (sender, e) =>
    {
        if (e.Error != null)
            tcs.TrySetException(e.Error);
        else
            tcs.TrySetResult(e.Result);
    };
    client.DownloadStringAsync(uri);
    return await tcs.Task;
#endif
}

Note you could also use the new .NET method “WebClient.DownloadStringTaskAsync” which would simplify the above quite a lot. I used the event based approach to demonstrate how you would handle the cases where you don’t already have a task implementation available.

Tags:

WPF vs Silverlight | Windows Runtime | WPF | Silverlight

Comments (4) -

1/2/2012 4:27:03 AM

Richard Watson

Thanks for the WRT posts.  They are helpful.

We developed some REST endpoints in the form of a both a proxy web site as well
as a Server Object Extension.  That coarse grained functionality is then consumed
by business objects which execute in Silverlight.  Today, those business objects
are compiled into an assembly for Silverlight was well as an assembly for the full
.NET.  Essentially, we are following the same design pattern that you did.

What we want to do is to resuse those same business objects in WinRT as well.  If we
can do that then we have the ability to produce some great Metro products as soon
as Windows 8 is released which is pretty cool.

That gets complex because it looks like we need SL 5 and VS 2011 (.NET 4.5) and
that all of this must run on the older OS's such as XP.  That means that ESRI must
support all of this as well as Microsoft.

I really like how all the new functionaly makes writing async code very clean.

Richard Watson United States

1/4/2012 9:01:16 AM

Morten

Richard: WinRT apps will not run on WinXP, Vista or 7, so no need to support a WinRT API on those platforms.
Also you do not need Silverlight 5 for Win8. This is not Silverlight (but if you need Silverlight s well, earlier versions will run just as fine on Win8).
As always with the latest Microsoft SDKs, the latest Visual Studio is needed.

Morten United States

1/4/2012 2:24:27 PM

Richard Watson

Thanks for the response Morten.  I understand what you said.

The thing that I want to do is to come up with single set of source code for business objects with an API which is consistent across Silverlight, WinRT, and .NET (non-WinRT).

Richard Watson United States

1/23/2012 12:12:13 PM

Loren Cress

I know that this isn't exactly the right place, but there doesn't seem to be a better one.  You seem to be quite knowledgable, though, so perhaps you could move it to the right place and/or post an entry relating to this issue.

Google tells me that I'm not the only one facing this problem: we are building a WPF application using the Esri WPF API, but in order to consume REST services we have to go through a proxy.  That would be fine, except that the proxy requires authentication.  All of the WebClient libraries support the Proxy object, which in turn supports a Credentials object.  The Esri API, though, only offers me a "ProxyURL" string, and a separate Credentials object, which doesn't appear to do anything for the proxy; I wouldn't expect it to.  That object seems to be for providing creds for the REST endpoint.

"ProxyURL" is obviously for supporting a "proxy page", which is not applicable for our situation - that's not what we're doing.  We'd just like to consume simple, insecure maps and services like ArcGIS Online.

One workaround that we've found is to build - in the application itself - our own tiny webserver/proxy that uses WebClient to pass http requests through to the company proxy.  That seems very kludgy, though. How can we get through the proxy without writing our own WebClient-based proxy into our application?

Loren Cress United States

3/28/2012 6:13:54 PM

five finger shoes vibram

YC- Any training Vibram shoes gets stale after four to six weeks and michael kors watch stops working http://www.vibramfive-sales.com/. So whether you're looking to Vibram Bikila learn how to use kettle vibrams five fingers bells for the first time or if you're a seasoned vet and looking for a new michael kors mid-size mercer chronograph watch, golden challenge, kettle bell books, DVD's and five finger vibram bikila instructional courses are always a good bet. No amount of vibram fivefinger shoes for women instructional articles, videos, books, or DVD's can replace in-person instruction michael kors sale when it comes to kettle bell five fingers uk sale training. Look up your local RKC and purchase some vibram five fingers kso training sessions as a gift to get your kettle bell aficionado going on the right foot - or watches michael kors to perfect their technique. These vibram 5 fingers sale may look a little different and special but actually they are really quite cool and can be used for a five fingers shoes uk shop multitude of purposes http://www.michael-kors-sale.net/. Whether you just want something to walk around the home or to the speed shoes, perhaps you climb or do some light trekking or you may want the Vibram Five Fingers for running. There is vibram five finger toes very little padding on the shoes, as Vibram have designed them in a way that reflects the michael kors mens watches natural properties of feet; this means five fingers uk sale that there is very little interference from the shoes, which effectively mimic barefoot movement. http://www.vibram-five-finger.net/

five finger shoes vibram People's Republic of China

3/31/2012 7:45:05 PM

annora coast dress

LF- Barbour jackets are a clothing manufacturer originating from the north of coast clothing England; they have gained a solid http://www.uk-barbour-jacket.org/ reputation in the creation and manufacturing of barbour jacket women hardwearing, durable and fashionable coast irah red designed for outdoor use. The reason that they are so popular at present is largely due to the recent country/townie barbour quilted jacket fashions that are set to be big coast fashion news this season. As a hunting-type barbour quilted jacket ladies, the Barbour quilted jacket is perfect for adapting to recent coast victory dress styles. Founded in 1894, the company red barbour jacket has never been far from the minds of floral dresses fashion conscious individuals throughout the world. Often considered the sophisticated man's style of fashion, these coats form part of a classical style of womens barbour jackets dress. Renowned for their coast maxi dresses hardwearing, high-quality garments, Barbour really are head and shoulders above the rest. They are famous for providing clothing for many barbour shop of the country's high-flying elite; as such, they have a fantastic reputation, which is coast evening dresses uk much warranted. http://www.uk-womendresses.biz/

annora coast dress People's Republic of China

Pingbacks and trackbacks (3)+

Comments are closed

About the author

Morten Nielsen

Silverlight MVP

Morten Nielsen
<--That's me
E-mail me Send mail

Twitter @dotMorten 

Disclaimer

The opinions expressed herein are my own personal opinions and do not represent my employer's view in any way.

© Copyright 2005-2011

Month List

RecentComments

Comment RSS