benjamn / ast-types

Esprima-compatible implementation of the Mozilla JS Parser API
MIT License
1.14k stars 197 forks source link

passing along source location when building nodes #23

Open jlongster opened 10 years ago

jlongster commented 10 years ago

The problem I had before was due to transformations not keeping the source locations in the final nodes. There are a few key places that need to copy along the source locs.

What's the right pattern to do this with builders? Do I need to assign the node to a variable and then do something like newNode.loc = oldNode.loc? Or can I pass along the source locations to the builders somehow?

benjamn commented 10 years ago

Technically the location object that really matters is newNode.original.loc, so you might be able to do newNode.original = oldNode.original. Then, if newNode.type === oldNode.type, the reprinter should be able to reuse the source from oldNode.

Those .original properties get set in the copyAst function: https://github.com/benjamn/recast/blob/1ddd828daaed35a43999331acafd761bf5430edf/lib/parser.js#L125

The idea is that recast.parse hands you back a copied AST where every node starts out with an .original property referring to the AST node originally produced by Esprima, so as you modify the copied tree the new nodes you introduce won't have an .original property, so they will be printed by the pretty-printer instead of getting reprinted using the original source.

GianlucaGuarini commented 5 years ago

@benjamn your answer is now 4 years old and I don't think it's still working. Is there a way to define the node location with the newest ast-types and recast versions? Your help will be really appreciate.

I guess something like that should work but it will not :(

const node = builders.callExpression(builders.identifier('foo'), [])

node.loc = {
  start: { line: 10, column: 0 },
  end: { line: 10, column: 3 }
}

const {map} = recast.print(node)
GianlucaGuarini commented 5 years ago

I have made also a live demo to show the issue https://runkit.com/gianlucaguarini/5c5b1271e4b0c90013575af7 @benjamn any help would be really appreciated!

I am using ast-types and recast in the new @riotjs/compiler and this is the only issue am not able to solve since a couple of weeks