JS syntax future-proofing, Macros, the "Reader" (was: Performance concern with let/const)
| But if we have macros, then many progressive | enhancement and anti-regressive polyfill approaches can be done, even | with new syntax (not just with APIs).
Seems like another good way of fixing the issue :-) However, this seems to require some form of conditionnal compilation to work , right? [1]
[1] www.javascriptkit.com/javatutors/conditionalcompile.shtml
François REMY wrote:
| But if we have macros, then many progressive | enhancement and anti-regressive polyfill approaches can be done, even | with new syntax (not just with APIs).
Seems like another good way of fixing the issue :-) However, this seems to require some form of conditionnal compilation to work , right? [1]
[1] www.javascriptkit.com/javatutors/conditionalcompile.shtml
Macros have nothing to do with conditional compilation per se. When you read Macros in a JS context, don't think the C Pre-Processor, think Scheme!
My point is: how do you make sure you don't redefine an existing syntax? Or, if that the syntax you're defining for your personnal use will not be reclaimed by a next version of ES?
// Polyfill for syntaxFeature:
/*@cc_on
/*@if !support syntaxFeature */
code that emulate the syntaxFeature
/* @endif */
*/
There's probably an anwser to that question, it's just that I'm not aware of it already :-)
-----Message d'origine---
François REMY wrote:
My point is: how do you make sure you don't redefine an existing syntax? Or, if that the syntax you're defining for your personnal use will not be reclaimed by a next version of ES?
// Polyfill for syntaxFeature: /@cc_on /@if !support syntaxFeature / code that emulate the syntaxFeature / @endif */ */
There's probably an anwser to that question, it's just that I'm not aware of it already :-)
Yes, polyfilling means has-syntax testing. I'm told the sweet.js project is considering how to do this, but I bet a donut that it'll not look like CPP or @-CPP or any such ugly blast from the past.
More in a bit.
It's still early to say. But my feeling is that if we can get macros working, we can introduce new syntax via modules, not just unconditionally throwing them in everywhere. Then you don't have to do these kinds of global conditional things; rather, you just import the syntax from modules. The dynamic testing would then be done during app setup, when you construct your global environment before running the client code that uses it.
The goal of macros is to make syntax more modular.
On 09/18/2012 09:47 AM, Brendan Eich wrote:
- Tim Disney with help from Paul Stansifer (Mozilla grad student interns) have figured out how to implement a Reader (Scheme sense) for JS, which does not fully parse JS but nevertheless correctly disambiguates /-as-division-operator from /-as-regexp-delimiter. See
This Reader handles bracketed forms: () {} [] and /re/. Presumably it could handle quasis too. Since these bracketed forms can nest, the Reader is a PDA and so more powerful than the Lexer (a DFA or equivalent), but it is much simpler than a full JS parser -- and you need a Reader for macros.
That's not possible. See, for example, the case I showed during the meeting:
boom = yield/area/ height;
Is /area/ a regexp or two divisions and a variable? You can't tell if you're using a purported universal parser based on ES5.1 and are unaware that yield is a contextual keyword which will be introduced into the language in ES6. And yes, you can then get arbitrarily out of sync:
boom = yield/a+"3/ string?" ...
Waldemar
Waldemar Horwat wrote:
On 09/18/2012 09:47 AM, Brendan Eich wrote:
- Tim Disney with help from Paul Stansifer (Mozilla grad student interns) have figured out how to implement a Reader (Scheme sense) for JS, which does not fully parse JS but nevertheless correctly disambiguates /-as-division-operator from /-as-regexp-delimiter. See
This Reader handles bracketed forms: () {} [] and /re/. Presumably it could handle quasis too. Since these bracketed forms can nest, the Reader is a PDA and so more powerful than the Lexer (a DFA or equivalent), but it is much simpler than a full JS parser -- and you need a Reader for macros.
That's not possible. See, for example, the case I showed during the meeting:
boom = yield/area/ height;
Is /area/ a regexp or two divisions and a variable? You can't tell if you're using a purported universal parser based on ES5.1 and are unaware that yield is a contextual keyword which will be introduced into the language in ES6. And yes, you can then get arbitrarily out of sync:
boom = yield/a+"3/ string?" ...
As I said to you at the meeting, there may be no problem if we simply stop adding contextual keywords and add macros instead.
We already gave up on adding /re/x and good riddance. Getting macros while freezing special form syntax strikes me as possibly a very good trade-off. What do you think?
François REMY wrote:
Hixie and Maciej raised this in 2007, IIRC (or was it 2008? Anyway, ES4 days). Waldemar and Lars Hansen shot it down because we thought (a) lexing requires parsing to disambiguate / uses; (b) it's future-hostile to new forms such as quasi-literals and (then still-proposed) /re/x variants.
Two things have happened since then that I find relevant:
We re-considered adding /re/x and decided not to, for similar reasons to those that stopped Hixie's idea. Complicating regexp syntax a la Perl's /x flag makes it even harder to parse JS, and embedded comments play hob (or must be banned).
Tim Disney with help from Paul Stansifer (Mozilla grad student interns) have figured out how to implement a Reader (Scheme sense) for JS, which does not fully parse JS but nevertheless correctly disambiguates /-as-division-operator from /-as-regexp-delimiter. See
mozilla/sweet.js
This Reader handles bracketed forms: () {} [] and /re/. Presumably it could handle quasis too. Since these bracketed forms can nest, the Reader is a PDA and so more powerful than the Lexer (a DFA or equivalent), but it is much simpler than a full JS parser -- and you need a Reader for macros.
So perhaps we are finally almost (kind of, getting there) ready to future-proof for macros by closing the door to more syntax of the regexp /x flag, or even yet another quasi-literal, kind.
If I recall correctly, Hixie's and Maciej's CSS-like error recovery (by old user agents facing new syntax) hope still seems misplaced. In CSS you can specify error recovery so that unknown style rules are skipped. In a version of JS extended per Hixie's idea, if an old user agent should skip
keyword ( head ) { body }
then how does the JS programmer write fallback or graceful-degradation code, or otherwise detect that keyword is not supported by the browser that loaded this content?
Without macros, you can't polyfill syntax. So such a new keyword could be used only for progressive enhancements, never for something that must not regress on older browsers.
That limits the appeal. But if we have macros, then many progressive enhancement and anti-regressive polyfill approaches can be done, even with new syntax (not just with APIs).
Yay, macros!