Skip to content

Commit 333df08

Browse files
authored
Merge pull request #2550 from Shopify/jb-current-attributes-compiler
Include type_parameters declarations in signatures
2 parents b8ee369 + b85a6fe commit 333df08

6 files changed

Lines changed: 40 additions & 11 deletions

File tree

lib/tapioca/dsl/compiler.rb

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -139,11 +139,16 @@ def parameters_types_from_signature(method_def, signature)
139139

140140
#: (RBI::Scope scope, (Method | UnboundMethod) method_def, ?class_method: bool) -> void
141141
def create_method_from_def(scope, method_def, class_method: false)
142+
parameters = compile_method_parameters_to_rbi(method_def)
143+
return_type = compile_method_return_type_to_rbi(method_def)
144+
type_params = extract_type_parameters(parameters.map(&:type).push(return_type))
145+
142146
scope.create_method(
143147
method_def.name.to_s,
144-
parameters: compile_method_parameters_to_rbi(method_def),
145-
return_type: compile_method_return_type_to_rbi(method_def),
148+
parameters: parameters,
149+
return_type: return_type,
146150
class_method: class_method,
151+
type_params: type_params,
147152
)
148153
end
149154

lib/tapioca/gem/listeners/sorbet_signatures.rb

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -8,8 +8,6 @@ class SorbetSignatures < Base
88
include Runtime::Reflection
99
include RBIHelper
1010

11-
TYPE_PARAMETER_MATCHER = /T\.type_parameter\(:?([[:word:]]+)\)/
12-
1311
private
1412

1513
# @override
@@ -42,9 +40,7 @@ def compile_signature(signature, parameters)
4240
sig.return_type = return_type
4341
@pipeline.push_symbol(return_type)
4442

45-
parameter_types.values.join(", ").scan(TYPE_PARAMETER_MATCHER).flatten.uniq.each do |k, _|
46-
sig.type_params << k
47-
end
43+
sig.type_params.concat(extract_type_parameters(parameter_types.values.map(&:to_s).push(return_type)))
4844

4945
case signature.mode
5046
when "abstract"

lib/tapioca/helpers/rbi_helper.rb

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -94,6 +94,13 @@ def as_non_nilable_type(type)
9494
end
9595
end
9696

97+
TYPE_PARAMETER_MATCHER = /T\.type_parameter\(:?([[:word:]]+)\)/
98+
99+
#: (Array[String] type_strings) -> Array[String]
100+
def extract_type_parameters(type_strings)
101+
type_strings.join(", ").scan(TYPE_PARAMETER_MATCHER).flatten.uniq
102+
end
103+
97104
#: (String name) -> bool
98105
def valid_method_name?(name)
99106
Prism.parse_success?("def self.#{name}(a); end")

lib/tapioca/rbi_ext/model.rb

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -65,10 +65,11 @@ def create_type_variable(name, type:, variance: :invariant, fixed: nil, upper: n
6565
#| ?return_type: String?,
6666
#| ?class_method: bool,
6767
#| ?visibility: RBI::Visibility,
68-
#| ?comments: Array[RBI::Comment]
68+
#| ?comments: Array[RBI::Comment],
69+
#| ?type_params: Array[String]
6970
#| ) ?{ (RBI::Method node) -> void } -> void
7071
def create_method(name, parameters: [], return_type: nil, class_method: false, visibility: RBI::Public.new,
71-
comments: [], &block)
72+
comments: [], type_params: [], &block)
7273
return unless Tapioca::RBIHelper.valid_method_name?(name)
7374

7475
sigs = []
@@ -77,7 +78,7 @@ def create_method(name, parameters: [], return_type: nil, class_method: false, v
7778
# If there is no block, and the params and return type have not been supplied, then
7879
# we create a single signature with the given parameters and return type
7980
params = parameters.map { |param| RBI::SigParam.new(param.param.name.to_s, param.type) }
80-
sigs << RBI::Sig.new(params: params, return_type: return_type || "T.untyped")
81+
sigs << RBI::Sig.new(params: params, return_type: return_type || "T.untyped", type_params: type_params)
8182
end
8283

8384
method = RBI::Method.new(

spec/tapioca/dsl/compiler_spec.rb

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,15 @@ def bar(a, b = 42, *c)
9292
def baz(d:, e: 42, **f, &blk)
9393
end
9494
95+
sig do
96+
type_parameters(:U, :V)
97+
.params(a: T.type_parameter(:U), blk: T.proc.params(arg: T.type_parameter(:U)).returns(T.type_parameter(:V)))
98+
.returns(T.type_parameter(:V))
99+
end
100+
def complex_type_params(a, &blk)
101+
blk.call(a)
102+
end
103+
95104
sig { type_parameters(:U).params(a: T.type_parameter(:U)).returns(T.type_parameter(:U)) }
96105
def foo(a)
97106
a
@@ -120,7 +129,10 @@ def bar(a, b = T.unsafe(nil), *c); end
120129
sig { params(d: ::String, e: ::Integer, f: ::Integer, blk: T.proc.params(a: ::String).returns(::String)).returns(::Integer) }
121130
def baz(d:, e: T.unsafe(nil), **f, &blk); end
122131
123-
sig { params(a: T.type_parameter(:U)).returns(T.type_parameter(:U)) }
132+
sig { type_parameters(:U, :V).params(a: T.type_parameter(:U), blk: T.proc.params(arg: T.type_parameter(:U)).returns(T.type_parameter(:V))).returns(T.type_parameter(:V)) }
133+
def complex_type_params(a, &blk); end
134+
135+
sig { type_parameters(:U).params(a: T.type_parameter(:U)).returns(T.type_parameter(:U)) }
124136
def foo(a); end
125137
126138
sig { params(a: ::Integer, b: ::Integer, c: ::Integer, d: ::Integer, e: ::Integer, f: ::Integer, blk: T.proc.void).void }

spec/tapioca/dsl/compilers/active_support_current_attributes_spec.rb

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -159,6 +159,11 @@ def user_id
159159
def user_id=(value)
160160
super
161161
end
162+
163+
sig { type_parameters(:T).params(t: T.untyped, blk: T.proc.returns(T.type_parameter(:T))).returns(T.type_parameter(:T)) }
164+
def with_type(t, &blk)
165+
blk.call
166+
end
162167
end
163168
RUBY
164169

@@ -174,6 +179,9 @@ def user_id; end
174179
175180
sig { params(value: T.nilable(::Integer)).void }
176181
def user_id=(value); end
182+
183+
sig { type_parameters(:T).params(t: T.untyped, blk: T.proc.returns(T.type_parameter(:T))).returns(T.type_parameter(:T)) }
184+
def with_type(t, &blk); end
177185
end
178186
179187
module GeneratedAttributeMethods

0 commit comments

Comments
 (0)