Issue #14844 has been updated by Eregon (Benoit Daloze).


Eregon (Benoit Daloze) wrote:
> I think we should have nodes with methods to access each part/field, such as ModuleDefinitionNode#body, ModuleDefinitionNode#name, etc.

A simpler alternative would be something like `RubyVM::AbstractSyntaxTree::Node#[]` to access fields of a node by name.
This would make the API much easier to use, using hardcoded offsets is not good for evolution and is really hard to use (even with pattern matching!).

Actually, we already have names, but they only seem to be shown with #pp:

```ruby
[3] pry(main)> node = RubyVM::AbstractSyntaxTree.parse("def foo; 42; end")
=> (SCOPE@1:0-1:16
 tbl: []
 args: nil
 body:
   (DEFN@1:0-1:16
    mid: :foo
    body:
      (SCOPE@1:0-1:16
       tbl: []
       args:
         (ARGS@1:7-1:7
          pre_num: 0
          pre_init: nil
          opt: nil
          first_post: nil
          post_num: 0
          post_init: nil
          rest: nil
          kw: nil
          kwrest: nil
          block: nil)
       body: (LIT@1:9-1:11 42))))
[7] pry(main)> node.children[2].children[0]
=> :foo
[8] pry(main)> node[:body][:mid]
NoMethodError: undefined method '[]' for #<RubyVM::AbstractSyntaxTree::Node:SCOPE@1:0-1:16>
[9] pry(main)> node.dig(:body, :mid)
NoMethodError: undefined method 'dig' for #<RubyVM::AbstractSyntaxTree::Node:SCOPE@1:0-1:16>
```

This would make AbstractSyntaxTree easier to use, more portable and possible to evolve without breaking code.

Note that some of these names seem a bit obscure and would be worth to be renamed to be clearer, e.g., `tbl` which seems to be the list of local variables.
(Similrly, `mid` could be `method_id` like in `TracePoint`)

FWIW, it seems many people are already using AbstractSyntaxTree, and most likely are not aware of the drawbacks (not stable API, cannot evolve the API safely currently, MRI-specific currently, might not represent the source faithfully, etc). Here is just one example: https://github.com/oracle/truffleruby/issues/1671

----------------------------------------
Feature #14844: Future of RubyVM::AST? 
https://bugs.ruby-lang.org/issues/14844#change-77665

* Author: rmosolgo (Robert Mosolgo)
* Status: Open
* Priority: Normal
* Assignee: 
* Target version: 
----------------------------------------
Hi! Thanks for all your great work on the Ruby language. 

I saw the new RubyVM::AST module in 2.6.0-preview2 and I quickly went to try it out. 

I'd love to have a well-documented, user-friendly way to parse and manipulate Ruby code using the Ruby standard library, so I'm pretty excited to try it out. (I've been trying to learn Ripper recently, too: https://ripper-preview.herokuapp.com/, https://rmosolgo.github.io/ripper_events/ .)

Based on my exploration, I opened a small PR on GitHub with some documentation: https://github.com/ruby/ruby/pull/1888

I'm curious though, are there future plans for this module? For example, we might: 

- Add more details about each node (for example, we could expose the names of identifiers and operators through the node classes)
- Document each node type 

I see there is a lot more information in the C structures that we could expose, and I'm interested to help out if it's valuable. What do you think? 



-- 
https://bugs.ruby-lang.org/

Unsubscribe: <mailto:ruby-core-request / ruby-lang.org?subject=unsubscribe>
<http://lists.ruby-lang.org/cgi-bin/mailman/options/ruby-core>