Safe, Closure-free, Serializable functions‏

David Bruant bruant.d at gmail.com
Thu Sep 26 02:21:09 PDT 2013


Le 26/09/2013 01:29, François REMY a écrit :
> Hi,
>
> TLDR ==> The web needs a way to express executable code that does not rely on its parent context, is guaranteed to be side-effect-free, and can be executed safely anywhere (even in a different thread/worker/window/device, or as callback for browser code being executed while the DOM is not ready to be accessed)
Why "need"? You don't really expose a use case. You only start with 
"It's been some time I've been working on this idea of a..."

Also, one thing is not really clear to me. Are you trying to protect the 
function from its caller/loader or the caller from the function? both?

> The good thing about those functions, is that they can safely be sent over the wires to another thread, or to another web page, because they do not possibly rely on any state or context.
This is an interesting use case.
I've come across such a use case when doing MongoDB MapReduce [1]. I was 
doing Node.js code and unlike in other MongoDB clients, I had the 
interesting benefit of having syntax coloration for my map and reduce 
functions:

     // global scope
     var map = '' + function(){
        // map code
     }

(in other language, you have to put the JS in a string and so don't have 
syntax coloration).
Of course, my functions couldn't use any Node.js built-in since they 
were meant to be serialized to be sent to MongoDB.
To be honest, I did fine with this trick. The function being global, I 
had no temptation to use anything from the parent scope... since there 
was no parent scope.

At scale, maybe I would have needed a more systematic approach to make 
sure my functions weren't using non-standard globals. But that can be 
part of my test infrastructure. I'm pretty sure an Esprima-based tool 
already exists to find free variables.

In the previous paragraph, I loosely used the word "standard". Indeed, 
there is no standard JavaScript implementation. There are a bunch of 
implementations with different levels of conformance to existing 
standards. For instance, at the time I used MongoDB, it was using an old 
SpiderMonkey that didn't have Object.keys. I learned this the hard way. 
In that experience, I learned that one of the things you're trying to 
achieve (move "standard" code from machine to machine) is somewhat 
undoable. It's a very context-sensitive problem. Now that MongoDB is 
using v8, maybe I can use Object.keys, but won't be able to use the 
non-standard-then-yet-convenient destructuring available in SpiderMonkey.

Also, MongoDB provides to the serialized function a non-standard "emit" 
function. Your proposal prohibits non-ES6 built-ins, thus preventing 
such an emit function to be provided (arguably, they should pass this 
function an argument). I can also easily imagine that if sharing code 
between two same-version Node.js instances, one may want to be able to 
use Node.js-specific additional globals.

> Is there some interest from anyone else in formalizing this for a future version of EcmaScript? Or any comment?
Given my experience with MongoDB, I'm tempted to ask: do we need this at 
all? A global function (no parent scope) and combined with a tool 
finding free variables might be enough to cover this use case.

David

[1] http://docs.mongodb.org/manual/core/map-reduce/


More information about the es-discuss mailing list