Scott Hanselman

NuGet Package of the Week #13 - Portable HttpClient makes portable libraries more useful

March 21, '13 Comments [17] Posted in NuGet | NuGetPOW | Win8 | Windows Client | WinPhone
Sponsored By

Reference Assemblies include .NET Portable AssembliesWhen you've got an idea for an app, it's likely that you've got the idea for that app in more than one place. By this I mean, you'll start with a phone app, then make a desktop app, then a web app. Or you'll make a game on one platform and then want it to work anywhere. In fact, with the rise of Xamarin, C# lets you put an app in every AppStore in the world with one language.

You likely already knew that you can target different versions of the .NET framework. You likely also know that there are small .NET Frameworks like Silverlight and the tiny .NET Micro Framework.

You can also target XBox and Windows Phone, OR better yet, target a profile called Portable Libraries that I've briefly mentioned before. Portable Libraries are a great idea that have some issues when you try to really use them. There's actually a great (if a little older) video with the inventors over at Channel 9. Note that Portable Libraries ship with Visual Studio 2012 and are a supported thing.

The idea is that you write a library that contains as much shared functionality as possible and then every application uses your now "portable" library. However, the subset of classes that are available are a subset. That means you can only use things that are available in the intersection of the targets you choose. Check this dialog:

Choose your target framework

And check out the Supported Features table at this MSDN article on Portable Libraries to find out what you can use where. Here's a graphical table I stole from Daniel.

PortableLIbraryChart

However, most folks that use Portable Libraries have ended up using them mostly for ViewModels - just simple classes without any real functionality. Almost as if we had a DLL full of structs. There are some great posts on how to make Portable Class Libraries work for you using architectural techniques like indirection and appropriate interfaces.

The number one complaint around code resuse and the number one voted item over at the Visual Studio UserVoice was "Add HttpClient support in Portable Class Libraries (including Windows Phone 8)." Why? Because the GETting of a remote resource via HTTP is such a fundamental thing that it'd be awesome to be able to bake that data access into a portable library and use it everywhere.

Now there is a Portable Http Client and you can get it via NuGet!

install-package Microsoft.net.http -pre

Here's an example of what the code looks like for a GET. Note that I'm using async and await also.

public static async Task<HttpResponseMessage> GetTheGoodStuff() 
{
var httpClient = new HttpClient();
HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Get, "http://hanselman.com/blog/");
var response = await httpClient.SendAsync(request);
return response;
}

.NET Portable Subset

If you were going to make a Twitter client (lame example, but bear with me) you could now put the JSON HTTP data access code in one library and share it across Windows Phone, Windows Store, WinForms, Console, whatever.

I'm hoping that the folks at MS and the folks at Mono will continue to work to make Portable Libraries a good option for Mono as well. I've been advocating (and pushing) to make something happen as well, as have the Portable Libraries folks. You'll find lots of working in the space around the web, so fear not, code reuse, either through Portable Libraries or via linked code files at compilation time is deeply possible. The game "Draw A Stickman Epic" achieved 95% code reuse by writing the game in C# with MonoGame!

.NET 4 or Windows Phone 7.5

If you want to use this HttpClient on .NET 4 or Windows Phone 7.5, note you might get a compile error if you use async and await.

Cannot await System.Threading.Task<HttpRequestMessage>

This is because .Net 4.0 and Windows Phone 7.5 did not support the async/await keywords. In order to fix this add a reference to the Microsoft.Bcl.Async nuget package, which adds the support for async and await in .NET 4 and WP7.5. Here's a post with more details on how this backport works.

Related Links

About Scott

Scott Hanselman is a former professor, former Chief Architect in finance, now speaker, consultant, father, diabetic, and Microsoft employee. I am a failed stand-up comic, a cornrower, and a book author.

facebook twitter subscribe
About   Newsletter
Sponsored By
Hosting By
Dedicated Windows Server Hosting by ORCS Web
Thursday, March 21, 2013 11:16:02 PM UTC
However, most folks that use Portable Libraries have ended up using them mostly for ViewModels - just simple classes without any real functionality. Almost as if we had a DLL full of structs.


Ouch! I certainly wouldn't call ViewModels classes without any functionality, although I suppose some people might prefer to make their ViewModels very thin and push most code down into the models. But the models can also be portable, so either way you can share most of your code using Portable Class Libraries!

In any case, I agree that HttpClient does make it much easier to put more code in PCLs. Previously, if you wanted to put your code in a Portable Class Library, you'd have to use HttpWebRequest, which isn't as nice of an API and doesn't support async code quite as well. Or you could have written platform-specific code for your networking and hooked it up to your PCL via the abstraction pattern, but since HttpClient wasn't available on Windows Phone, .NET 4, or Silverlight, you would probably have had to implement it using HttpWebRequest in any case.

Anyway, thanks for the post. :-)
Daniel Plaisted
Friday, March 22, 2013 5:06:53 AM UTC
Daniel - Sorry about that, I meant just that one starts with the hopes and dreams of filling Portable Libraries with ALL core functionality and then they have to scale it back some. Your point about HttpWebRequest is well-taken.
Friday, March 22, 2013 7:43:08 AM UTC
C# *is* lets you put an app in every AppStore..
Daniel B
Friday, March 22, 2013 9:28:38 AM UTC
Our writing of portable code predates Portable Libraries, so although they look really cool if they're "good enough", I suspect they'd be a step back for us.

