What is estree-walker?
The estree-walker package is a simple utility for walking an ESTree-compliant AST (Abstract Syntax Tree), such as those produced by parsers like Acorn or Esprima. It allows users to traverse the tree and manipulate nodes during the traversal.
What are estree-walker's main functionalities?
Walking an AST
This feature allows you to traverse an AST, performing actions when entering and leaving each node. The 'enter' function is called when a node is entered, and the 'leave' function is called when a node is left during the traversal.
const { walk } = require('estree-walker');
const ast = { /* some AST object */ };
walk(ast, {
enter(node, parent, prop, index) {
// Perform actions upon entering a node
},
leave(node, parent, prop, index) {
// Perform actions upon leaving a node
}
});
Manipulating Nodes
This feature demonstrates how you can manipulate nodes during traversal. In this example, numeric literal values are doubled.
const { walk } = require('estree-walker');
const ast = { /* some AST object */ };
walk(ast, {
enter(node) {
if (node.type === 'Literal' && typeof node.value === 'number') {
node.value *= 2; // Double the number
}
}
});
Other packages similar to estree-walker
acorn-walk
Acorn-walk is a small, fast, JavaScript-based AST walker for the Acorn parser. It provides similar functionality to estree-walker but is specifically designed to work with the ASTs generated by Acorn.
babel-traverse
Babel-traverse is part of the Babel toolchain and allows for traversing and manipulating Babel-generated ASTs. It offers a more complex API and additional features compared to estree-walker, such as scope tracking and path manipulation.
recast
Recast provides AST traversal and manipulation capabilities, as well as source map support and pretty-printing of the modified code. It is more feature-rich than estree-walker and integrates with the Esprima parser.
estree-walker
Simple utility for walking an ESTree-compliant AST, such as one generated by acorn.
Installation
npm i estree-walker
Usage
var walk = require( 'estree-walker' ).walk;
var acorn = require( 'acorn' );
ast = acorn.parse( sourceCode, options );
walk( ast, {
enter: function ( node, parent, prop, index ) {
},
leave: function ( node, parent, prop, index ) {
}
});
Inside the enter
function, calling this.skip()
will prevent the node's children being walked, or the leave
function (which is optional) being called.
Call this.replace(new_node)
in either enter
or leave
to replace the current node with a new one.
Call this.remove()
in either enter
or leave
to remove the current node.
Why not use estraverse?
The ESTree spec is evolving to accommodate ES6/7. I've had a couple of experiences where estraverse was unable to handle an AST generated by recent versions of acorn, because it hard-codes visitor keys.
estree-walker, by contrast, simply enumerates a node's properties to find child nodes (and child lists of nodes), and is therefore resistant to spec changes. It's also much smaller. (The performance, if you're wondering, is basically identical.)
None of which should be taken as criticism of estraverse, which has more features and has been battle-tested in many more situations, and for which I'm very grateful.
License
MIT