A View Inside My Head

Jason's Random Thoughts of Interest


Metro: Introducing the Local and Web Contexts

I recently recorded an episode of The Tablet Show with Carl Franklin and Richard Campbell (it will be published at the end of July 2012) where I rambled on about discussed different concepts that are needed to construct a Geospatial Metro-style application.  Since I seem to do more web development these days than anything else, I naturally approached this from a HTML/JavaScript developer's point of view.

The geospatial part is really irrelevant.  I included it because I could speak to the subject matter, and it permitted me to establish some constraints around the otherwise huge topic of writing a Metro-style application.  From the web developer's point of view, though, there are existing JavaScript-based APIs that the developer will be interested in using while writing the Metro application (i.e., jQuery and OpenLayers comes to mind).  

Now, when you write a Metro application using .NET or C++, there's a compilation step that takes place to compile the source code into an executable (EXE and/or DLL).  The executable and any dependencies are packaged into an application package (an .appx file), which is really just a renamed .zip file that contains the files, a manifest, and cryptographic information to ensure that the contents were not tampered with.  Aside from WinRT libraries, everything that is needed to run the application must be included in the package.

HTML/JavaScript Metro applications, by contrast, actually run as a web page inside of an Internet Explorer 10 process.  The source files are stored within the application package, much as they would be on a web server.  But, instead of downloading HTML, JavaScript, CSS, and images from a web server across a network, the resources are retrieved from the .appx file on the user's hard drive (much faster load times, and the application is still accessible when there is no network connectivity).

Metro-style applications built using HTML/JavaScript still have access to the Windows Runtime and can do just about anything that their compiled-counterparts can.  In order to allow such privileged access, however, certain common practices in the web world had to be explicitly prohibited.  Specifically, anything that attempts to inject HTML or script into the DOM of a Metro-style application will result in an exception (to prevent third-party script injection attacks).  More details can be found here: http://msdn.microsoft.com/en-us/library/windows/apps/hh465380.aspx

This safe HTML filtering causes a problem with a lot of existing JavaScript libraries.  So, how is a developer supposed to use such a library inside of a Metro application?  It turns out that in the case of Metro-style applications, Internet Explorer 10 will assume two different personalities: Local context and Web context.  

The application bootstraps into the Local context.  This mode is what you'll find most people talking about when they discuss building Metro-style applications using HTML/JavaScript because it has full access to WinJS (and WinRT). Local context URIs start with the "ms-appx" protocol, and the resources must exist in the .appx file.

The Web context is totally isolated from the Local context, and cannot access WinRT and a lot of other things that the Local context can.  As a result, code running in the Web context behaves pretty much like a normal web application today.  This means that developers can continue using those existing JavaScript libraries that don't work in the Local context!

Web context URIs start with the "ms-appx-web" protocol (if the resource exists in the .appx file), or the "http" protocol (if the resource is to be loaded from a web server).  Specific differences between Local and Web contexts is documented here: http://msdn.microsoft.com/en-us/library/windows/apps/hh465373.aspx

In practice, an IFRAME is used to introduce Web context content into a Metro application.  In this way, the outermost web page runs in the Local context, while the IFRAME's content runs in the Web context.  It's possible for the IFRAME to be styled to fill the entire screen, if needed (and the outermost web page becomes just a thin hosting shell).

A common scenario is that data in the Local context will need to be sent to the web context (and vice versa).  For instance, code running in the Local context may listen for events fired by the device's Compass sensor.  When a new directional heading is established, the Local context code will need to send the new data to the Web context code for further processing.

HTML5 defines a means to do this cross-document communication using the window.postMessage() function.  In the case of the new Compass reading, the Local context code would post a message to the IFRAME.  The Web context code would need to register an event listener for the window's "message" event.

The messages themselves are strings, and the developer is left with the task of implementing a data protocol.  JavaScript Object Notation (JSON) will often be used to serialize JavaScript object to a string representation for the purpose of transferring across the contexts (the sending side will use JSON.stringify() to serialize the object, while the receiving side will use JSON.parse() to deserialize it).

The hybrid Local-Web context architecture allows an existing HTML5/JavaScript web application to be converted into a Metro-style application without the need to modify third-party JavaScript libraries.  Though, even after such a conversion, there will still likely be some clean-up needed to make the existing application behave more like a Metro-style application, such as implementing the App Bar for commands, and taking advantage of the Search and Sharing contracts.  But, the reward for going through this effort is an application that can then be distributed or offered for sale on the Windows Store to an audience of millions of potential users.

Want to try these things out today before Windows 8 launches this Fall?  Release candidates are available for free:

Windows 8 Download: http://aka.ms/JenWin8

Visual Studio 2012 Download: http://aka.ms/JenVS2012