rbs 3.2.2 → 3.3.0.pre.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.github/workflows/comments.yml +1 -1
- data/.github/workflows/ruby.yml +7 -2
- data/CHANGELOG.md +85 -0
- data/Gemfile.lock +14 -14
- data/README.md +11 -2
- data/Rakefile +10 -7
- data/Steepfile +7 -7
- data/core/basic_object.rbs +7 -7
- data/core/binding.rbs +3 -3
- data/core/builtin.rbs +171 -5
- data/core/constants.rbs +17 -17
- data/core/dir.rbs +3 -3
- data/core/encoding.rbs +434 -628
- data/core/enumerator.rbs +37 -0
- data/core/exception.rbs +11 -11
- data/core/false_class.rbs +5 -11
- data/core/fiber.rbs +3 -3
- data/core/file_test.rbs +28 -26
- data/core/kernel.rbs +900 -21
- data/core/marshal.rbs +24 -14
- data/core/match_data.rbs +8 -8
- data/core/math.rbs +57 -53
- data/core/method.rbs +3 -1
- data/core/module.rbs +38 -36
- data/core/nil_class.rbs +7 -13
- data/core/object.rbs +3 -966
- data/core/process.rbs +3 -3
- data/core/ractor.rbs +2 -2
- data/core/rb_config.rbs +64 -43
- data/core/regexp.rbs +3 -3
- data/core/signal.rbs +10 -4
- data/core/struct.rbs +1 -1
- data/core/thread.rbs +7 -7
- data/core/thread_group.rbs +9 -9
- data/core/true_class.rbs +5 -11
- data/core/unbound_method.rbs +56 -7
- data/core/warning.rbs +33 -0
- data/docs/collection.md +56 -6
- data/docs/data_and_struct.md +57 -0
- data/docs/stdlib.md +61 -2
- data/docs/syntax.md +123 -2
- data/ext/rbs_extension/lexer.c +624 -569
- data/ext/rbs_extension/lexer.h +1 -0
- data/ext/rbs_extension/lexer.re +1 -0
- data/ext/rbs_extension/lexstate.c +1 -0
- data/ext/rbs_extension/parser.c +6 -0
- data/goodcheck.yml +2 -2
- data/lib/rbs/annotate/formatter.rb +13 -3
- data/lib/rbs/annotate/rdoc_source.rb +10 -1
- data/lib/rbs/cli/colored_io.rb +48 -0
- data/lib/rbs/cli/diff.rb +80 -0
- data/lib/rbs/cli.rb +151 -16
- data/lib/rbs/collection/config/lockfile.rb +0 -25
- data/lib/rbs/collection/config/lockfile_generator.rb +0 -6
- data/lib/rbs/collection/installer.rb +1 -1
- data/lib/rbs/collection/sources/git.rb +6 -4
- data/lib/rbs/collection/sources/local.rb +7 -5
- data/lib/rbs/diff.rb +104 -0
- data/lib/rbs/environment.rb +1 -1
- data/lib/rbs/method_type.rb +23 -0
- data/lib/rbs/prototype/rb.rb +2 -9
- data/lib/rbs/prototype/runtime/helpers.rb +59 -0
- data/lib/rbs/prototype/runtime/value_object_generator.rb +236 -0
- data/lib/rbs/prototype/runtime.rb +234 -150
- data/lib/rbs/sorter.rb +144 -117
- data/lib/rbs/test/guaranteed.rb +31 -0
- data/lib/rbs/test/type_check.rb +4 -4
- data/lib/rbs/test.rb +3 -0
- data/lib/rbs/types.rb +184 -3
- data/lib/rbs/version.rb +1 -1
- data/lib/rbs/writer.rb +4 -4
- data/lib/rbs.rb +1 -0
- data/rbs.gemspec +1 -0
- data/sig/annotate/formatter.rbs +2 -2
- data/sig/annotate/rdoc_annotater.rbs +1 -1
- data/sig/cli/colored_io.rbs +15 -0
- data/sig/cli/diff.rbs +21 -0
- data/sig/cli.rbs +2 -0
- data/sig/collection/config/lockfile.rbs +0 -6
- data/sig/diff.rbs +23 -0
- data/sig/errors.rbs +1 -5
- data/sig/method_types.rbs +6 -0
- data/sig/prototype/runtime.rbs +108 -0
- data/sig/rdoc/rbs.rbs +4 -0
- data/sig/shims/bundler.rbs +5 -0
- data/sig/sorter.rbs +23 -5
- data/sig/types.rbs +29 -0
- data/stdlib/benchmark/0/benchmark.rbs +1 -1
- data/stdlib/cgi/0/core.rbs +2 -2
- data/stdlib/did_you_mean/0/did_you_mean.rbs +2 -2
- data/stdlib/digest/0/digest.rbs +1 -1
- data/stdlib/fileutils/0/fileutils.rbs +1 -1
- data/stdlib/forwardable/0/forwardable.rbs +4 -4
- data/stdlib/io-console/0/io-console.rbs +1 -1
- data/stdlib/json/0/json.rbs +37 -0
- data/stdlib/logger/0/logger.rbs +2 -2
- data/stdlib/net-http/0/manifest.yaml +1 -1
- data/stdlib/net-http/0/net-http.rbs +16 -63
- data/stdlib/net-protocol/0/manifest.yaml +2 -0
- data/stdlib/net-protocol/0/net-protocol.rbs +56 -0
- data/stdlib/openssl/0/openssl.rbs +1 -1
- data/stdlib/pp/0/manifest.yaml +2 -0
- data/stdlib/pp/0/pp.rbs +301 -0
- data/stdlib/{yaml → psych}/0/dbm.rbs +3 -3
- data/stdlib/psych/0/manifest.yaml +3 -0
- data/stdlib/psych/0/psych.rbs +391 -0
- data/stdlib/{yaml → psych}/0/store.rbs +2 -2
- data/stdlib/rdoc/0/code_object.rbs +55 -0
- data/stdlib/rdoc/0/comment.rbs +60 -0
- data/stdlib/rdoc/0/context.rbs +153 -0
- data/stdlib/rdoc/0/markup.rbs +119 -0
- data/stdlib/rdoc/0/parser.rbs +56 -0
- data/stdlib/rdoc/0/rdoc.rbs +0 -372
- data/stdlib/rdoc/0/ri.rbs +17 -0
- data/stdlib/rdoc/0/store.rbs +48 -0
- data/stdlib/rdoc/0/top_level.rbs +97 -0
- data/stdlib/socket/0/basic_socket.rbs +1 -1
- data/stdlib/socket/0/socket.rbs +1 -1
- data/stdlib/uri/0/common.rbs +1 -1
- data/stdlib/yaml/0/manifest.yaml +1 -2
- data/stdlib/yaml/0/yaml.rbs +1 -199
- metadata +46 -9
- data/sig/shims/pp.rbs +0 -3
- data/sig/shims.rbs +0 -47
|
@@ -1,26 +1,82 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
|
+
require_relative 'runtime/helpers'
|
|
4
|
+
require_relative 'runtime/value_object_generator'
|
|
5
|
+
|
|
3
6
|
module RBS
|
|
4
7
|
module Prototype
|
|
5
8
|
class Runtime
|
|
6
|
-
|
|
9
|
+
class Todo
|
|
10
|
+
def initialize(builder:)
|
|
11
|
+
@builder = builder
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
def skip_mixin?(type_name:, module_name:, mixin_class:)
|
|
15
|
+
return false unless @builder.env.module_class_entry(type_name.absolute!)
|
|
16
|
+
return false unless @builder.env.module_class_entry(module_name.absolute!)
|
|
17
|
+
|
|
18
|
+
mixin_decls(type_name).any? do |decl|
|
|
19
|
+
decl.instance_of?(mixin_class) && decl.name == module_name.absolute!
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def skip_singleton_method?(module_name:, method:, accessibility:)
|
|
24
|
+
return false unless @builder.env.module_class_entry(module_name.absolute!)
|
|
25
|
+
|
|
26
|
+
method_definition = @builder.build_singleton(module_name.absolute!).methods[method.name]
|
|
27
|
+
return false unless method_definition
|
|
28
|
+
|
|
29
|
+
method_definition.accessibility == accessibility
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
def skip_instance_method?(module_name:, method:, accessibility:)
|
|
33
|
+
return false unless @builder.env.module_class_entry(module_name.absolute!)
|
|
34
|
+
|
|
35
|
+
method_definition = @builder.build_instance(module_name.absolute!).methods[method.name]
|
|
36
|
+
return false unless method_definition
|
|
37
|
+
|
|
38
|
+
method_definition.accessibility == accessibility
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
def skip_constant?(module_name:, name:)
|
|
42
|
+
namespace = Namespace.new(path: module_name.split('::').map(&:to_sym), absolute: true)
|
|
43
|
+
@builder.env.constant_decl?(TypeName.new(namespace: namespace, name: name))
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
private
|
|
47
|
+
|
|
48
|
+
def mixin_decls(type_name)
|
|
49
|
+
type_name_absolute = type_name.absolute!
|
|
50
|
+
(@mixin_decls_cache ||= {}).fetch(type_name_absolute) do
|
|
51
|
+
@mixin_decls_cache[type_name_absolute] = @builder.env.class_decls[type_name_absolute].decls.flat_map do |d|
|
|
52
|
+
d.decl.members.select { |m| m.kind_of?(AST::Members::Mixin) }
|
|
53
|
+
end
|
|
54
|
+
end
|
|
55
|
+
end
|
|
56
|
+
end
|
|
57
|
+
private_constant :Todo
|
|
58
|
+
|
|
59
|
+
include Prototype::Helpers
|
|
60
|
+
include Runtime::Helpers
|
|
7
61
|
|
|
8
62
|
attr_reader :patterns
|
|
9
63
|
attr_reader :env
|
|
10
64
|
attr_reader :merge
|
|
65
|
+
attr_reader :todo
|
|
11
66
|
attr_reader :owners_included
|
|
12
67
|
attr_accessor :outline
|
|
13
68
|
|
|
14
|
-
def initialize(patterns:, env:, merge:, owners_included: [])
|
|
69
|
+
def initialize(patterns:, env:, merge:, todo: false, owners_included: [])
|
|
15
70
|
@patterns = patterns
|
|
16
71
|
@decls = nil
|
|
17
|
-
@modules =
|
|
72
|
+
@modules = {}
|
|
18
73
|
@env = env
|
|
19
74
|
@merge = merge
|
|
20
75
|
@owners_included = owners_included.map do |name|
|
|
21
76
|
Object.const_get(name)
|
|
22
77
|
end
|
|
23
78
|
@outline = false
|
|
79
|
+
@todo = todo
|
|
24
80
|
end
|
|
25
81
|
|
|
26
82
|
def target?(const)
|
|
@@ -36,6 +92,10 @@ module RBS
|
|
|
36
92
|
end
|
|
37
93
|
end
|
|
38
94
|
|
|
95
|
+
def todo_object
|
|
96
|
+
@todo_object ||= Todo.new(builder: builder) if todo
|
|
97
|
+
end
|
|
98
|
+
|
|
39
99
|
def builder
|
|
40
100
|
@builder ||= DefinitionBuilder.new(env: env)
|
|
41
101
|
end
|
|
@@ -47,8 +107,11 @@ module RBS
|
|
|
47
107
|
def decls
|
|
48
108
|
unless @decls
|
|
49
109
|
@decls = []
|
|
50
|
-
@modules = ObjectSpace.each_object(Module)
|
|
51
|
-
|
|
110
|
+
@modules = ObjectSpace.each_object(Module)
|
|
111
|
+
.map { |mod| [const_name(mod), mod] }
|
|
112
|
+
.select { |name, _| name }
|
|
113
|
+
.to_h
|
|
114
|
+
@modules.select { |name, mod| target?(mod) }.sort_by { |name, _| name }.each do |_, mod|
|
|
52
115
|
case mod
|
|
53
116
|
when Class
|
|
54
117
|
generate_class mod
|
|
@@ -58,48 +121,46 @@ module RBS
|
|
|
58
121
|
end
|
|
59
122
|
end
|
|
60
123
|
|
|
61
|
-
@decls
|
|
124
|
+
@decls or raise
|
|
62
125
|
end
|
|
63
126
|
|
|
64
|
-
def
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
else
|
|
71
|
-
TypeName.new(name: last.to_sym, namespace: Namespace.parse(prefix.join("::")))
|
|
72
|
-
end
|
|
73
|
-
else
|
|
74
|
-
TypeName.new(name: last.to_sym, namespace: Namespace.empty)
|
|
127
|
+
private def each_mixined_module(type_name, mod)
|
|
128
|
+
each_mixined_module_one(type_name, mod) do |module_name, module_full_name, is_prepend|
|
|
129
|
+
yield module_name, module_full_name, is_prepend ? AST::Members::Prepend : AST::Members::Include
|
|
130
|
+
end
|
|
131
|
+
each_mixined_module_one(type_name, mod.singleton_class) do |module_name, module_full_name, _|
|
|
132
|
+
yield module_name, module_full_name, AST::Members::Extend
|
|
75
133
|
end
|
|
76
134
|
end
|
|
77
135
|
|
|
78
|
-
def
|
|
79
|
-
supers = Set[]
|
|
136
|
+
private def each_mixined_module_one(type_name, mod)
|
|
137
|
+
supers = Set[] #: Set[Module]
|
|
138
|
+
prepends = mod.ancestors.take_while { |m| !mod.equal?(m) }.to_set
|
|
80
139
|
|
|
81
140
|
mod.included_modules.each do |mix|
|
|
82
141
|
supers.merge(mix.included_modules)
|
|
83
142
|
end
|
|
84
143
|
|
|
85
|
-
if mod.is_a?(Class)
|
|
86
|
-
mod.superclass
|
|
87
|
-
|
|
88
|
-
|
|
144
|
+
if mod.is_a?(Class)
|
|
145
|
+
if superclass = mod.superclass
|
|
146
|
+
superclass.included_modules.each do |mix|
|
|
147
|
+
supers << mix
|
|
148
|
+
supers.merge(mix.included_modules)
|
|
149
|
+
end
|
|
89
150
|
end
|
|
90
151
|
end
|
|
91
152
|
|
|
92
|
-
mod.included_modules.each do |mix|
|
|
93
|
-
|
|
153
|
+
mod.included_modules.uniq.each do |mix|
|
|
154
|
+
if !supers.include?(mix) || prepends.include?(mix)
|
|
94
155
|
unless const_name(mix)
|
|
95
156
|
RBS.logger.warn("Skipping anonymous module #{mix} included in #{mod}")
|
|
96
157
|
else
|
|
97
|
-
module_name = module_full_name = to_type_name(const_name(mix), full_name: true)
|
|
158
|
+
module_name = module_full_name = to_type_name(const_name!(mix), full_name: true)
|
|
98
159
|
if module_full_name.namespace == type_name.namespace
|
|
99
160
|
module_name = TypeName.new(name: module_full_name.name, namespace: Namespace.empty)
|
|
100
161
|
end
|
|
101
162
|
|
|
102
|
-
yield module_name, module_full_name, mix
|
|
163
|
+
yield module_name, module_full_name, prepends.include?(mix)
|
|
103
164
|
end
|
|
104
165
|
end
|
|
105
166
|
end
|
|
@@ -108,19 +169,19 @@ module RBS
|
|
|
108
169
|
def method_type(method)
|
|
109
170
|
untyped = Types::Bases::Any.new(location: nil)
|
|
110
171
|
|
|
111
|
-
required_positionals = []
|
|
112
|
-
optional_positionals = []
|
|
113
|
-
rest = nil
|
|
114
|
-
trailing_positionals = []
|
|
115
|
-
required_keywords = {}
|
|
116
|
-
optional_keywords = {}
|
|
117
|
-
rest_keywords = nil
|
|
172
|
+
required_positionals = [] #: Array[Types::Function::Param]
|
|
173
|
+
optional_positionals = [] #: Array[Types::Function::Param]
|
|
174
|
+
rest = nil #: Types::Function::Param?
|
|
175
|
+
trailing_positionals = [] #: Array[Types::Function::Param]
|
|
176
|
+
required_keywords = {} #: Hash[Symbol, Types::Function::Param]
|
|
177
|
+
optional_keywords = {} #: Hash[Symbol, Types::Function::Param]
|
|
178
|
+
rest_keywords = nil #: Types::Function::Param?
|
|
118
179
|
|
|
119
180
|
requireds = required_positionals
|
|
120
181
|
|
|
121
|
-
block = nil
|
|
182
|
+
block = nil #: Types::Block?
|
|
122
183
|
|
|
123
|
-
method.parameters.each do |kind, name|
|
|
184
|
+
method.parameters.each do |(kind, name)|
|
|
124
185
|
case kind
|
|
125
186
|
when :req
|
|
126
187
|
requireds << Types::Function::Param.new(name: name, type: untyped)
|
|
@@ -132,8 +193,10 @@ module RBS
|
|
|
132
193
|
name = nil if name == :* # For `def f(...) end` syntax
|
|
133
194
|
rest = Types::Function::Param.new(name: name, type: untyped)
|
|
134
195
|
when :keyreq
|
|
196
|
+
name or raise
|
|
135
197
|
required_keywords[name] = Types::Function::Param.new(name: nil, type: untyped)
|
|
136
198
|
when :key
|
|
199
|
+
name or raise
|
|
137
200
|
optional_keywords[name] = Types::Function::Param.new(name: nil, type: untyped)
|
|
138
201
|
when :keyrest
|
|
139
202
|
rest_keywords = Types::Function::Param.new(name: nil, type: untyped)
|
|
@@ -175,6 +238,7 @@ module RBS
|
|
|
175
238
|
def merge_rbs(module_name, members, instance: nil, singleton: nil)
|
|
176
239
|
if merge
|
|
177
240
|
if env.class_decls[module_name.absolute!]
|
|
241
|
+
# @type var kind: AST::Members::MethodDefinition::kind
|
|
178
242
|
case
|
|
179
243
|
when instance
|
|
180
244
|
method = builder.build_instance(module_name.absolute!).methods[instance]
|
|
@@ -194,6 +258,7 @@ module RBS
|
|
|
194
258
|
annotations: [],
|
|
195
259
|
method_type: type.update.tap do |ty|
|
|
196
260
|
def ty.to_s
|
|
261
|
+
location or raise
|
|
197
262
|
location.source
|
|
198
263
|
end
|
|
199
264
|
end
|
|
@@ -224,14 +289,27 @@ module RBS
|
|
|
224
289
|
when singleton
|
|
225
290
|
method = mod.singleton_class.instance_method(singleton)
|
|
226
291
|
method.owner == mod.singleton_class || owners_included.any? {|m| method.owner == m.singleton_class }
|
|
292
|
+
else
|
|
293
|
+
raise
|
|
227
294
|
end
|
|
228
295
|
end
|
|
229
296
|
|
|
230
297
|
def generate_methods(mod, module_name, members)
|
|
298
|
+
module_name_absolute = to_type_name(const_name!(mod), full_name: true).absolute!
|
|
231
299
|
mod.singleton_methods.select {|name| target_method?(mod, singleton: name) }.sort.each do |name|
|
|
232
300
|
method = mod.singleton_class.instance_method(name)
|
|
301
|
+
next if todo_object&.skip_singleton_method?(module_name: module_name_absolute, method: method, accessibility: :public)
|
|
233
302
|
|
|
234
|
-
if
|
|
303
|
+
if can_alias?(mod.singleton_class, method)
|
|
304
|
+
members << AST::Members::Alias.new(
|
|
305
|
+
new_name: method.name,
|
|
306
|
+
old_name: method.original_name,
|
|
307
|
+
kind: :singleton,
|
|
308
|
+
location: nil,
|
|
309
|
+
comment: nil,
|
|
310
|
+
annotations: [],
|
|
311
|
+
)
|
|
312
|
+
else
|
|
235
313
|
merge_rbs(module_name, members, singleton: name) do
|
|
236
314
|
RBS.logger.info "missing #{module_name}.#{name} #{method.source_location}"
|
|
237
315
|
|
|
@@ -248,15 +326,6 @@ module RBS
|
|
|
248
326
|
visibility: nil
|
|
249
327
|
)
|
|
250
328
|
end
|
|
251
|
-
else
|
|
252
|
-
members << AST::Members::Alias.new(
|
|
253
|
-
new_name: method.name,
|
|
254
|
-
old_name: method.original_name,
|
|
255
|
-
kind: :singleton,
|
|
256
|
-
location: nil,
|
|
257
|
-
comment: nil,
|
|
258
|
-
annotations: [],
|
|
259
|
-
)
|
|
260
329
|
end
|
|
261
330
|
end
|
|
262
331
|
|
|
@@ -266,8 +335,18 @@ module RBS
|
|
|
266
335
|
|
|
267
336
|
public_instance_methods.sort.each do |name|
|
|
268
337
|
method = mod.instance_method(name)
|
|
338
|
+
next if todo_object&.skip_instance_method?(module_name: module_name_absolute, method: method, accessibility: :public)
|
|
269
339
|
|
|
270
|
-
if
|
|
340
|
+
if can_alias?(mod, method)
|
|
341
|
+
members << AST::Members::Alias.new(
|
|
342
|
+
new_name: method.name,
|
|
343
|
+
old_name: method.original_name,
|
|
344
|
+
kind: :instance,
|
|
345
|
+
location: nil,
|
|
346
|
+
comment: nil,
|
|
347
|
+
annotations: [],
|
|
348
|
+
)
|
|
349
|
+
else
|
|
271
350
|
merge_rbs(module_name, members, instance: name) do
|
|
272
351
|
RBS.logger.info "missing #{module_name}##{name} #{method.source_location}"
|
|
273
352
|
|
|
@@ -284,27 +363,30 @@ module RBS
|
|
|
284
363
|
visibility: nil
|
|
285
364
|
)
|
|
286
365
|
end
|
|
287
|
-
else
|
|
288
|
-
members << AST::Members::Alias.new(
|
|
289
|
-
new_name: method.name,
|
|
290
|
-
old_name: method.original_name,
|
|
291
|
-
kind: :instance,
|
|
292
|
-
location: nil,
|
|
293
|
-
comment: nil,
|
|
294
|
-
annotations: [],
|
|
295
|
-
)
|
|
296
366
|
end
|
|
297
367
|
end
|
|
298
368
|
end
|
|
299
369
|
|
|
300
370
|
private_instance_methods = mod.private_instance_methods.select {|name| target_method?(mod, instance: name) }
|
|
301
371
|
unless private_instance_methods.empty?
|
|
372
|
+
added = false
|
|
302
373
|
members << AST::Members::Private.new(location: nil)
|
|
303
374
|
|
|
304
375
|
private_instance_methods.sort.each do |name|
|
|
305
376
|
method = mod.instance_method(name)
|
|
377
|
+
next if todo_object&.skip_instance_method?(module_name: module_name_absolute, method: method, accessibility: :private)
|
|
306
378
|
|
|
307
|
-
|
|
379
|
+
added = true
|
|
380
|
+
if can_alias?(mod, method)
|
|
381
|
+
members << AST::Members::Alias.new(
|
|
382
|
+
new_name: method.name,
|
|
383
|
+
old_name: method.original_name,
|
|
384
|
+
kind: :instance,
|
|
385
|
+
location: nil,
|
|
386
|
+
comment: nil,
|
|
387
|
+
annotations: [],
|
|
388
|
+
)
|
|
389
|
+
else
|
|
308
390
|
merge_rbs(module_name, members, instance: name) do
|
|
309
391
|
RBS.logger.info "missing #{module_name}##{name} #{method.source_location}"
|
|
310
392
|
|
|
@@ -321,22 +403,28 @@ module RBS
|
|
|
321
403
|
visibility: nil
|
|
322
404
|
)
|
|
323
405
|
end
|
|
324
|
-
else
|
|
325
|
-
members << AST::Members::Alias.new(
|
|
326
|
-
new_name: method.name,
|
|
327
|
-
old_name: method.original_name,
|
|
328
|
-
kind: :instance,
|
|
329
|
-
location: nil,
|
|
330
|
-
comment: nil,
|
|
331
|
-
annotations: [],
|
|
332
|
-
)
|
|
333
406
|
end
|
|
334
407
|
end
|
|
408
|
+
|
|
409
|
+
members.pop unless added
|
|
410
|
+
end
|
|
411
|
+
end
|
|
412
|
+
|
|
413
|
+
private def can_alias?(mod, method)
|
|
414
|
+
return false if method.name == method.original_name
|
|
415
|
+
|
|
416
|
+
begin
|
|
417
|
+
mod.instance_method(method.original_name) && true
|
|
418
|
+
rescue NameError
|
|
419
|
+
false
|
|
335
420
|
end
|
|
336
421
|
end
|
|
337
422
|
|
|
338
423
|
def generate_constants(mod, decls)
|
|
424
|
+
module_name = const_name!(mod)
|
|
339
425
|
mod.constants(false).sort.each do |name|
|
|
426
|
+
next if todo_object&.skip_constant?(module_name: module_name, name: name)
|
|
427
|
+
|
|
340
428
|
begin
|
|
341
429
|
value = mod.const_get(name)
|
|
342
430
|
rescue StandardError, LoadError => e
|
|
@@ -344,8 +432,10 @@ module RBS
|
|
|
344
432
|
next
|
|
345
433
|
end
|
|
346
434
|
|
|
347
|
-
next if value.
|
|
348
|
-
|
|
435
|
+
next if object_class(value).equal?(Class)
|
|
436
|
+
next if object_class(value).equal?(Module)
|
|
437
|
+
|
|
438
|
+
unless object_class(value).name
|
|
349
439
|
RBS.logger.warn("Skipping constant #{name} #{value} of #{mod} as an instance of anonymous class")
|
|
350
440
|
next
|
|
351
441
|
end
|
|
@@ -358,8 +448,12 @@ module RBS
|
|
|
358
448
|
type: Types::Bases::Any.new(location: nil),
|
|
359
449
|
location: nil
|
|
360
450
|
)
|
|
451
|
+
when ARGF
|
|
452
|
+
Types::ClassInstance.new(name: TypeName("::RBS::Unnamed::ARGFClass"), args: [], location: nil)
|
|
453
|
+
when ENV
|
|
454
|
+
Types::ClassInstance.new(name: TypeName("::RBS::Unnamed::ENVClass"), args: [], location: nil)
|
|
361
455
|
else
|
|
362
|
-
value_type_name = to_type_name(const_name(value
|
|
456
|
+
value_type_name = to_type_name(const_name!(object_class(value)), full_name: true).absolute!
|
|
363
457
|
args = type_args(value_type_name)
|
|
364
458
|
Types::ClassInstance.new(name: value_type_name, args: args, location: nil)
|
|
365
459
|
end
|
|
@@ -374,62 +468,56 @@ module RBS
|
|
|
374
468
|
end
|
|
375
469
|
|
|
376
470
|
def generate_super_class(mod)
|
|
377
|
-
|
|
471
|
+
superclass = mod.superclass
|
|
472
|
+
|
|
473
|
+
if superclass.nil? || superclass == ::Object
|
|
378
474
|
nil
|
|
379
|
-
elsif const_name(
|
|
380
|
-
RBS.logger.warn("Skipping anonymous superclass #{
|
|
475
|
+
elsif const_name(superclass).nil?
|
|
476
|
+
RBS.logger.warn("Skipping anonymous superclass #{superclass} of #{mod}")
|
|
381
477
|
nil
|
|
382
478
|
else
|
|
383
|
-
super_name = to_type_name(const_name(
|
|
479
|
+
super_name = to_type_name(const_name!(superclass), full_name: true).absolute!
|
|
384
480
|
super_args = type_args(super_name)
|
|
385
481
|
AST::Declarations::Class::Super.new(name: super_name, args: super_args, location: nil)
|
|
386
482
|
end
|
|
387
483
|
end
|
|
388
484
|
|
|
389
485
|
def generate_class(mod)
|
|
390
|
-
|
|
486
|
+
type_name_absolute = to_type_name(const_name!(mod), full_name: true).absolute!
|
|
487
|
+
type_name = to_type_name(const_name!(mod))
|
|
391
488
|
outer_decls = ensure_outer_module_declarations(mod)
|
|
392
489
|
|
|
393
490
|
# Check if a declaration exists for the actual module
|
|
394
|
-
decl = outer_decls.detect
|
|
491
|
+
decl = outer_decls.detect do |decl|
|
|
492
|
+
decl.is_a?(AST::Declarations::Class) && decl.name.name == only_name(mod).to_sym
|
|
493
|
+
end #: AST::Declarations::Class?
|
|
494
|
+
|
|
395
495
|
unless decl
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
496
|
+
if mod < Struct
|
|
497
|
+
decl = StructGenerator.new(mod).build_decl
|
|
498
|
+
elsif RUBY_VERSION >= '3.2' && mod < Data
|
|
499
|
+
decl = DataGenerator.new(mod).build_decl
|
|
500
|
+
else
|
|
501
|
+
decl = AST::Declarations::Class.new(
|
|
502
|
+
name: to_type_name(only_name(mod)),
|
|
503
|
+
type_params: type_params(mod),
|
|
504
|
+
super_class: generate_super_class(mod),
|
|
505
|
+
members: [],
|
|
506
|
+
annotations: [],
|
|
507
|
+
location: nil,
|
|
508
|
+
comment: nil
|
|
509
|
+
)
|
|
510
|
+
end
|
|
405
511
|
|
|
406
512
|
outer_decls << decl
|
|
407
513
|
end
|
|
408
514
|
|
|
409
|
-
|
|
410
|
-
args = type_args(module_full_name)
|
|
411
|
-
decl.members << AST::Members::Include.new(
|
|
412
|
-
name: module_name,
|
|
413
|
-
args: args,
|
|
414
|
-
location: nil,
|
|
415
|
-
comment: nil,
|
|
416
|
-
annotations: []
|
|
417
|
-
)
|
|
418
|
-
end
|
|
515
|
+
generate_mixin(mod, decl, type_name, type_name_absolute)
|
|
419
516
|
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
decl.members << AST::Members::Extend.new(
|
|
423
|
-
name: module_name,
|
|
424
|
-
args: args,
|
|
425
|
-
location: nil,
|
|
426
|
-
comment: nil,
|
|
427
|
-
annotations: []
|
|
428
|
-
)
|
|
517
|
+
unless mod < Struct || (RUBY_VERSION >= '3.2' && mod < Data)
|
|
518
|
+
generate_methods(mod, type_name, decl.members) unless outline
|
|
429
519
|
end
|
|
430
520
|
|
|
431
|
-
generate_methods(mod, type_name, decl.members) unless outline
|
|
432
|
-
|
|
433
521
|
generate_constants mod, decl.members
|
|
434
522
|
end
|
|
435
523
|
|
|
@@ -441,11 +529,15 @@ module RBS
|
|
|
441
529
|
return
|
|
442
530
|
end
|
|
443
531
|
|
|
532
|
+
type_name_absolute = to_type_name(name, full_name: true).absolute!
|
|
444
533
|
type_name = to_type_name(name)
|
|
445
534
|
outer_decls = ensure_outer_module_declarations(mod)
|
|
446
535
|
|
|
447
536
|
# Check if a declaration exists for the actual class
|
|
448
|
-
decl = outer_decls.detect
|
|
537
|
+
decl = outer_decls.detect do |decl|
|
|
538
|
+
decl.is_a?(AST::Declarations::Module) && decl.name.name == only_name(mod).to_sym
|
|
539
|
+
end #: AST::Declarations::Module?
|
|
540
|
+
|
|
449
541
|
unless decl
|
|
450
542
|
decl = AST::Declarations::Module.new(
|
|
451
543
|
name: to_type_name(only_name(mod)),
|
|
@@ -460,20 +552,19 @@ module RBS
|
|
|
460
552
|
outer_decls << decl
|
|
461
553
|
end
|
|
462
554
|
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
466
|
-
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
|
|
472
|
-
|
|
555
|
+
generate_mixin(mod, decl, type_name, type_name_absolute)
|
|
556
|
+
|
|
557
|
+
generate_methods(mod, type_name, decl.members) unless outline
|
|
558
|
+
|
|
559
|
+
generate_constants mod, decl.members
|
|
560
|
+
end
|
|
561
|
+
|
|
562
|
+
def generate_mixin(mod, decl, type_name, type_name_absolute)
|
|
563
|
+
each_mixined_module(type_name, mod) do |module_name, module_full_name, mixin_class|
|
|
564
|
+
next if todo_object&.skip_mixin?(type_name: type_name_absolute, module_name: module_full_name, mixin_class: mixin_class)
|
|
473
565
|
|
|
474
|
-
each_included_module(type_name, mod.singleton_class) do |module_name, module_full_name, _|
|
|
475
566
|
args = type_args(module_full_name)
|
|
476
|
-
decl.members <<
|
|
567
|
+
decl.members << mixin_class.new(
|
|
477
568
|
name: module_name,
|
|
478
569
|
args: args,
|
|
479
570
|
location: nil,
|
|
@@ -481,26 +572,33 @@ module RBS
|
|
|
481
572
|
annotations: []
|
|
482
573
|
)
|
|
483
574
|
end
|
|
484
|
-
|
|
485
|
-
generate_methods(mod, type_name, decl.members) unless outline
|
|
486
|
-
|
|
487
|
-
generate_constants mod, decl.members
|
|
488
575
|
end
|
|
489
576
|
|
|
490
577
|
# Generate/find outer module declarations
|
|
491
578
|
# This is broken down into another method to comply with `DRY`
|
|
492
579
|
# This generates/finds declarations in nested form & returns the last array of declarations
|
|
493
580
|
def ensure_outer_module_declarations(mod)
|
|
494
|
-
|
|
495
|
-
|
|
581
|
+
# @type var outer_module_names: Array[String]
|
|
582
|
+
*outer_module_names, _ = const_name!(mod).split(/::/) #=> parent = [A, B], mod = C
|
|
583
|
+
# Copy the entries in ivar @decls, not .dup
|
|
584
|
+
destination = @decls || [] #: Array[AST::Declarations::Class::member]
|
|
496
585
|
|
|
497
586
|
outer_module_names&.each_with_index do |outer_module_name, i|
|
|
498
|
-
current_name = outer_module_names
|
|
499
|
-
outer_module = @modules
|
|
500
|
-
outer_decl = destination.detect
|
|
587
|
+
current_name = outer_module_names.take(i+1).join('::')
|
|
588
|
+
outer_module = @modules[current_name]
|
|
589
|
+
outer_decl = destination.detect do |decl|
|
|
590
|
+
case outer_module
|
|
591
|
+
when Class
|
|
592
|
+
decl.is_a?(AST::Declarations::Class) && decl.name.name == outer_module_name.to_sym
|
|
593
|
+
when Module
|
|
594
|
+
decl.is_a?(AST::Declarations::Module) && decl.name.name == outer_module_name.to_sym
|
|
595
|
+
end
|
|
596
|
+
end #: AST::Declarations::Class | AST::Declarations::Module | nil
|
|
501
597
|
|
|
502
598
|
# Insert AST::Declarations if declarations are not added previously
|
|
503
599
|
unless outer_decl
|
|
600
|
+
outer_module or raise
|
|
601
|
+
|
|
504
602
|
if outer_module.is_a?(Class)
|
|
505
603
|
outer_decl = AST::Declarations::Class.new(
|
|
506
604
|
name: to_type_name(outer_module_name),
|
|
@@ -533,37 +631,21 @@ module RBS
|
|
|
533
631
|
destination
|
|
534
632
|
end
|
|
535
633
|
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
const_name(mod).split(/::/).last # (A::B::C) => C
|
|
540
|
-
end
|
|
541
|
-
|
|
542
|
-
def const_name(const)
|
|
543
|
-
@module_name_method ||= Module.instance_method(:name)
|
|
544
|
-
name = @module_name_method.bind(const).call
|
|
545
|
-
return nil unless name
|
|
546
|
-
|
|
547
|
-
begin
|
|
548
|
-
Object.const_get(name)
|
|
549
|
-
rescue NameError
|
|
550
|
-
# Should generate const name if anonymous or internal module (e.g. NameError::message)
|
|
551
|
-
nil
|
|
552
|
-
else
|
|
553
|
-
name
|
|
554
|
-
end
|
|
634
|
+
def object_class(value)
|
|
635
|
+
@object_class ||= Object.instance_method(:class)
|
|
636
|
+
@object_class.bind_call(value)
|
|
555
637
|
end
|
|
556
638
|
|
|
557
639
|
def type_args(type_name)
|
|
558
|
-
if class_decl = env.class_decls
|
|
559
|
-
class_decl.type_params.size.times.map { :
|
|
640
|
+
if class_decl = env.class_decls.fetch(type_name.absolute!, nil)
|
|
641
|
+
class_decl.type_params.size.times.map { Types::Bases::Any.new(location: nil) }
|
|
560
642
|
else
|
|
561
643
|
[]
|
|
562
644
|
end
|
|
563
645
|
end
|
|
564
646
|
|
|
565
647
|
def type_params(mod)
|
|
566
|
-
type_name = to_type_name(const_name(mod), full_name: true)
|
|
648
|
+
type_name = to_type_name(const_name!(mod), full_name: true)
|
|
567
649
|
if class_decl = env.class_decls[type_name.absolute!]
|
|
568
650
|
class_decl.type_params
|
|
569
651
|
else
|
|
@@ -580,7 +662,9 @@ module RBS
|
|
|
580
662
|
return # When the method is defined in eval
|
|
581
663
|
end
|
|
582
664
|
|
|
583
|
-
|
|
665
|
+
if ast && ast.type == :SCOPE
|
|
666
|
+
block_from_body(ast)
|
|
667
|
+
end
|
|
584
668
|
end
|
|
585
669
|
end
|
|
586
670
|
end
|