(feat. Babel, plugins and macros)
Perspective
A close look at our toolset
How to extend those tools
Learning from other languages
Easy to understand
Not too verbose
Eloquently describes something that is complex
(list 10 20)
(add 10 20 30)
(define add
(lambda (x y z)
(+ x y z)))
(list 10 20 30)
'(list 10 20 30)
Minimalism
Extensibility
First class functions
Closures
First class functions
Closures
eval
(the compiler)
Tokenize
Parse
Transform
Generate
(Tokenization)
program: String => tokens: Array<Object>
(Parsing)
tokens: Array<Object> => AST: Tree
where Tree is really just Object
originalAST: Tree => transformedAST: Tree
(of code)
AST: Tree => program: String
Walks the AST
Visits each node in depth first order
Is invoked by the transformer
Passed to the Traverser
Decides what happens when traverser enters or exits a node
We will define this for plugins
transformer(ast) {
...
let visitor = {
Identiier: {
enter() {
// Do stuff
}
exit () {
// Other stuff
}
}
BinaryExpression() {
// Only do stuff when entering
}
...
};
let newAst = traverse(ast, visitor);
...
return newAst;
}
Syntax plugins
Transform plugins
Things that can syntactically parse and transform code around them
Evaluated at compile time
babel-plugin-macros
Macros transform code
Extend language compilers
as well as frameworks that restrict modifications to the compiler
Macros over plugins
Generally easier to write
Less configuration
There's a lot to be learned from other languages
It pays off to keep an open mind
JavaScript is awesome
Thanks!