Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rewrite RBI generation for gems #297

Merged
merged 7 commits into from May 4, 2021
Merged

Rewrite RBI generation for gems #297

merged 7 commits into from May 4, 2021

Conversation

Morriar
Copy link
Collaborator

@Morriar Morriar commented Apr 28, 2021

Motivation

This PR makes the RBI generation for gems more flexible by introducing a clean and extensible API.

Implementation

  1. The first commit introduce the new RBI generation API
  2. The second uses this API in symbol_generator
  3. The subsequent commits apply minor cosmetic changes to the current tests

I recommend reading the changes on the test file commit by commit.

Tests

See included tests.

@Morriar Morriar requested a review from a team April 28, 2021 22:48
@Morriar Morriar self-assigned this Apr 28, 2021
@Morriar Morriar force-pushed the at-rbi-gen branch 4 times, most recently from b2fbcc2 to d850143 Compare April 28, 2021 23:13
Copy link
Contributor

@KaanOzkan KaanOzkan left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a few comments. I haven't gone over symbol_generator.rb in detail in terms of equivalence but the tests provide confidence. I am okay with the formatting changes with the new builder such as no parentheses and single line definitions for empty classes/modules.

Rewriters and rbi tests look good to me.

lib/tapioca/rbi/printer.rb Show resolved Hide resolved
sig { override.params(v: Printer).void }
def accept_printer(v)
v.printl(visibility.to_s)
end
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We are printing visibility information both alongside method definition and on its own in a class. Given that RBIs are also used as documentation in Jump to definition I'm curious if it'll be better to always add visibility information to the method definition and print alongside it. While never printing a Visibility node on its own for methods?

private def foo; end

vs

private
...
def foo; end

Copy link
Collaborator Author

@Morriar Morriar Apr 30, 2021

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point. I'm all in favor (it also removes the need of NestNonPublicMethods). Curious of @paracycle's opinion on this?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Like @KaanOzkan said, it would definitely make the privacy level of the method more accessible, at the risk of making the RBI more verbose. I like the idea and we can have it as the default, but it would be nice to allow this to be configurable, if possible.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll provide a follow up PR making this kind of option available from the CLI, wdyt?

lib/tapioca/rbi/rewriters/sort_nodes.rb Show resolved Hide resolved
Copy link
Member

@paracycle paracycle left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I left a couple of comments but this is sooo much nicer than what we had before. Thank you, this looks great.

lib/tapioca/rbi/rewriters/nest_non_public_methods.rb Outdated Show resolved Hide resolved
return if symbol_ignored?(name)
klass = class_of(value)
klass_name = name_of(klass)

return if klass_name&.start_with?("T::Types::", "T::Private::")

type_name = public_module?(klass) && klass_name || "T.untyped"
indented("#{name} = T.let(T.unsafe(nil), #{type_name})")
tree << RBI::Const.new(name, "T.let(T.unsafe(nil), #{type_name})")
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Observation: It might be good to make the T.let(T.unsafe(nil), XXX) part encapsulated by introducing something like an RBI:ValueConst.new(name, type: type) thing.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's a good idea but I'm not convinced in the naming nor the API, do you mind if we wait the rewrite of the DSL part to get more use cases and figure what's best?

lib/tapioca/compilers/symbol_table/symbol_generator.rb Outdated Show resolved Hide resolved
lib/tapioca/compilers/symbol_table/symbol_generator.rb Outdated Show resolved Hide resolved
Copy link
Contributor

@mutecipher mutecipher left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

200w

lib/tapioca/rbi/model.rb Show resolved Hide resolved
lib/tapioca/rbi/printer.rb Show resolved Hide resolved
end

sig { params(string: T.nilable(String)).void }
def printt(string = nil)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we use a more descriptive name? Maybe indented_print?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would prefer not.

I chose those names so it aligns nicely in the code:

v.indent
v.printt "some code"
v.printn "some other code"
v.printl "more code"
v.dedent

I added a comment on each of them to explain the behaviour. Is it better?

lib/tapioca/rbi/printer.rb Show resolved Hide resolved
lib/tapioca/rbi/printer.rb Outdated Show resolved Hide resolved
lib/tapioca/rbi/rewriters/group_nodes.rb Outdated Show resolved Hide resolved
Signed-off-by: Alexandre Terrasa <alexandre.terrasa@shopify.com>
Signed-off-by: Alexandre Terrasa <alexandre.terrasa@shopify.com>
Signed-off-by: Alexandre Terrasa <alexandre.terrasa@shopify.com>
Signed-off-by: Alexandre Terrasa <alexandre.terrasa@shopify.com>
Signed-off-by: Alexandre Terrasa <alexandre.terrasa@shopify.com>
Signed-off-by: Alexandre Terrasa <alexandre.terrasa@shopify.com>
Signed-off-by: Alexandre Terrasa <alexandre.terrasa@shopify.com>
Copy link
Member

@vinistock vinistock left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Awesome work 🚀

@Morriar Morriar merged commit 8cec0e3 into master May 4, 2021
@Morriar Morriar deleted the at-rbi-gen branch May 4, 2021 19:42
@shopify-shipit shopify-shipit bot temporarily deployed to production May 19, 2021 17:37 Inactive
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

5 participants