importModule followup
On Aug 17, 2008, at 8:59 PM, Maksim Lin wrote:
Hi,
In a comment on John Resigs blog about ES-Harmony, Hannes Wallnoefer suggested that a simple module system he has implemented for helma-ng [1] could be used for a future ES versions implementation.
I think Brendan may have misunderstood the proposal as in a later comment he said that : "...Hannes points out how to solve it in-language, but that wheel is (a) a leaky abstraction, which could be abused; (b) something no one should have to re-invent."
which I dont think is right
Which point, (a) or (b)?
since the way I understand Hannes importModule() to work is that the code that is "imported" from the corresponding js file is given a new object as its parent scope (rather then the global one) and then that objects prototype is set to the global scope. Tis then prevents the imported code from modifying the "real" gloabl scope while still giving it read-access to it. Hopefully I've explained it correctly, so apologies to Hannes if I
haven't.
This does not work, since it is possible to mutate the properties of
mutable objects named by properties on the prototype chain, not
merely shadow prototype properties by assigning direct properties of
the same name. But I'd like to hear more about Helma NG does it.
But I can't see how does that work as "in-language". To me it seems that this requires the js implementation to do the above (messing with the parent scope of the imported code) as it can't be done by the application programmer in js unless you use a bunch of proprietary moz API's like the mock example on the helma-ng page:
Right. Magic not expressible in the language must be used, or there
will be integrity problems, or to put it another way, abstraction leaks.
So instead why not have a new standard function importModule() that does the above as part of the language spec?
Several distinct functions are being mixed by importModule that
should be separated:
-
Addressing the module to be imported in an "external" storage
hierarchy, whether by URLs on the web or pathnames in a Unix
filesystem, etc. -
Whether loading of code from the addressed module is synchronous
or asynchronous with the call to importModule. Local file access
probably means importModule is synchronous, but this is wrong for the
Web browser embedding. -
Once having addressed the module and loaded its contents, how the
module's provided names are required and accessed.
Many times in TC39 we've discussed the module problem, and most agree
that 1 and 2 do not belong in the Ecma core language specification.
They belong (at least -- other embeddings matter too) in the HTML5 spec.
Item 3 is important, and there's already some work under way to
develop an idea based on PLT Scheme, which I'd like to propose for ES-
Harmony. Dave Herman wrote up a sketch at
doku.php?id=proposals:modules. It has a "Caveat lector".
This page links to www.mozilla.org/rhino
scopes.html#sharingscopes, which has further sections on sealing and
dynamic scope (which I remember reading long ago -- see the document
history). Again, without sealing of the "super-global", there are
integrity problems.
Anyway, having a first class module system means not having to worry
about prototype and scope link cutting and re-welding, etc. This is
one reason why there must be life beyond ES3.1, which is to say, in
Harmony.
I should also add that Ejscript (www.ejscript.org) successfully
implemented the Program Unit abstraction from ES4 as the basis for a
modules mechanism.
Several distinct functions are being mixed by importModule that should be separated:
- Addressing the module to be imported in an "external" storage hierarchy, whether by URLs on the web or pathnames in a Unix filesystem, etc.
We use optional program URLs, but then also allow external resolution
via an search path for modules.
- Whether loading of code from the addressed module is synchronous or asynchronous with the call to importModule. Local file access probably means importModule is synchronous, but this is wrong for the Web browser embedding.
We've assumed synchronous and don't currently have an async mechanism.
- Once having addressed the module and loaded its contents, how the module's provided names are required and accessed.
We have done this 2 ways now. First without namespaces where all
module properties were enclosed in a module object that was added to
the scope chain. More recently in keeping with the ES4 proposals, we
used namespaces and module names corresponded to a namespace. Either
way, both approaches have worked well.
Many times in TC39 we've discussed the module problem, and most agree that 1 and 2 do not belong in the Ecma core language specification. They belong (at least -- other embeddings matter too) in the HTML5
spec.Item 3 is important, and there's already some work under way to develop an idea based on PLT Scheme, which I'd like to propose for ES- Harmony. Dave Herman wrote up a sketch at doku.php?id=proposals:modules. It has a "Caveat lector".
This page links to www.mozilla.org/rhino scopes.html#sharingscopes, which has further sections on sealing and dynamic scope (which I remember reading long ago -- see the document history). Again, without sealing of the "super-global", there are integrity problems.
Anyway, having a first class module system means not having to worry about prototype and scope link cutting and re-welding, etc. This is one reason why there must be life beyond ES3.1, which is to say, in Harmony.
One other thing modules effectively can solve is order of
initialization over multiple program units.
Michael O'Brien
On Mon, Aug 18, 2008 at 2:42 PM, Brendan Eich <brendan at mozilla.org> wrote:
On Aug 17, 2008, at 8:59 PM, Maksim Lin wrote:
Hi,
In a comment on John Resigs blog about ES-Harmony, Hannes Wallnoefer suggested that a simple module system he has implemented for helma-ng [1] could be used for a future ES versions implementation.
I think Brendan may have misunderstood the proposal as in a later comment he said that : "...Hannes points out how to solve it in-language, but that wheel is (a) a leaky abstraction, which could be abused; (b) something no one should have to re-invent."
which I dont think is right
Which point, (a) or (b)?
both.
This does not work, since it is possible to mutate the properties of mutable objects named by properties on the prototype chain, not merely shadow prototype properties by assigning direct properties of the same name. But
point very well taken! you're very right, properties in the global scope that are objects themselves are up for modification and thats exactly the reason for sealed objects being discussed (as you say) on the rhino docs page. But if this was a std language or embedding implementaton feaure then no one would need to reinvent it.
I'd like to hear more about Helma NG does it.
Hopefully Hannes can chime in on this, as I've not had a proper look at how its implemented, rather just been using it to write some small js modules using the new interface.
From that perspective it works well - perhaps not well enough to stop
the complete global scope modification, but certainly enough for module writers to not step on each others toes and let module user easily seperte out the modules into clear 'namespaces'.
Several distinct functions are being mixed by importModule that should be separated:
- Addressing the module to be imported in an "external" storage hierarchy, whether by URLs on the web or pathnames in a Unix filesystem, etc.
well I guess this is something hat should be left up to the embedding, so yet anther reason perhaps for this to be specified the same way <script> is - outside of ES spec.
- Whether loading of code from the addressed module is synchronous or asynchronous with the call to importModule. Local file access probably means importModule is synchronous, but this is wrong for the Web browser embedding.
yes completely aagree. I do tend to ahve a servr side slant to my thinking. But then again coldn't it be the same a for <script> elements?
- Once having addressed the module and loaded its contents, how the module's provided names are required and accessed.
Well Helma NG has a sensible default and also lets you specify an optional name prefix.
Many times in TC39 we've discussed the module problem, and most agree that 1 and 2 do not belong in the Ecma core language specification. They belong (at least -- other embeddings matter too) in the HTML5 spec.
yep completely agree as I said above.
Item 3 is important, and there's already some work under way to develop an idea based on PLT Scheme, which I'd like to propose for ES-Harmony. Dave Herman wrote up a sketch at proposals:modules. It has a "Caveat lector".
thanks for the ref, I'l make sure to read through it.
Anyway, having a first class module system means not having to worry about prototype and scope link cutting and re-welding, etc. This is one reason why there must be life beyond ES3.1, which is to say, in Harmony.
/be
I would assume that anykind of modules proposal would be post 3.1 ?
Maks,
On Aug 18, 2008, at 5:58 AM, Maksim Lin wrote:
On Mon, Aug 18, 2008 at 2:42 PM, Brendan Eich <brendan at mozilla.org>
wrote:On Aug 17, 2008, at 8:59 PM, Maksim Lin wrote:
I think Brendan may have misunderstood the proposal as in a later comment he said that : "...Hannes points out how to solve it in-language, but that wheel is (a) a leaky abstraction, which could be abused; (b) something no one should have to re-invent."
which I dont think is right
Which point, (a) or (b)?
both.
I hate to quibble, but my point (b) was simply that the language
should support modules in a first-class way. Otherwise, everyone, not
just Hannes et al. in Helma NG, but at least each JS engine
maintainer and probably (at first) every engine embedder has to
reinvent the wheel.
Perhaps we agree. :-/
This does not work, since it is possible to mutate the properties
of mutable objects named by properties on the prototype chain, not merely shadow prototype properties by assigning direct properties of the same
name. Butpoint very well taken! you're very right, properties in the global scope that are objects themselves are up for modification and thats exactly the reason for sealed objects being discussed (as you say) on the rhino docs page. But if this was a std language or embedding implementaton feaure then no one would need to reinvent it.
Right, so I see we agree on (b). Again my point in John's blog was
that without further evolution of the core language, people can only
reinvent module wheels using baling wire and duct tape (proto/parent
link cutting/re-welding) in individual embeddings or engines (if they
upstream the patches).
- Whether loading of code from the addressed module is
synchronous or asynchronous with the call to importModule. Local file access
probably means importModule is synchronous, but this is wrong for the Web browser embedding.yes completely aagree. I do tend to ahve a servr side slant to my
thinking. But then again coldn't it be the same a for <script> elements?
Scripts are synchronously loaded today, but browsers are working on
async loading techniques, and IE promulgated the defer attribute into
HTML5. But if importModulel is just a global function, then there's
no way to avoid blocking mid-script evaluation on it (its call could
be indirect, obscured). That is not possible in some browsers, and
not desirable in any event (scripts run to completion, or seem to; no
preemption, not even by event handlers, unless you fly a dialog that
allows such things).
- Once having addressed the module and loaded its contents, how the module's provided names are required and accessed.
Well Helma NG has a sensible default and also lets you specify an optional name prefix.
Yeah; Python is not a bad inspiration but we are looking at PLT- Scheme's module system too.
I would assume that anykind of modules proposal would be post 3.1 ?
For sure -- ES-Harmony.
On Aug 18, 2008, at 8:35 AM, Brendan Eich wrote:
Scripts are synchronously loaded today, but browsers are working on async loading techniques, and IE promulgated the defer attribute into HTML5.
Er, into HTML4.
(Coffee time! ;-)
In a comment on John Resigs blog about ES-Harmony, Hannes Wallnoefer suggested that a simple module system he has implemented for helma-ng [1] could be used for a future ES versions implementation.
I think Brendan may have misunderstood the proposal as in a later comment he said that : "...Hannes points out how to solve it in-language, but that wheel is (a) a leaky abstraction, which could be abused; (b) something no one should have to re-invent."
which I dont think is right since the way I understand Hannes importModule() to work is that the code that is "imported" from the corresponding js file is given a new object as its parent scope (rather then the global one) and then that objects prototype is set to the global scope. Tis then prevents the imported code from modifying the "real" gloabl scope while still giving it read-access to it. Hopefully I've explained it correctly, so apologies to Hannes if I haven't.
But I can't see how does that work as "in-language". To me it seems that this requires the js implementation to do the above (messing with the parent scope of the imported code) as it can't be done by the application programmer in js unless you use a bunch of proprietary moz API's like the mock example on the helma-ng page:
// set reference to global object var global = global || this;
function include(script, as) { var scope = new Object(); scope.parent = null; scope.proto = global; // scope is now a top level scope that inherits // from the global, shared top level scope scope.load(script); this[as] = scope; }
So instead why not have a new standard function importModule() that does the above as part of the language spec?
Or perhaps it really belongs as part of the Host implementation and should be part of the DOM or something, but then if thats the case, what is the case for having package/module functionality in the ES spec at all?
thanks, Maks.
[1] dev.helma.org/wiki/Modules+and+Scopes+in+Helma+NG