Ember.js in windows (8) store app requires MSApp.execUnsafeLocalFunction

The following stackoverflow question describes the problem of not being able to run ember.js inside a JavaScript “local” windows 8 store application. Could any of the contributors please have a look at it? http://stackoverflow.com/questions/16445497/ember-js-in-windows-8-store-app-requires-msapp-execunsafelocalfunction.

In short: The HTML “browser host” of the windows store application works in a rather restricted mode. For instance setting innerHTML, outerHTML or appending content holding script elements will all get blocked if not explicitely encapuslated by a “proxy” function provide by Microsoft (MSApp.execUnsafeLocalFunction).

I personally expect other vendors to also go this way in the future. It is a simple mechanism to prevent malicious code injection by means of the outerHTML or innerHTML property.

Any response would be appreciated. Thanks!

Libraries I used

  • ember-1.0.0-rc.3
  • handlebars-1.0.0-rc.3
  • jquery-2.0.0 (suppose to be ready for Windows 8 apps)
  • jquery-ui-1.10.3

Microsoft explains the limitations mentioned above here

Right now, Ember views rely on the ability to set the innerHTML property of an element in order to render. After the 1.0 release, we’re planning to do some cool stuff using the raw DOM API, but again, I don’t think that will be done until the 1.1 timeframe.

It would be great if ember supported the Win8 store environment in the future. Till then: Have you thought about introducing some sort of proxy mechanism/function that would allow us to surround those jquery $().appendTo calls by a wrapper as described in my stackoverflow post?

Supporting Windows 8 is definitely important to us. Can you propose an API that would make this easier? Would it be possible for Windows 8 developers to monkeypatch Ember.$?

I will have a look at the Ember sources to see if there is a place for some sort of a “Platform” API. What I have seen so far is, that there is a platform class in the Ember Namespace. Not sure if that would be the correct place for an API (for solving at least a part of the problem)

Regarding Ember.$: It’s not only jQuery that causes problems. There are a number of Ember code fragments that make direct use of the innerHTML property. For instance the metamorph helpers such as “needsShy” etc., do try to set the innerHTML property (in this case for capability testing only). However, since these functions are auto executed at the time of bootstrapping ember, monkeypatching post bootstrapping will not work here.

Give me some time to investigate (need to mention, that I am not the JavaScript expert…). We’ll see what comes out.

Hey Ale,

How do you see yourself using Ember within a Win8 app? I built one some time ago and frameworks like Ember or Angular didn’t really seemed suited to the dev model for Win8 apps. Things might have changed but if you’re able to help me understand your use case, I can ping my colleagues at MS about their thoughts on this and offer some feedback.

Rey

1 Like

Hey Ray

We are currently looking for a framework to be used on various platforms, not Win8 only. The kind of applications we are building are targeting the Enterprise and the Government, i.e. no app development for private use (for now). I don’t see any reason not to use Ember as the base framework. The Win8 Environment (WinJs, API, etc.) will only be used if absolutely required. This of course limits us to build rather simple apps that do not much interact with the platform they run on. This is not a problem since we usually build “traditional” client/server applications. The only difference to before is, they will not only run in the browser, but also as App.

Any way, if really somebody at MS would have a look at what I mentioned in this Topic, it would certainly be highly appreciated.

Andreas

So it sounds like you’re looking to leverage the Win8 WebView to wrap your browser-based apps?

It might be that WebView is used underneath. The tests I did was with a regular Javascript / Windows 8 Store App as you create it in Visual Studio 2012. Using the WebView (from within a XAML Application) would be similar to use PhoneGap as the “Hosting” container. If somebody want to look at integrating with PhoneGap for Windows 8 store… welcome. I would be interested as well.

Ok

here is an idea of how such a

layer of platform abstraction/decoupling

could look like. Its intention is to pre-configure certain parts of Ember to let it better fit into / adapt to the platform it is running on.

The following code fragment represents the decoupling of DOM and jQuery calls inside Ember. The sample provided is not complete, it only covers the DOM innerHtml setter and jQuery.appendTo(). There are more DOM manipulation around that needed to be taken into account. The code fragment needs to be added after the Ember object is created and of course before any of the wrapped calls are used by Ember). A Windows 8 Store App configuration of the Ember.Decouple object is shown at the end of this post.

   /**
  Layer of abstraction/decoupling to wrap calls to the DOM and jQuery.
  The "Ember.Decouple" allows wrapping calls to DOM.innerHtml
  and jQuery.appendTo() by some platform specific code.
  For instance Windows 8 store applications required that calls to
  innerHtml are executed as unsafe code if the content being assigned
  to the innerHtml property contains <script> elements.
  The "decoupling" can be configured by creating a javascript
  object named PlatformDecouple. This object must be created prior to loading/parsing Ember.js
*/
(function () {
  if ('undefined' !== typeof PlatformDecouple) {
    Ember.Decouple = PlatformDecouple;
  }
  else {
    Ember.Decouple = {};
  }
  Ember.Decouple.DOM = Ember.Decouple.DOM || {};  
  Ember.Decouple.DOM.innerHtml = Ember.Decouple.DOM.innerHtml || function (element, content) { element.innerHTML = content; };
  // ... more DOM decoupling

  Ember.Decouple.jQuery = Ember.Decouple.jQuery || {};
  Ember.Decouple.jQuery.appendTo = Ember.Decouple.jQuery.appendTo || function (elem, target) { elem.appendTo(target); };
  // ... more jQuery decoupling
})();

Inside Ember, Setting the innerHtml property would no longer be:

element.innerHTML = html;

but would be wrapped by

Ember.Decouple.DOM.innerHtml(element, html);

The same applies to jQuery calls:

this.$().appendTo(target);

became

Ember.Decouple.jQuery.appendTo(this.$(), target);  

Configuration of the decoupling layer would happen prior to parsing ember.js. The following code fragment configures the decoupling layer to work in a Windows 8 store application:

/**
configure ember to wrap certain calls with MSApp.execUnsafeLocalFunction
*/
PlatformDecouple = {}
PlatformDecouple.DOM = {}
PlatformDecouple.DOM.innerHtml = function (element, content) {
  MSApp.execUnsafeLocalFunction(function () { element.innerHTML = content; });
};
PlatformDecouple.jQuery = {}
PlatformDecouple.jQuery.appendTo = function (elem, target) {
  MSApp.execUnsafeLocalFunction(function () { elem.appendTo(target); });
};

There are probably other places inside Ember where such a mechanism could be helpful. As I said, I am not a JavaScript expert nor do I have fundamental knowledge of ember internals. But… might this be a way to go for?

If not, what would be the alternative instead of waiting for ember version 2 or higher?

Regards, Andreas