So we have multiple projects to maintain, but we take a different approach to doing it from what seems to be the common way. As far as I can tell, other places tend to use file linking, so when you add a file in your master project you have to manually add a link to it in all the others.

We don't do that. We take advantage of MSBuild being the underlying language of project files, and structure our project so that shared code is all under one root folder, while any partial classes that may be needed to extend support to a particular environment will be in a different folder tree. When we add a file to the shared folder tree in the master project in the normal way, it's picked up by the other projects because we include those files using wildcards:

<Compile Include="Source\**\*.cs">
<SubType>Code</SubType>
</Compile>
There are a couple of minor drawbacks:
  • In order to pick up new files, the other projects have to be unloaded and reloaded, because the wildcards are only evaluated at load time.
  • If you forget and manually add a file in the shared folder tree to one of the other projects using Solution Explorer, then the wildcard entry in the underlying MSBuild gets thrown away and all the files are included explicitly. Easy to revert, but annoying when it happens.
  • So, not perfect, but we think it compares favourably with the linking files approach.

    Maybe the Project Linker closes the gap on ease of use when working with linked files. We haven't done a serious evaluation of it.
    Friday, March 22, 2013 1:08:02 PM UTC
    Two questions:

    Why does the Supported Features table show the dynamic keyword as not being supporting in .NET 4.0?

    How is the "Add HttpClient support" item "the number one voted item over at the Visual Studio UserVoice"? It has 1887 votes; I posted a suggestion which got 3317 votes. Last time I checked, 3317 is higher than 1887.
    Richard
    Friday, March 22, 2013 1:17:30 PM UTC
    That's great! (and I've found PCLs to be far more useful than just for viewmodels)

    Also, "MonoGame" is fantastic. :)
    Matthew Toney
    Friday, March 22, 2013 3:25:10 PM UTC
    @Gavin Greig: I'd love to hear what you're missing from Portable Class Libraries (PCL) and why you want source sharing instead.

    Assume for a second we'd give you support for #if -- would this change the picture?

    @Richard: Regarding dynamic -- good question, I'll double check.

    You're correct, your item was definitely was more popular. But at some point the item was declined which removes it from the list. When we released HttpClient, it was the highest voted ACTIVE user voice item. Sorry about that.
    Friday, March 22, 2013 4:52:45 PM UTC
    @Immo Landwerth

    To be honest some of it is just that our portable projects pre-date the Portable Class Libraries and serious exploration of PCL as an alternative hasn't been a high enough priority. However, something I'd anticipate immediate difficulty with is that we're targetting Mono and iOS (MonoTouch, we haven't moved to Xamarin yet) as well as targets that you do support directly.

    We try to avoid #if whenever possible, but I've just checked our main portable library and there are four usages, three of which are to do with portability, so I expect #if could be helpful.
    Monday, March 25, 2013 9:42:16 PM UTC
    hello,
    i opened new project ASP.NET MVC 4 on two VS2012 and press CTRL+F5 for take preview.
    i create different user & password in each WebApp preview.
    i login to first webApp, then to second webApp.
    i see first webApp logout automatically!!!

    i see all session is together.

    Is problem in Web Matrix?!

    WebMatrix.WebData.WebSecurity
    seilsepour
    Thursday, March 28, 2013 4:37:51 PM UTC
    What is unclear to me is how would the "Windows Phone 8" column look like in that table. Any idea?
    Friday, March 29, 2013 6:00:18 AM UTC
    The portable HttpClient really is an awesome library. Started porting my Dropbox library to it a while ago to give it async/await and WinRT support. https://github.com/dkarzon/DropNet2

    Pretty keen to see more of these awesome projects coming out from Microsoft focusing on cross platform development.
    Friday, March 29, 2013 8:30:41 AM UTC
    I see you have Windows Blue Mr. Hanselman :) ...
    Pop Catalin
    Friday, March 29, 2013 4:21:20 PM UTC
    Pop - No....why would you think that?

    Andrei - I'll ask!
    Friday, March 29, 2013 4:42:19 PM UTC
    The blue window chrome slightly different nuance of blue than (the default blue) in Windows 8, that's why I've figured it must be Windows Blue :). It's long shot I know, but I was kind of hopping for this to be true.
    Pop Catalin
    Monday, April 22, 2013 3:12:47 PM UTC
    @Andy Cohen,

    according to this Link "http://connect.microsoft.com/VisualStudio/feedback/details/781331/vs-2012-update-2-ctp-4-doesnt-work-with-portable-httpclient" this seems to be a bug in the updated 2 of VS2012 and can be solved by using the repair button in the Installer.

    Had the same problem and got it solved by reparing the update.
    Kai
    Thursday, September 26, 2013 8:41:16 AM UTC
    Why is the compact framework not supported by portable libraries?

    As I understand it, Xbox 360 is essentially compact framework and it is supported. Compact framework may be old, but it is still in wide use. The company I work for still uses it for some handheld scanner devices which means that the poor souls who work on that project are stuck in Visual Studio 2008 with old-fashioned C# syntax while the rest of us are in VS 2012 with lovely C# 5.
    Damian Powell
    Comments are closed.

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