1.3.1 • Published 8 years ago

esdom v1.3.1

Weekly downloads
7
License
Unlicensed
Repository
github
Last release
8 years ago

esdom Build Status Code Climate

DEMO

Build up DOM from AST or AST from DOM. Just because DOM is something more familiar to web-developers than AST, though there are tools like esquery or ast-types. ESDOM is forward-compatible with esquery, so everything is done via esdom can be painlessly refactored to use esquery.

Works both in browsers and node.

$ npm install esdom

var esdom = require('esdom');
var esprima = require('esprima');
var escodegen = require('escodegen');

var ast = esprima.parse(code);

var el = esdom.toDOM(ast);
el.querySelector('Identifier').setAttribute('name', 'x');
ast = esdom.toAST(el);

escodegen.print(ast);

Mapping nodes

Mapping is done to be compatible with ESQuery selectors as much as possible.

Let’s take an examplary source:

var a = 1;

AST for the source will be:

{
	"type": "Program",
	"body": [
		{
			"type": "VariableDeclaration",
			"declarations": [
				{
					"type": "VariableDeclarator",
					"id": {
						"type": "Identifier",
						"name": "a"
					},
					"init": {
						"type": "Literal",
						"value": 1,
						"raw": "1"
					}
				}
			],
			"kind": "var"
		}
	]
}

And resulting HTML:

<program class="Program Node Printable" type="Program" body="[]">
	<variabledeclaration class="VariableDeclaration Declaration Statement Node Printable" type="VariableDeclaration" declarations="[]" kind="var" prop="body">
		<variabledeclarator class="VariableDeclarator Node Printable" type="VariableDeclarator" id="Identifier" init="Literal" prop="declarations">
			<identifier class="Identifier Expression Pattern Node Printable" type="Identifier" name="a" prop="id"></identifier>
			<literal class="Literal Expression Pattern Node Printable" type="Literal" value="1" raw="1" prop="init"></literal>
		</variabledeclarator>
	</variabledeclaration>
</program>

So all esquery css selectors work just fine with that html, with some exceptions:

  • :first-child and :last-child selectors always return non-empty result, where esquery may return nothing. For example, selector VariableDeclarator > Identifier:first-child returns <Identifier>, where esquery returns null.
  • Nested attribute selector should be replaced with subject indicator (or :has): [attr.subAttr=xyz]![attr] > [subAttr=xyz]
  • To select custom esquery pseudos like :statement, it is recommended to use esdom/query, otherwise it should be replaced with natural DOM class .Statement.
  • Regular expression and conditional selectors should be replaced with according css selectors.

In all other regards it works just the same.

Notes

  • esquery is inable to select list of nodes, like all function params, or all function body statements. With esdom you can do .Function > [prop="params"].
  • esdom might be somewhat slow in browsers due to using browser API. In node, DOM is emulated via dom-lite, so it’s times faster.
  • esdom work only with ES5.

Analysis

ESDOM also provides helpful scope/variable analysis, marking nodes with additional data- attributes. To analyze DOM, call esdom.analyze(dom), and it will set attributes:

AttributeDescription
data-scope=<id>Scope indicator
data-scope-globalGlobal scope flag
data-scope-parent=<scope-id>Parent scope id
data-variable=<id>Variable indicator with unique id
data-variable-declarationVariable declaration flag
data-variable-scope=<scope-id>Variable holding scope

API

MethodDescription
.toDOM(ast)Convert AST to DOM element.
.toAST(element)Build AST from DOM element.
.analyze(element)Mark up AST nodes

NPM