rbs 0.3.1 → 0.8.0

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.
Files changed (82) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/ruby.yml +7 -1
  3. data/.gitignore +1 -1
  4. data/CHANGELOG.md +39 -0
  5. data/COPYING +1 -1
  6. data/Gemfile +16 -2
  7. data/README.md +87 -48
  8. data/Rakefile +54 -22
  9. data/bin/rbs-prof +9 -0
  10. data/bin/run_in_md.rb +49 -0
  11. data/bin/test_runner.rb +0 -2
  12. data/docs/sigs.md +6 -6
  13. data/docs/stdlib.md +3 -5
  14. data/docs/syntax.md +6 -3
  15. data/goodcheck.yml +65 -0
  16. data/lib/rbs.rb +3 -0
  17. data/lib/rbs/ast/declarations.rb +115 -14
  18. data/lib/rbs/ast/members.rb +41 -17
  19. data/lib/rbs/cli.rb +315 -122
  20. data/lib/rbs/constant.rb +4 -4
  21. data/lib/rbs/constant_table.rb +51 -45
  22. data/lib/rbs/definition.rb +175 -59
  23. data/lib/rbs/definition_builder.rb +802 -604
  24. data/lib/rbs/environment.rb +352 -210
  25. data/lib/rbs/environment_walker.rb +14 -23
  26. data/lib/rbs/errors.rb +184 -3
  27. data/lib/rbs/factory.rb +14 -0
  28. data/lib/rbs/parser.y +95 -27
  29. data/lib/rbs/prototype/rb.rb +119 -117
  30. data/lib/rbs/prototype/rbi.rb +5 -3
  31. data/lib/rbs/prototype/runtime.rb +34 -7
  32. data/lib/rbs/substitution.rb +12 -1
  33. data/lib/rbs/test.rb +82 -3
  34. data/lib/rbs/test/errors.rb +5 -1
  35. data/lib/rbs/test/hook.rb +133 -259
  36. data/lib/rbs/test/observer.rb +17 -0
  37. data/lib/rbs/test/setup.rb +35 -19
  38. data/lib/rbs/test/setup_helper.rb +29 -0
  39. data/lib/rbs/test/spy.rb +0 -321
  40. data/lib/rbs/test/tester.rb +116 -0
  41. data/lib/rbs/test/type_check.rb +43 -7
  42. data/lib/rbs/type_name_resolver.rb +58 -0
  43. data/lib/rbs/types.rb +94 -2
  44. data/lib/rbs/validator.rb +51 -0
  45. data/lib/rbs/variance_calculator.rb +12 -2
  46. data/lib/rbs/version.rb +1 -1
  47. data/lib/rbs/writer.rb +127 -91
  48. data/rbs.gemspec +0 -9
  49. data/schema/annotation.json +14 -0
  50. data/schema/comment.json +26 -0
  51. data/schema/decls.json +353 -0
  52. data/schema/function.json +87 -0
  53. data/schema/location.json +56 -0
  54. data/schema/members.json +248 -0
  55. data/schema/methodType.json +44 -0
  56. data/schema/types.json +299 -0
  57. data/stdlib/benchmark/benchmark.rbs +151 -151
  58. data/stdlib/builtin/encoding.rbs +2 -0
  59. data/stdlib/builtin/enumerable.rbs +4 -4
  60. data/stdlib/builtin/enumerator.rbs +3 -1
  61. data/stdlib/builtin/fiber.rbs +5 -1
  62. data/stdlib/builtin/file.rbs +0 -3
  63. data/stdlib/builtin/io.rbs +4 -4
  64. data/stdlib/builtin/proc.rbs +1 -2
  65. data/stdlib/builtin/symbol.rbs +1 -1
  66. data/stdlib/builtin/thread.rbs +2 -2
  67. data/stdlib/csv/csv.rbs +4 -6
  68. data/stdlib/fiber/fiber.rbs +117 -0
  69. data/stdlib/json/json.rbs +1 -1
  70. data/stdlib/logger/formatter.rbs +23 -0
  71. data/stdlib/logger/log_device.rbs +39 -0
  72. data/stdlib/logger/logger.rbs +507 -0
  73. data/stdlib/logger/period.rbs +7 -0
  74. data/stdlib/logger/severity.rbs +8 -0
  75. data/stdlib/mutex_m/mutex_m.rbs +77 -0
  76. data/stdlib/pathname/pathname.rbs +6 -6
  77. data/stdlib/prime/integer-extension.rbs +1 -1
  78. data/stdlib/prime/prime.rbs +44 -44
  79. data/stdlib/pty/pty.rbs +159 -0
  80. data/stdlib/tmpdir/tmpdir.rbs +1 -1
  81. metadata +28 -116
  82. data/lib/rbs/test/test_helper.rb +0 -183
@@ -1,188 +1,375 @@
1
1
  module RBS
2
2
  class DefinitionBuilder
3
3
  attr_reader :env
4
+ attr_reader :type_name_resolver
5
+
4
6
  attr_reader :instance_cache
5
7
  attr_reader :singleton_cache
8
+ attr_reader :interface_cache
9
+
10
+ attr_reader :one_instance_cache
11
+ attr_reader :one_singleton_cache
12
+
13
+ attr_reader :instance_ancestors_cache
14
+ attr_reader :singleton_ancestor_cache
15
+
16
+ attr_reader :one_instance_ancestors_cache
17
+ attr_reader :one_singleton_ancestors_cache
18
+
19
+ class OneAncestors
20
+ attr_reader :type_name
21
+ attr_reader :params
22
+ attr_reader :super_class
23
+ attr_reader :self_types
24
+ attr_reader :included_modules
25
+ attr_reader :prepended_modules
26
+ attr_reader :extended_modules
27
+
28
+ def initialize(type_name:, params:, super_class:, self_types:, included_modules:, prepended_modules:, extended_modules:)
29
+ @type_name = type_name
30
+ @params = params
31
+ @super_class = super_class
32
+ @self_types = self_types
33
+ @included_modules = included_modules
34
+ @prepended_modules = prepended_modules
35
+ @extended_modules = extended_modules
36
+ end
37
+
38
+ def each_ancestor(&block)
39
+ if block_given?
40
+ yield super_class if super_class
41
+ self_types&.each(&block)
42
+ included_modules&.each(&block)
43
+ prepended_modules&.each(&block)
44
+ extended_modules&.each(&block)
45
+ else
46
+ enum_for :each_ancestor
47
+ end
48
+ end
49
+
50
+ def self.class_instance(type_name:, params:, super_class:)
51
+ new(
52
+ type_name: type_name,
53
+ params: params,
54
+ super_class: super_class,
55
+ self_types: nil,
56
+ included_modules: [],
57
+ prepended_modules: [],
58
+ extended_modules: nil
59
+ )
60
+ end
61
+
62
+ def self.singleton(type_name:, super_class:)
63
+ new(
64
+ type_name: type_name,
65
+ params: nil,
66
+ super_class: super_class,
67
+ self_types: nil,
68
+ included_modules: nil,
69
+ prepended_modules: nil,
70
+ extended_modules: []
71
+ )
72
+ end
73
+
74
+ def self.module_instance(type_name:, params:)
75
+ new(
76
+ type_name: type_name,
77
+ params: params,
78
+ self_types: [],
79
+ included_modules: [],
80
+ prepended_modules: [],
81
+ super_class: nil,
82
+ extended_modules: nil
83
+ )
84
+ end
85
+ end
6
86
 
7
87
  def initialize(env:)
8
88
  @env = env
89
+ @type_name_resolver = TypeNameResolver.from_env(env)
90
+
9
91
  @instance_cache = {}
10
92
  @singleton_cache = {}
93
+ @interface_cache = {}
94
+
95
+ @one_instance_cache = {}
96
+ @one_singleton_cache = {}
97
+
98
+ @instance_ancestors_cache = {}
99
+ @singleton_ancestor_cache = {}
100
+
101
+ @one_instance_ancestors_cache = {}
102
+ @one_singleton_ancestors_cache = {}
11
103
  end
12
104
 
13
- def build_ancestors(self_ancestor, ancestors: [], building_ancestors: [], location: nil)
14
- decl = env.find_class(self_ancestor.name)
15
- namespace = self_ancestor.name.absolute!.to_namespace
105
+ def validate_super_class!(type_name, entry)
106
+ with_super_classes = entry.decls.select {|d| d.decl.super_class }
16
107
 
17
- RecursiveAncestorError.check!(self_ancestor,
18
- ancestors: building_ancestors,
19
- location: location || decl.location)
20
- building_ancestors.push self_ancestor
108
+ return if with_super_classes.size <= 1
21
109
 
22
- case self_ancestor
23
- when Definition::Ancestor::Instance
24
- args = self_ancestor.args
25
- param_names = decl.type_params.each.map(&:name)
26
-
27
- InvalidTypeApplicationError.check!(
28
- type_name: self_ancestor.name,
29
- args: args,
30
- params: decl.type_params,
31
- location: location || decl.location
32
- )
110
+ super_types = with_super_classes.map do |d|
111
+ super_class = d.decl.super_class
112
+ Types::ClassInstance.new(name: super_class.name, args: super_class.args, location: nil)
113
+ end
33
114
 
34
- sub = Substitution.build(param_names, args)
115
+ super_types.uniq!
35
116
 
36
- case decl
37
- when AST::Declarations::Class
38
- unless self_ancestor.name == BuiltinNames::BasicObject.name
39
- super_ancestor = decl.super_class&.yield_self do |super_class|
40
- Definition::Ancestor::Instance.new(
41
- name: absolute_type_name(super_class.name, namespace: namespace, location: location || decl.location),
42
- args: super_class.args.map {|ty| absolute_type(ty.sub(sub), namespace: namespace) }
43
- )
44
- end || Definition::Ancestor::Instance.new(name: BuiltinNames::Object.name, args: [])
117
+ return if super_types.size == 1
118
+
119
+ raise SuperclassMismatchError.new(name: type_name, super_classes: super_types, entry: entry)
120
+ end
121
+
122
+ def one_instance_ancestors(type_name)
123
+ as = one_instance_ancestors_cache[type_name] and return as
45
124
 
46
- build_ancestors(super_ancestor, ancestors: ancestors, building_ancestors: building_ancestors)
125
+ entry = env.class_decls[type_name] or raise "Unknown name for one_instance_ancestors: #{type_name}"
126
+ params = entry.type_params.each.map(&:name)
127
+
128
+ case entry
129
+ when Environment::ClassEntry
130
+ validate_super_class!(type_name, entry)
131
+ primary = entry.primary
132
+ super_class = primary.decl.super_class
133
+
134
+ if type_name != BuiltinNames::BasicObject.name
135
+ if super_class
136
+ super_name = super_class.name
137
+ super_args = super_class.args
138
+ else
139
+ super_name = BuiltinNames::Object.name
140
+ super_args = []
47
141
  end
142
+
143
+ NoSuperclassFoundError.check!(super_name, env: env, location: primary.decl.location)
144
+
145
+ ancestors = OneAncestors.class_instance(
146
+ type_name: type_name,
147
+ params: params,
148
+ super_class: Definition::Ancestor::Instance.new(name: super_name, args: super_args)
149
+ )
150
+ else
151
+ ancestors = OneAncestors.class_instance(
152
+ type_name: type_name,
153
+ params: params,
154
+ super_class: nil
155
+ )
48
156
  end
157
+ when Environment::ModuleEntry
158
+ ancestors = OneAncestors.module_instance(type_name: type_name, params: params)
49
159
 
50
- decl.members.each do |member|
51
- case member
52
- when AST::Members::Include
53
- if member.name.class?
54
- ancestor = Definition::Ancestor::Instance.new(
55
- name: absolute_type_name(member.name, namespace: namespace, location: member.location),
56
- args: member.args.map {|ty| absolute_type(ty.sub(sub), namespace: namespace) }
57
- )
58
- build_ancestors ancestor, ancestors: ancestors, building_ancestors: building_ancestors, location: member.location
59
- end
60
- end
160
+ entry.self_types.each do |module_self|
161
+ NoSelfTypeFoundError.check!(module_self, env: env)
162
+ ancestors.self_types.push Definition::Ancestor::Instance.new(name: module_self.name, args: module_self.args)
61
163
  end
164
+ else
165
+ raise "Unexpected entry for: #{type_name}"
166
+ end
62
167
 
63
- ancestors.unshift(self_ancestor)
168
+ mixin_ancestors(entry,
169
+ included_modules: ancestors.included_modules,
170
+ prepended_modules: ancestors.prepended_modules,
171
+ extended_modules: nil)
64
172
 
65
- env.each_extension(self_ancestor.name).sort_by {|e| e.extension_name.to_s }.each do |extension|
66
- InvalidExtensionParameterError.check!(
67
- type_name: self_ancestor.name,
68
- extension_name: extension.extension_name,
69
- extension_params: extension.type_params,
70
- class_params: self_ancestor.args.map(&:name),
71
- location: extension.location
72
- )
173
+ one_instance_ancestors_cache[type_name] = ancestors
174
+ end
73
175
 
74
- sub = Substitution.build(extension.type_params, self_ancestor.args)
176
+ def one_singleton_ancestors(type_name)
177
+ as = one_singleton_ancestors_cache[type_name] and return as
75
178
 
76
- extension.members.each do |member|
77
- case member
78
- when AST::Members::Include
79
- if member.name.class?
80
- ancestor = Definition::Ancestor::Instance.new(
81
- name: absolute_type_name(member.name, namespace: namespace, location: member.location),
82
- args: member.args.map {|ty| absolute_type(ty.sub(sub), namespace: namespace) }
83
- )
84
- build_ancestors ancestor, ancestors: ancestors, building_ancestors: building_ancestors, location: member.location
85
- end
86
- end
87
- end
179
+ entry = env.class_decls[type_name] or raise "Unknown name for one_singleton_ancestors: #{type_name}"
88
180
 
89
- extension_ancestor = Definition::Ancestor::ExtensionInstance.new(
90
- name: extension.name.absolute!,
91
- extension_name: extension.extension_name,
92
- args: self_ancestor.args,
93
- )
94
- ancestors.unshift(extension_ancestor)
181
+ case entry
182
+ when Environment::ClassEntry
183
+ validate_super_class!(type_name, entry)
184
+ primary = entry.primary
185
+ super_class = primary.decl.super_class
95
186
 
96
- extension.members.each do |member|
97
- case member
98
- when AST::Members::Prepend
99
- if member.name.class?
100
- ancestor = Definition::Ancestor::Instance.new(
101
- name: absolute_type_name(member.name, namespace: namespace, location: member.location),
102
- args: member.args.map {|ty| absolute_type(ty.sub(sub), namespace: namespace) }
103
- )
104
- build_ancestors ancestor, ancestors: ancestors, building_ancestors: building_ancestors, location: member.location
105
- end
106
- end
187
+ if type_name != BuiltinNames::BasicObject.name
188
+ if super_class
189
+ super_name = super_class.name
190
+ else
191
+ super_name = BuiltinNames::Object.name
107
192
  end
108
- end
109
193
 
110
- decl.members.each do |member|
111
- case member
112
- when AST::Members::Prepend
113
- ancestor = Definition::Ancestor::Instance.new(
114
- name: absolute_type_name(member.name, namespace: namespace, location: member.location),
115
- args: member.args.map {|ty| absolute_type(ty.sub(sub), namespace: namespace) }
116
- )
117
- build_ancestors ancestor, ancestors: ancestors, building_ancestors: building_ancestors, location: member.location
118
- end
119
- end
120
- when Definition::Ancestor::Singleton
121
- case decl
122
- when AST::Declarations::Class
123
- if self_ancestor.name == BuiltinNames::BasicObject.name
124
- class_ancestor = Definition::Ancestor::Instance.new(
125
- name: BuiltinNames::Class.name,
126
- args: []
127
- )
128
- build_ancestors class_ancestor, ancestors: ancestors, building_ancestors: building_ancestors
129
- else
130
- super_ancestor = decl.super_class&.yield_self do |super_class|
131
- Definition::Ancestor::Singleton.new(
132
- name: absolute_type_name(super_class.name, namespace: namespace, location: location || decl.location)
133
- )
134
- end || Definition::Ancestor::Singleton.new(name: BuiltinNames::Object.name)
194
+ NoSuperclassFoundError.check!(super_name, env: env, location: primary.decl.location)
135
195
 
136
- build_ancestors(super_ancestor, ancestors: ancestors, building_ancestors: building_ancestors)
137
- end
138
- when AST::Declarations::Module
139
- module_ancestor = Definition::Ancestor::Instance.new(
140
- name: BuiltinNames::Module.name,
141
- args: []
196
+ ancestors = OneAncestors.singleton(
197
+ type_name: type_name,
198
+ super_class: Definition::Ancestor::Singleton.new(name: super_name)
199
+ )
200
+ else
201
+ ancestors = OneAncestors.singleton(
202
+ type_name: type_name,
203
+ super_class: Definition::Ancestor::Instance.new(name: BuiltinNames::Class.name, args: [])
142
204
  )
143
- build_ancestors module_ancestor, ancestors: ancestors, building_ancestors: building_ancestors
144
205
  end
206
+ when Environment::ModuleEntry
207
+ ancestors = OneAncestors.singleton(
208
+ type_name: type_name,
209
+ super_class: Definition::Ancestor::Instance.new(name: BuiltinNames::Module.name, args: [])
210
+ )
211
+
212
+ else
213
+ raise "Unexpected entry for: #{type_name}"
214
+ end
215
+
216
+ mixin_ancestors(entry,
217
+ included_modules: nil,
218
+ prepended_modules: nil,
219
+ extended_modules: ancestors.extended_modules)
220
+
221
+ one_singleton_ancestors_cache[type_name] = ancestors
222
+ end
223
+
224
+ def mixin_ancestors(entry, included_modules:, extended_modules:, prepended_modules:)
225
+ entry.decls.each do |d|
226
+ decl = d.decl
227
+
228
+ align_params = Substitution.build(
229
+ decl.type_params.each.map(&:name),
230
+ Types::Variable.build(entry.type_params.each.map(&:name))
231
+ )
145
232
 
146
- decl.members.each do |member|
233
+ decl.each_mixin do |member|
147
234
  case member
235
+ when AST::Members::Include
236
+ if included_modules
237
+ NoMixinFoundError.check!(member.name, env: env, member: member)
238
+
239
+ module_name = member.name
240
+ module_args = member.args.map {|type| type.sub(align_params) }
241
+
242
+ included_modules << Definition::Ancestor::Instance.new(name: module_name, args: module_args)
243
+ end
244
+
245
+ when AST::Members::Prepend
246
+ if prepended_modules
247
+ NoMixinFoundError.check!(member.name, env: env, member: member)
248
+
249
+ module_name = member.name
250
+ module_args = member.args.map {|type| type.sub(align_params) }
251
+
252
+ prepended_modules << Definition::Ancestor::Instance.new(name: module_name, args: module_args)
253
+ end
254
+
148
255
  when AST::Members::Extend
149
- if member.name.class?
150
- ancestor = Definition::Ancestor::Instance.new(
151
- name: absolute_type_name(member.name, namespace: namespace, location: member.location),
152
- args: member.args.map {|ty| absolute_type(ty.sub(sub), namespace: namespace) }
153
- )
154
- build_ancestors ancestor, ancestors: ancestors, building_ancestors: building_ancestors, location: member.location
256
+ if extended_modules
257
+ NoMixinFoundError.check!(member.name, env: env, member: member)
258
+
259
+ module_name = member.name
260
+ module_args = member.args
261
+
262
+ extended_modules << Definition::Ancestor::Instance.new(name: module_name, args: module_args)
155
263
  end
156
264
  end
157
265
  end
266
+ end
267
+ end
268
+
269
+ def instance_ancestors(type_name, building_ancestors: [])
270
+ as = instance_ancestors_cache[type_name] and return as
271
+
272
+ entry = env.class_decls[type_name] or raise "Unknown name for instance_ancestors: #{type_name}"
273
+ params = entry.type_params.each.map(&:name)
274
+ args = Types::Variable.build(params)
275
+ self_ancestor = Definition::Ancestor::Instance.new(name: type_name, args: args)
276
+
277
+ RecursiveAncestorError.check!(self_ancestor,
278
+ ancestors: building_ancestors,
279
+ location: entry.primary.decl.location)
280
+ building_ancestors.push self_ancestor
281
+
282
+ one_ancestors = one_instance_ancestors(type_name)
283
+
284
+ ancestors = []
285
+
286
+ case entry
287
+ when Environment::ClassEntry
288
+ if one_ancestors.super_class
289
+ super_name = one_ancestors.super_class.name
290
+ super_args = one_ancestors.super_class.args
291
+
292
+ super_ancestors = instance_ancestors(super_name, building_ancestors: building_ancestors)
293
+ ancestors.unshift(*super_ancestors.apply(super_args, location: entry.primary.decl.location))
294
+ end
295
+ end
158
296
 
159
- ancestors.unshift(self_ancestor)
297
+ one_ancestors.included_modules.each do |mod|
298
+ if mod.name.class?
299
+ name = mod.name
300
+ args = mod.args
301
+ mod_ancestors = instance_ancestors(name, building_ancestors: building_ancestors)
302
+ ancestors.unshift(*mod_ancestors.apply(args, location: entry.primary.decl.location))
303
+ end
304
+ end
160
305
 
161
- env.each_extension(self_ancestor.name).sort_by {|e| e.extension_name.to_s }.each do |extension|
162
- extension.members.each do |member|
163
- case member
164
- when AST::Members::Extend
165
- if member.name.class?
166
- ancestor = Definition::Ancestor::Instance.new(
167
- name: absolute_type_name(member.name, namespace: namespace, location: member.location),
168
- args: member.args.map {|ty| absolute_type(ty, namespace: namespace) }
169
- )
170
- build_ancestors ancestor, ancestors: ancestors, building_ancestors: building_ancestors, location: member.location
171
- end
172
- end
173
- end
306
+ ancestors.unshift(self_ancestor)
174
307
 
175
- extension_ancestor = Definition::Ancestor::ExtensionSingleton.new(
176
- name: extension.name.absolute!,
177
- extension_name: extension.extension_name
178
- )
179
- ancestors.unshift(extension_ancestor)
308
+ one_ancestors.prepended_modules.each do |mod|
309
+ if mod.name.class?
310
+ name = mod.name
311
+ args = mod.args
312
+ mod_ancestors = instance_ancestors(name, building_ancestors: building_ancestors)
313
+ ancestors.unshift(*mod_ancestors.apply(args, location: entry.primary.decl.location))
314
+ end
315
+ end
316
+
317
+ building_ancestors.pop
318
+
319
+ instance_ancestors_cache[type_name] = Definition::InstanceAncestors.new(
320
+ type_name: type_name,
321
+ params: params,
322
+ ancestors: ancestors
323
+ )
324
+ end
325
+
326
+ def singleton_ancestors(type_name, building_ancestors: [])
327
+ as = singleton_ancestor_cache[type_name] and return as
328
+
329
+ entry = env.class_decls[type_name] or raise "Unknown name for singleton_ancestors: #{type_name}"
330
+ self_ancestor = Definition::Ancestor::Singleton.new(name: type_name)
331
+
332
+ RecursiveAncestorError.check!(self_ancestor,
333
+ ancestors: building_ancestors,
334
+ location: entry.primary.decl.location)
335
+ building_ancestors.push self_ancestor
336
+
337
+ one_ancestors = one_singleton_ancestors(type_name)
338
+
339
+ ancestors = []
340
+
341
+ case one_ancestors.super_class
342
+ when Definition::Ancestor::Instance
343
+ super_name = one_ancestors.super_class.name
344
+ super_args = one_ancestors.super_class.args
345
+
346
+ super_ancestors = instance_ancestors(super_name, building_ancestors: building_ancestors)
347
+ ancestors.unshift(*super_ancestors.apply(super_args, location: entry.primary.decl.location))
348
+
349
+ when Definition::Ancestor::Singleton
350
+ super_name = one_ancestors.super_class.name
351
+
352
+ super_ancestors = singleton_ancestors(super_name, building_ancestors: [])
353
+ ancestors.unshift(*super_ancestors.ancestors)
354
+ end
355
+
356
+ one_ancestors.extended_modules.each do |mod|
357
+ if mod.name.class?
358
+ name = mod.name
359
+ args = mod.args
360
+ mod_ancestors = instance_ancestors(name, building_ancestors: building_ancestors)
361
+ ancestors.unshift(*mod_ancestors.apply(args, location: entry.primary.decl.location))
180
362
  end
181
363
  end
182
364
 
365
+ ancestors.unshift(self_ancestor)
366
+
183
367
  building_ancestors.pop
184
368
 
185
- ancestors
369
+ singleton_ancestor_cache[type_name] = Definition::SingletonAncestors.new(
370
+ type_name: type_name,
371
+ ancestors: ancestors
372
+ )
186
373
  end
187
374
 
188
375
  def each_member_with_accessibility(members, accessibility: :public)
@@ -200,334 +387,365 @@ module RBS
200
387
 
201
388
  def build_instance(type_name)
202
389
  try_cache type_name, cache: instance_cache do
203
- decl = env.find_class(type_name)
204
- self_ancestor = Definition::Ancestor::Instance.new(name: type_name,
205
- args: Types::Variable.build(decl.type_params.each.map(&:name)))
206
- self_type = Types::ClassInstance.new(name: type_name, args: self_ancestor.args, location: nil)
207
-
208
- case decl
209
- when AST::Declarations::Class, AST::Declarations::Module
210
- ancestors = build_ancestors(self_ancestor)
211
- definition_pairs = ancestors.map do |ancestor|
390
+ entry = env.class_decls[type_name] or raise "Unknown name for build_instance: #{type_name}"
391
+
392
+ case entry
393
+ when Environment::ClassEntry, Environment::ModuleEntry
394
+ ancestors = instance_ancestors(type_name)
395
+ self_type = Types::ClassInstance.new(name: type_name,
396
+ args: Types::Variable.build(entry.type_params.each.map(&:name)),
397
+ location: nil)
398
+
399
+ definition_pairs = ancestors.ancestors.map do |ancestor|
212
400
  case ancestor
213
401
  when Definition::Ancestor::Instance
214
402
  [ancestor, build_one_instance(ancestor.name)]
215
403
  when Definition::Ancestor::Singleton
216
404
  [ancestor, build_one_singleton(ancestor.name)]
217
- when Definition::Ancestor::ExtensionInstance
218
- [ancestor, build_one_instance(ancestor.name, extension_name: ancestor.extension_name)]
219
- when Definition::Ancestor::ExtensionSingleton
220
- [ancestor, build_one_extension_singleton(ancestor.name, extension_name: ancestor.extension_name)]
405
+ else
406
+ raise
221
407
  end
222
408
  end
223
409
 
224
- if decl.is_a?(AST::Declarations::Module)
225
- if decl.self_type
226
- self_interface = absolute_type(decl.self_type, namespace: type_name.to_namespace)
227
- ancestor = Definition::Ancestor::Instance.new(name: self_interface.name,
228
- args: self_interface.args)
229
-
230
- definition_pairs.push [ancestor, build_one_instance(ancestor.name)]
410
+ if entry.is_a?(Environment::ModuleEntry)
411
+ entry.self_types.each do |module_self|
412
+ ancestor = Definition::Ancestor::Instance.new(name: module_self.name, args: module_self.args)
413
+ definition_pairs.push(
414
+ [
415
+ ancestor,
416
+ if module_self.name.interface?
417
+ build_interface(module_self.name)
418
+ else
419
+ build_instance(module_self.name)
420
+ end
421
+ ]
422
+ )
231
423
  end
232
424
  end
233
425
 
234
- merge_definitions(definition_pairs, decl: decl, self_type: self_type, ancestors: ancestors)
426
+ merge_definitions(type_name, definition_pairs, entry: entry, self_type: self_type, ancestors: ancestors)
427
+
428
+ else
429
+ raise
235
430
  end
236
431
  end
237
432
  end
238
433
 
239
434
  def build_singleton(type_name)
240
435
  try_cache type_name, cache: singleton_cache do
241
- decl = env.find_class(type_name)
242
- self_ancestor = Definition::Ancestor::Singleton.new(name: type_name)
243
- self_type = Types::ClassSingleton.new(name: type_name, location: nil)
436
+ entry = env.class_decls[type_name] or raise "Unknown name for build_singleton: #{type_name}"
437
+
438
+ case entry
439
+ when Environment::ClassEntry, Environment::ModuleEntry
440
+ ancestors = singleton_ancestors(type_name)
441
+ self_type = Types::ClassSingleton.new(name: type_name, location: nil)
442
+ instance_type = Types::ClassInstance.new(
443
+ name: type_name,
444
+ args: Types::Variable.build(entry.type_params.each.map(&:name)),
445
+ location: nil
446
+ )
244
447
 
245
- case decl
246
- when AST::Declarations::Class, AST::Declarations::Module
247
- ancestors = build_ancestors(self_ancestor)
248
- definition_pairs = ancestors.map do |ancestor|
448
+ definition_pairs = ancestors.ancestors.map do |ancestor|
249
449
  case ancestor
250
450
  when Definition::Ancestor::Instance
251
451
  [ancestor, build_one_instance(ancestor.name)]
252
452
  when Definition::Ancestor::Singleton
253
- [ancestor, build_one_singleton(ancestor.name)]
254
- when Definition::Ancestor::ExtensionInstance
255
- [ancestor, build_one_instance(ancestor.name, extension_name: ancestor.extension_name)]
256
- when Definition::Ancestor::ExtensionSingleton
257
- [ancestor, build_one_singleton(ancestor.name, extension_name: ancestor.extension_name)]
453
+ definition = build_one_singleton(ancestor.name)
454
+ definition = definition.sub(Substitution.build([], [], instance_type: instance_type))
455
+ definition = definition.map_method_type do |method_type|
456
+ s = Substitution.build(
457
+ method_type.free_variables.to_a,
458
+ method_type.free_variables.map { Types::Bases::Any.new(location: nil) }
459
+ )
460
+ method_type.sub(s)
461
+ end
462
+
463
+ [
464
+ ancestor,
465
+ definition
466
+ ]
467
+ else
468
+ raise
258
469
  end
259
470
  end
260
471
 
261
- if decl.is_a?(AST::Declarations::Class)
262
- definition_pairs.find {|ancestor, _| ancestor == self_ancestor }.tap do |_, definition|
263
- unless definition.methods[:new]&.implemented_in == decl
264
- instance_definition = build_instance(type_name)
265
- class_params = decl.type_params.each.map(&:name)
266
- initialize_method = instance_definition.methods[:initialize]
267
- method_types = initialize_method.method_types.map do |method_type|
268
- case method_type
269
- when MethodType
270
- fvs = method_type.free_variables + class_params
271
- unless fvs.empty?
272
- param_name_set = Set.new(class_params)
273
- bound_variables = method_type.type_params
274
- renamed_types = bound_variables.map do |x|
275
- if param_name_set.member?(x)
276
- Types::Variable.fresh(x)
277
- else
278
- Types::Variable.new(name: x, location: nil)
279
- end
280
- end
281
- sub = Substitution.build(bound_variables, renamed_types)
282
- method_type_params = renamed_types.unshift(*class_params)
283
- else
284
- sub = Substitution.build([], [])
285
- method_type_params = method_type.type_params
286
- end
472
+ merge_definitions(type_name, definition_pairs, entry: entry, self_type: self_type, ancestors: ancestors)
473
+ else
474
+ raise
475
+ end
476
+ end
477
+ end
287
478
 
288
- MethodType.new(
289
- type_params: method_type_params,
290
- type: method_type.type.sub(sub).with_return_type(instance_definition.self_type),
291
- block: method_type.block&.yield_self {|ty| ty.sub(sub) },
292
- location: method_type.location
293
- )
294
- end
295
- end.compact
296
-
297
- definition.methods[:new] = Definition::Method.new(
298
- super_method: nil,
299
- defined_in: nil,
300
- implemented_in: env.find_class(RBS::BuiltinNames::Class.name),
301
- method_types: method_types,
302
- accessibility: :public,
303
- attributes: [:incompatible],
304
- annotations: [],
305
- comment: nil
479
+ def method_definition_members(type_name, entry, kind:)
480
+ interface_methods = {}
481
+ methods = {}
482
+
483
+ entry.decls.each do |d|
484
+ each_member_with_accessibility(d.decl.members) do |member, accessibility|
485
+ case member
486
+ when AST::Members::MethodDefinition
487
+ case kind
488
+ when :singleton
489
+ next unless member.singleton?
490
+ when :instance
491
+ next unless member.instance?
492
+ end
493
+
494
+ methods[member.name] ||= []
495
+ methods[member.name] << [
496
+ member.update(types: member.types),
497
+ accessibility
498
+ ]
499
+ when AST::Members::Include, AST::Members::Extend
500
+ if member.name.interface?
501
+ if (kind == :instance && member.is_a?(AST::Members::Include)) || (kind == :singleton && member.is_a?(AST::Members::Extend))
502
+ NoMixinFoundError.check!(member.name, env: env, member: member)
503
+
504
+ interface_name = member.name
505
+ interface_args = member.args
506
+
507
+ interface_definition = build_interface(interface_name)
508
+
509
+ InvalidTypeApplicationError.check!(
510
+ type_name: interface_name,
511
+ args: interface_args,
512
+ params: interface_definition.type_params_decl,
513
+ location: member.location
306
514
  )
515
+
516
+ sub = Substitution.build(interface_definition.type_params, interface_args)
517
+
518
+ interface_definition.methods.each do |name, method|
519
+ interface_methods[name] = [method.sub(sub), member]
520
+ end
307
521
  end
308
522
  end
309
523
  end
524
+ end
525
+ end
526
+
527
+ result = {}
528
+
529
+ interface_methods.each do |name, pair|
530
+ method_definition, _ = pair
531
+ result[name] = [:public, method_definition]
532
+ end
533
+
534
+ methods.each do |method_name, array|
535
+ if result[method_name]
536
+ unless array.all? {|pair| pair[0].overload? }
537
+ raise MethodDefinitionConflictWithInterfaceMixinError.new(
538
+ type_name: type_name,
539
+ method_name: method_name,
540
+ kind: :instance,
541
+ mixin_member: interface_methods[method_name][1],
542
+ entries: array.map(&:first)
543
+ )
544
+ end
545
+
546
+ unless array.all? {|pair| pair[1] == :public}
547
+ raise InconsistentMethodVisibilityError.new(
548
+ type_name: type_name,
549
+ method_name: method_name,
550
+ kind: :instance,
551
+ member_pairs: array
552
+ )
553
+ end
554
+
555
+ result[method_name] += array.map(&:first)
556
+ else
557
+ case
558
+ when array.size == 1 && !array[0][0].overload?
559
+ member, visibility = array[0]
560
+ result[method_name] = [visibility, nil, member]
561
+
562
+ when array.count {|pair| !pair[0].overload? } == 1
563
+ visibilities = array.group_by {|pair| pair[1] }
564
+
565
+ if visibilities.size > 1
566
+ raise InconsistentMethodVisibilityError.new(
567
+ type_name: type_name,
568
+ method_name: method_name,
569
+ kind: :instance,
570
+ member_pairs: array
571
+ )
572
+ end
573
+
574
+ overloads, primary = array.map(&:first).partition(&:overload?)
575
+ result[method_name] = [array[0][1], nil, *primary, *overloads]
310
576
 
311
- merge_definitions(definition_pairs, decl: decl, self_type: self_type, ancestors: ancestors)
577
+ else
578
+ raise InvalidOverloadMethodError.new(
579
+ type_name: type_name,
580
+ method_name: method_name,
581
+ kind: :instance,
582
+ members: array.map(&:first)
583
+ )
584
+ end
312
585
  end
313
586
  end
587
+
588
+ result
314
589
  end
315
590
 
316
- def build_one_instance(type_name, extension_name: nil)
317
- decl = if extension_name
318
- env.each_extension(type_name).find {|ext| ext.extension_name == extension_name } or
319
- raise "Unknown extension: #{type_name} (#{extension_name})"
320
- else
321
- env.find_class(type_name)
322
- end
323
-
324
- case decl
325
- when AST::Declarations::Interface
326
- build_interface type_name, decl
327
- else
328
- namespace = type_name.to_namespace
591
+ def build_one_instance(type_name)
592
+ try_cache(type_name, cache: one_instance_cache) do
593
+ entry = env.class_decls[type_name]
329
594
 
330
- case decl
331
- when AST::Declarations::Class, AST::Declarations::Module
332
- self_type = Types::ClassInstance.new(name: type_name,
333
- args: Types::Variable.build(decl.type_params.each.map(&:name)),
334
- location: nil)
335
- ancestors = [Definition::Ancestor::Instance.new(name: type_name, args: self_type.args)]
336
- when AST::Declarations::Extension
337
- self_type = Types::ClassInstance.new(name: type_name, args: Types::Variable.build(decl.type_params), location: nil)
338
- ancestors = [Definition::Ancestor::ExtensionInstance.new(name: type_name,
339
- extension_name: extension_name,
340
- args: self_type.args)]
341
- end
595
+ self_type = Types::ClassInstance.new(name: type_name,
596
+ args: Types::Variable.build(entry.type_params.each.map(&:name)),
597
+ location: nil)
598
+ ancestors = [Definition::Ancestor::Instance.new(name: type_name, args: self_type.args)]
342
599
 
343
- Definition.new(declaration: decl, self_type: self_type, ancestors: ancestors).tap do |definition|
344
- alias_members = []
600
+ Definition.new(type_name: type_name, entry: entry, self_type: self_type, ancestors: ancestors).tap do |definition|
601
+ method_definition_members(type_name, entry, kind: :instance).each do |method_name, array|
602
+ visibility, method_def, *members = array
345
603
 
346
- each_member_with_accessibility(decl.members) do |member, accessibility|
347
- case member
348
- when AST::Members::MethodDefinition
349
- if member.instance?
350
- name = member.name
351
- method_types = member.types.map do |method_type|
352
- case method_type
353
- when MethodType
354
- method_type.map_type do |type|
355
- absolute_type(type, namespace: namespace)
356
- end
357
- when :super
358
- :super
359
- end
604
+ m = if method_def
605
+ Definition::Method.new(
606
+ super_method: nil,
607
+ accessibility: visibility,
608
+ defs: method_def.defs.map {|defn| defn.update(implemented_in: type_name) }
609
+ )
610
+ else
611
+ Definition::Method.new(
612
+ super_method: nil,
613
+ accessibility: visibility,
614
+ defs: []
615
+ )
360
616
  end
361
617
 
362
- DuplicatedMethodDefinitionError.check!(
363
- decl: decl,
364
- methods: definition.methods,
365
- name: name,
366
- location: member.location
367
- )
368
-
369
- attrs = if name == :initialize
370
- (member.attributes + [:incompatible]).uniq
371
- else
372
- member.attributes
373
- end
374
-
375
- definition.methods[name] = Definition::Method.new(super_method: nil,
376
- method_types: method_types,
377
- defined_in: decl,
378
- implemented_in: decl,
379
- accessibility: accessibility,
380
- attributes: attrs,
381
- annotations: member.annotations,
382
- comment: member.comment)
383
- end
384
- when AST::Members::AttrReader, AST::Members::AttrAccessor, AST::Members::AttrWriter
385
- name = member.name
386
- type = absolute_type(member.type, namespace: namespace)
387
- ivar_name = case member.ivar_name
388
- when false
389
- nil
390
- else
391
- member.ivar_name || :"@#{member.name}"
392
- end
393
-
394
- if member.is_a?(AST::Members::AttrReader) || member.is_a?(AST::Members::AttrAccessor)
395
- definition.methods[name] = Definition::Method.new(
396
- super_method: nil,
397
- method_types: [
398
- MethodType.new(
399
- type_params: [],
400
- type: Types::Function.empty(type),
401
- block: nil,
402
- location: nil
403
- )
404
- ],
405
- defined_in: decl,
406
- implemented_in: decl,
407
- accessibility: accessibility,
408
- attributes: [],
409
- annotations: member.annotations,
410
- comment: member.comment
618
+ definition.methods[method_name] = members.inject(m) do |original, member|
619
+ defs = member.types.map do |method_type|
620
+ Definition::Method::TypeDef.new(
621
+ type: method_type,
622
+ member: member,
623
+ implemented_in: type_name,
624
+ defined_in: type_name
411
625
  )
412
626
  end
413
627
 
414
- if member.is_a?(AST::Members::AttrWriter) || member.is_a?(AST::Members::AttrAccessor)
415
- definition.methods[:"#{name}="] = Definition::Method.new(
416
- super_method: nil,
417
- method_types: [
418
- MethodType.new(
419
- type_params: [],
420
- type: Types::Function.new(required_positionals: [Types::Function::Param.new(name: name, type: type)],
421
- optional_positionals: [],
422
- rest_positionals: nil,
423
- trailing_positionals: [],
424
- required_keywords: {},
425
- optional_keywords: {},
426
- rest_keywords: nil,
427
- return_type: type),
428
- block: nil,
429
- location: nil
430
- )
431
- ],
432
- defined_in: decl,
433
- implemented_in: decl,
434
- accessibility: accessibility,
435
- attributes: [],
436
- annotations: member.annotations,
437
- comment: member.comment
628
+ Definition::Method.new(
629
+ super_method: nil,
630
+ defs: defs + original.defs,
631
+ accessibility: original.accessibility
632
+ )
633
+ end
634
+ end
635
+
636
+ entry.decls.each do |d|
637
+ each_member_with_accessibility(d.decl.members) do |member, accessibility|
638
+ case member
639
+ when AST::Members::AttrReader, AST::Members::AttrAccessor, AST::Members::AttrWriter
640
+ name = member.name
641
+ type = member.type
642
+
643
+ ivar_name = case member.ivar_name
644
+ when false
645
+ nil
646
+ else
647
+ member.ivar_name || :"@#{member.name}"
648
+ end
649
+
650
+ if member.is_a?(AST::Members::AttrReader) || member.is_a?(AST::Members::AttrAccessor)
651
+ definition.methods[name] = Definition::Method.new(
652
+ super_method: nil,
653
+ defs: [
654
+ Definition::Method::TypeDef.new(
655
+ type: MethodType.new(
656
+ type_params: [],
657
+ type: Types::Function.empty(type),
658
+ block: nil,
659
+ location: nil
660
+ ),
661
+ member: member,
662
+ defined_in: type_name,
663
+ implemented_in: type_name
664
+ )
665
+ ],
666
+ accessibility: accessibility
667
+ )
668
+ end
669
+
670
+ if member.is_a?(AST::Members::AttrWriter) || member.is_a?(AST::Members::AttrAccessor)
671
+ definition.methods[:"#{name}="] = Definition::Method.new(
672
+ super_method: nil,
673
+ defs: [
674
+ Definition::Method::TypeDef.new(
675
+ type: MethodType.new(
676
+ type_params: [],
677
+ type: Types::Function.empty(type).update(
678
+ required_positionals: [Types::Function::Param.new(name: name, type: type)]
679
+ ),
680
+ block: nil,
681
+ location: nil
682
+ ),
683
+ member: member,
684
+ defined_in: type_name,
685
+ implemented_in: type_name
686
+ ),
687
+ ],
688
+ accessibility: accessibility
689
+ )
690
+ end
691
+
692
+ if ivar_name
693
+ definition.instance_variables[ivar_name] = Definition::Variable.new(
694
+ parent_variable: nil,
695
+ type: type,
696
+ declared_in: type_name
697
+ )
698
+ end
699
+
700
+ when AST::Members::InstanceVariable
701
+ definition.instance_variables[member.name] = Definition::Variable.new(
702
+ parent_variable: nil,
703
+ type: member.type,
704
+ declared_in: type_name
438
705
  )
439
- end
440
706
 
441
- if ivar_name
442
- definition.instance_variables[ivar_name] = Definition::Variable.new(
707
+ when AST::Members::ClassVariable
708
+ definition.class_variables[member.name] = Definition::Variable.new(
443
709
  parent_variable: nil,
444
- type: type,
445
- declared_in: decl
710
+ type: member.type,
711
+ declared_in: type_name
446
712
  )
447
- end
448
713
 
449
- when AST::Members::Alias
450
- if member.instance?
451
- alias_members << member
452
714
  end
453
- when AST::Members::Include
454
- if member.name.interface?
455
- absolute_name = absolute_type_name(member.name, namespace: namespace, location: member.location)
456
- interface_definition = build_one_instance(absolute_name)
457
- absolute_args = member.args.map {|ty| absolute_type(ty, namespace: namespace) }
458
-
459
- InvalidTypeApplicationError.check!(
460
- type_name: absolute_name,
461
- args: absolute_args,
462
- params: interface_definition.type_params_decl,
463
- location: member.location
464
- )
715
+ end
716
+ end
465
717
 
466
- sub = Substitution.build(interface_definition.type_params, absolute_args)
467
- interface_definition.methods.each do |name, method|
468
- method_types = method.method_types.map do |method_type|
469
- method_type.sub(sub).map_type do |type|
470
- absolute_type(type, namespace: namespace)
471
- end
472
- end
718
+ entry.decls.each do |d|
719
+ d.decl.members.each do |member|
720
+ case member
721
+ when AST::Members::Alias
722
+ if member.instance?
723
+ UnknownMethodAliasError.check!(
724
+ methods: definition.methods,
725
+ original_name: member.old_name,
726
+ aliased_name: member.new_name,
727
+ location: member.location
728
+ )
473
729
 
474
730
  DuplicatedMethodDefinitionError.check!(
475
- decl: decl,
731
+ decl: d.decl,
476
732
  methods: definition.methods,
477
- name: name,
733
+ name: member.new_name,
478
734
  location: member.location
479
735
  )
480
736
 
481
- definition.methods[name] = Definition::Method.new(
482
- super_method: nil,
483
- method_types: method_types,
484
- defined_in: method.defined_in,
485
- implemented_in: decl,
486
- accessibility: method.accessibility,
487
- attributes: [],
488
- annotations: method.annotations,
489
- comment: member.comment
490
- )
737
+ definition.methods[member.new_name] = definition.methods[member.old_name]
491
738
  end
492
739
  end
493
- when AST::Members::InstanceVariable
494
- definition.instance_variables[member.name] = Definition::Variable.new(
495
- type: absolute_type(member.type, namespace: namespace),
496
- parent_variable: nil,
497
- declared_in: decl
498
- )
499
- when AST::Members::ClassVariable
500
- definition.class_variables[member.name] = Definition::Variable.new(
501
- type: absolute_type(member.type, namespace: namespace),
502
- parent_variable: nil,
503
- declared_in: decl
504
- )
505
740
  end
506
741
  end
507
742
 
508
- alias_members.each do |member|
509
- UnknownMethodAliasError.check!(
510
- methods: definition.methods,
511
- original_name: member.old_name,
512
- aliased_name: member.new_name,
513
- location: member.location
514
- )
515
-
516
- DuplicatedMethodDefinitionError.check!(
517
- decl: decl,
518
- methods: definition.methods,
519
- name: member.new_name,
520
- location: member.location
743
+ entry.decls.each do |d|
744
+ validate_parameter_variance(
745
+ decl: d.decl,
746
+ methods: definition.methods
521
747
  )
522
-
523
- # FIXME: may cause a problem if #old_name has super type
524
- definition.methods[member.new_name] = definition.methods[member.old_name]
525
748
  end
526
-
527
- validate_parameter_variance(
528
- decl: decl,
529
- methods: definition.methods
530
- )
531
749
  end
532
750
  end
533
751
  end
@@ -543,14 +761,8 @@ module RBS
543
761
  end
544
762
 
545
763
  def validate_parameter_variance(decl:, methods:)
546
- type_params = case decl
547
- when AST::Declarations::Extension
548
- env.find_class(decl.name.absolute!).type_params.rename_to(decl.type_params)
549
- else
550
- decl.type_params
551
- end
764
+ type_params = decl.type_params
552
765
 
553
- namespace = decl.name.absolute!.to_namespace
554
766
  calculator = VarianceCalculator.new(builder: self)
555
767
  param_names = type_params.each.map(&:name)
556
768
 
@@ -558,9 +770,8 @@ module RBS
558
770
 
559
771
  if decl.is_a?(AST::Declarations::Class)
560
772
  if decl.super_class
561
- absolute_super_name = absolute_type_name(decl.super_class.name, namespace: namespace, location: decl.location)
562
- absolute_args = decl.super_class.args.map {|type| absolute_type(type, namespace: namespace) }
563
- result = calculator.in_inherit(name: absolute_super_name, args: absolute_args, variables: param_names)
773
+ super_class = decl.super_class
774
+ result = calculator.in_inherit(name: super_class.name, args: super_class.args, variables: param_names)
564
775
 
565
776
  validate_params_with type_params, result: result do |param|
566
777
  errors.push InvalidVarianceAnnotationError::InheritanceError.new(
@@ -574,9 +785,7 @@ module RBS
574
785
  case member
575
786
  when AST::Members::Include
576
787
  if member.name.class?
577
- absolute_module_name = absolute_type_name(member.name, namespace: namespace, location: decl.location)
578
- absolute_args = member.args.map {|type| absolute_type(type, namespace: namespace) }
579
- result = calculator.in_inherit(name: absolute_module_name, args: absolute_args, variables: param_names)
788
+ result = calculator.in_inherit(name: member.name, args: member.args, variables: param_names)
580
789
 
581
790
  validate_params_with type_params, result: result do |param|
582
791
  errors.push InvalidVarianceAnnotationError::MixinError.new(
@@ -610,148 +819,151 @@ module RBS
610
819
  end
611
820
  end
612
821
 
613
- def build_one_singleton(type_name, extension_name: nil)
614
- decl = if extension_name
615
- env.each_extension(type_name).find {|ext| ext.extension_name == extension_name } or
616
- raise "Unknown extension: #{type_name} (#{extension_name})"
617
- else
618
- env.find_class(type_name)
619
- end
822
+ def build_one_singleton(type_name)
823
+ try_cache(type_name, cache: one_singleton_cache) do
824
+ entry = env.class_decls[type_name]
620
825
 
621
- namespace = type_name.to_namespace
622
-
623
- case decl
624
- when AST::Declarations::Module, AST::Declarations::Class
625
826
  self_type = Types::ClassSingleton.new(name: type_name, location: nil)
626
827
  ancestors = [Definition::Ancestor::Singleton.new(name: type_name)]
627
- when AST::Declarations::Extension
628
- self_type = Types::ClassSingleton.new(name: type_name, location: nil)
629
- ancestors = [Definition::Ancestor::ExtensionSingleton.new(name: type_name, extension_name: extension_name)]
630
- end
631
828
 
632
- Definition.new(declaration: decl, self_type: self_type, ancestors: ancestors).tap do |definition|
633
- alias_members = []
829
+ Definition.new(type_name: type_name, entry: entry, self_type: self_type, ancestors: ancestors).tap do |definition|
830
+ method_definition_members(type_name, entry, kind: :singleton).each do |method_name, array|
831
+ visibility, method_def, *members = array
634
832
 
635
- each_member_with_accessibility(decl.members) do |member, accessibility|
636
- case member
637
- when AST::Members::MethodDefinition
638
- if member.singleton?
639
- name = member.name
640
- method_types = member.types.map do |method_type|
641
- method_type.map_type do |type|
642
- absolute_type(type, namespace: namespace)
643
- end
833
+ m = Definition::Method.new(
834
+ super_method: nil,
835
+ defs: method_def&.yield_self do |method_def|
836
+ method_def.defs.map {|defn| defn.update(implemented_in: type_name) }
837
+ end || [],
838
+ accessibility: visibility
839
+ )
840
+ definition.methods[method_name] = members.inject(m) do |original, new|
841
+ defs = new.types.map do |type|
842
+ Definition::Method::TypeDef.new(
843
+ type: type,
844
+ member: new,
845
+ defined_in: type_name,
846
+ implemented_in: type_name
847
+ )
644
848
  end
645
-
646
- DuplicatedMethodDefinitionError.check!(
647
- decl: decl,
648
- methods: definition.methods,
649
- name: name,
650
- location: member.location
849
+ Definition::Method.new(
850
+ super_method: nil,
851
+ defs: defs + original.defs,
852
+ accessibility: original.accessibility
651
853
  )
652
-
653
- definition.methods[name] = Definition::Method.new(super_method: nil,
654
- method_types: method_types,
655
- defined_in: decl,
656
- implemented_in: decl,
657
- accessibility: accessibility,
658
- attributes: member.attributes,
659
- annotations: member.annotations,
660
- comment: member.comment)
661
854
  end
662
- when AST::Members::Alias
663
- if member.singleton?
664
- alias_members << member
855
+ end
856
+
857
+ entry.decls.each do |d|
858
+ d.decl.members.each do |member|
859
+ case member
860
+ when AST::Members::Alias
861
+ if member.singleton?
862
+ UnknownMethodAliasError.check!(
863
+ methods: definition.methods,
864
+ original_name: member.old_name,
865
+ aliased_name: member.new_name,
866
+ location: member.location
867
+ )
868
+
869
+ DuplicatedMethodDefinitionError.check!(
870
+ decl: d.decl,
871
+ methods: definition.methods,
872
+ name: member.new_name,
873
+ location: member.location
874
+ )
875
+
876
+ definition.methods[member.new_name] = definition.methods[member.old_name]
877
+ end
878
+ end
665
879
  end
666
- when AST::Members::Extend
667
- if member.name.interface?
668
- absolute_name = absolute_type_name(member.name, namespace: namespace, location: member.location)
669
- interface_definition = build_one_instance(absolute_name)
670
- absolute_args = member.args.map {|ty| absolute_type(ty, namespace: namespace) }
671
-
672
- InvalidTypeApplicationError.check!(
673
- type_name: absolute_name,
674
- args: absolute_args,
675
- params: interface_definition.type_params_decl,
676
- location: member.location
677
- )
880
+ end
678
881
 
679
- sub = Substitution.build(interface_definition.type_params, absolute_args)
680
- interface_definition.methods.each do |name, method|
681
- method_types = method.method_types.map do |method_type|
682
- method_type.sub(sub).map_type do |type|
683
- absolute_type(type, namespace: namespace)
882
+ unless definition.methods.key?(:new)
883
+ instance = build_one_instance(type_name)
884
+ initialize = instance.methods[:initialize]
885
+
886
+ if initialize
887
+ class_params = entry.type_params.each.map(&:name)
888
+
889
+ initialize_defs = initialize.defs
890
+ definition.methods[:new] = Definition::Method.new(
891
+ super_method: nil,
892
+ defs: initialize_defs.map do |initialize_def|
893
+ method_type = initialize_def.type
894
+
895
+ class_type_param_vars = Set.new(class_params)
896
+ method_type_param_vars = Set.new(method_type.type_params)
897
+
898
+ if class_type_param_vars.intersect?(method_type_param_vars)
899
+ renamed_method_params = method_type.type_params.map do |name|
900
+ if class_type_param_vars.include?(name)
901
+ Types::Variable.fresh(name).name
902
+ else
903
+ name
904
+ end
905
+ end
906
+ method_params = class_params + renamed_method_params
907
+
908
+ sub = Substitution.build(method_type.type_params, Types::Variable.build(renamed_method_params))
909
+ else
910
+ method_params = class_params + method_type.type_params
911
+ sub = Substitution.build([], [])
684
912
  end
685
- end
686
913
 
687
- DuplicatedMethodDefinitionError.check!(
688
- decl: decl,
689
- methods: definition.methods,
690
- name: name,
691
- location: member.location
914
+ method_type = method_type.map_type {|ty| ty.sub(sub) }
915
+ method_type = method_type.update(
916
+ type_params: method_params,
917
+ type: method_type.type.with_return_type(Types::Bases::Instance.new(location: nil))
918
+ )
919
+
920
+ Definition::Method::TypeDef.new(
921
+ type: method_type,
922
+ member: initialize_def.member,
923
+ defined_in: nil,
924
+ implemented_in: nil
925
+ )
926
+ end,
927
+ accessibility: :public
928
+ )
929
+ end
930
+ end
931
+
932
+ entry.decls.each do |d|
933
+ each_member_with_accessibility(d.decl.members) do |member, _|
934
+ case member
935
+ when AST::Members::ClassInstanceVariable
936
+ definition.instance_variables[member.name] = Definition::Variable.new(
937
+ parent_variable: nil,
938
+ type: member.type,
939
+ declared_in: type_name
692
940
  )
693
941
 
694
- definition.methods[name] = Definition::Method.new(
695
- super_method: nil,
696
- method_types: method_types,
697
- defined_in: method.defined_in,
698
- implemented_in: decl,
699
- accessibility: method.accessibility,
700
- attributes: method.attributes,
701
- annotations: method.annotations,
702
- comment: member.comment
942
+ when AST::Members::ClassVariable
943
+ definition.class_variables[member.name] = Definition::Variable.new(
944
+ parent_variable: nil,
945
+ type: member.type,
946
+ declared_in: type_name
703
947
  )
704
948
  end
705
949
  end
706
- when AST::Members::ClassInstanceVariable
707
- definition.instance_variables[member.name] = Definition::Variable.new(
708
- type: absolute_type(member.type, namespace: namespace),
709
- parent_variable: nil,
710
- declared_in: decl
711
- )
712
- when AST::Members::ClassVariable
713
- definition.class_variables[member.name] = Definition::Variable.new(
714
- type: absolute_type(member.type, namespace: namespace),
715
- parent_variable: nil,
716
- declared_in: decl
717
- )
718
950
  end
719
951
  end
720
-
721
- alias_members.each do |member|
722
- UnknownMethodAliasError.check!(
723
- methods: definition.methods,
724
- original_name: member.old_name,
725
- aliased_name: member.new_name,
726
- location: member.location
727
- )
728
-
729
- DuplicatedMethodDefinitionError.check!(
730
- decl: decl,
731
- methods: definition.methods,
732
- name: member.new_name,
733
- location: member.location
734
- )
735
-
736
- # FIXME: may cause a problem if #old_name has super type
737
- definition.methods[member.new_name] = definition.methods[member.old_name]
738
- end
739
952
  end
740
953
  end
741
954
 
742
- def merge_definitions(pairs, decl:, self_type:, ancestors:)
743
- Definition.new(declaration: decl, self_type: self_type, ancestors: ancestors).tap do |definition|
955
+ def merge_definitions(type_name, pairs, entry:, self_type:, ancestors:)
956
+ Definition.new(type_name: type_name, entry: entry, self_type: self_type, ancestors: ancestors).tap do |definition|
744
957
  pairs.reverse_each do |(ancestor, current_definition)|
745
958
  sub = case ancestor
746
- when Definition::Ancestor::Instance, Definition::Ancestor::ExtensionInstance
959
+ when Definition::Ancestor::Instance
747
960
  Substitution.build(current_definition.type_params, ancestor.args)
748
- when Definition::Ancestor::Singleton, Definition::Ancestor::ExtensionSingleton
961
+ when Definition::Ancestor::Singleton
749
962
  Substitution.build([], [])
750
963
  end
751
- namespace = current_definition.name.absolute!.to_namespace
752
964
 
753
965
  current_definition.methods.each do |name, method|
754
- merge_method definition.methods, name, method, sub, namespace
966
+ merge_method definition.methods, name, method, sub
755
967
  end
756
968
 
757
969
  current_definition.instance_variables.each do |name, variable|
@@ -775,25 +987,13 @@ module RBS
775
987
  )
776
988
  end
777
989
 
778
- def merge_method(methods, name, method, sub, namespace)
990
+ def merge_method(methods, name, method, sub)
779
991
  super_method = methods[name]
780
992
 
781
993
  methods[name] = Definition::Method.new(
782
- method_types: method.method_types.flat_map do |method_type|
783
- case method_type
784
- when MethodType
785
- [absolute_type(method_type.sub(sub), namespace: namespace)]
786
- when :super
787
- super_method.method_types
788
- end
789
- end,
790
994
  super_method: super_method,
791
- defined_in: method.defined_in,
792
- implemented_in: method.implemented_in,
793
995
  accessibility: method.accessibility,
794
- attributes: method.attributes,
795
- annotations: method.annotations,
796
- comment: method.comment
996
+ defs: sub.mapping.empty? ? method.defs : method.defs.map {|defn| defn.update(type: defn.type.sub(sub)) }
797
997
  )
798
998
  end
799
999
 
@@ -816,31 +1016,45 @@ module RBS
816
1016
  end
817
1017
  end
818
1018
 
819
- def build_interface(type_name, declaration = env.find_class(type_name))
820
- self_type = Types::Interface.new(
821
- name: type_name,
822
- args: declaration.type_params.each.map {|p| Types::Variable.new(name: p.name, location: nil) },
823
- location: nil
824
- )
1019
+ def build_interface(type_name)
1020
+ try_cache(type_name, cache: interface_cache) do
1021
+ entry = env.interface_decls[type_name] or raise "Unknown name for build_interface: #{type_name}"
1022
+ declaration = entry.decl
825
1023
 
826
- namespace = type_name.to_namespace
1024
+ self_type = Types::Interface.new(
1025
+ name: type_name,
1026
+ args: Types::Variable.build(declaration.type_params.each.map(&:name)),
1027
+ location: nil
1028
+ )
827
1029
 
828
- Definition.new(declaration: declaration, self_type: self_type, ancestors: []).tap do |definition|
829
- alias_members = []
1030
+ Definition.new(type_name: type_name, entry: entry, self_type: self_type, ancestors: nil).tap do |definition|
1031
+ include_members = []
1032
+ def_members = []
1033
+ alias_members = []
830
1034
 
831
- declaration.members.each do |member|
832
- case member
833
- when AST::Members::Include
834
- mixin_name = env.absolute_interface_name(member.name, namespace: namespace) || member.name.absolute!
835
- mixin = build_one_instance(mixin_name)
1035
+ declaration.members.each do |member|
1036
+ case member
1037
+ when AST::Members::Include
1038
+ include_members << member
1039
+ when AST::Members::MethodDefinition
1040
+ def_members << member
1041
+ when AST::Members::Alias
1042
+ alias_members << member
1043
+ end
1044
+ end
1045
+
1046
+ include_members.each do |member|
1047
+ NoMixinFoundError.check!(member.name, env: env, member: member)
836
1048
 
837
- args = member.args.map {|type| absolute_type(type, namespace: namespace) }
838
- type_params = mixin.declaration.type_params
1049
+ mixin = build_interface(member.name)
1050
+
1051
+ args = member.args
1052
+ type_params = mixin.entry.decl.type_params
839
1053
 
840
1054
  InvalidTypeApplicationError.check!(
841
1055
  type_name: type_name,
842
1056
  args: args,
843
- params: type_params,
1057
+ params: type_params.each.map(&:name),
844
1058
  location: member.location
845
1059
  )
846
1060
 
@@ -849,11 +1063,8 @@ module RBS
849
1063
  definition.methods[name] = method.sub(sub)
850
1064
  end
851
1065
  end
852
- end
853
1066
 
854
- declaration.members.each do |member|
855
- case member
856
- when AST::Members::MethodDefinition
1067
+ def_members.each do |member|
857
1068
  DuplicatedMethodDefinitionError.check!(
858
1069
  decl: declaration,
859
1070
  methods: definition.methods,
@@ -863,57 +1074,44 @@ module RBS
863
1074
 
864
1075
  method = Definition::Method.new(
865
1076
  super_method: nil,
866
- method_types: member.types.map do |method_type|
867
- method_type.map_type {|ty| absolute_type(ty, namespace: namespace) }
1077
+ defs: member.types.map do |method_type|
1078
+ Definition::Method::TypeDef.new(
1079
+ type: method_type,
1080
+ member: member,
1081
+ defined_in: type_name,
1082
+ implemented_in: nil
1083
+ )
868
1084
  end,
869
- defined_in: declaration,
870
- implemented_in: nil,
871
- accessibility: :public,
872
- attributes: member.attributes,
873
- annotations: member.annotations,
874
- comment: member.comment
1085
+ accessibility: :public
875
1086
  )
876
1087
  definition.methods[member.name] = method
877
- when AST::Members::Alias
878
- alias_members << member
879
1088
  end
880
- end
881
1089
 
882
- alias_members.each do |member|
883
- UnknownMethodAliasError.check!(
884
- methods: definition.methods,
885
- original_name: member.old_name,
886
- aliased_name: member.new_name,
887
- location: member.location
888
- )
1090
+ alias_members.each do |member|
1091
+ UnknownMethodAliasError.check!(
1092
+ methods: definition.methods,
1093
+ original_name: member.old_name,
1094
+ aliased_name: member.new_name,
1095
+ location: member.location
1096
+ )
889
1097
 
890
- DuplicatedMethodDefinitionError.check!(
891
- decl: declaration,
892
- methods: definition.methods,
893
- name: member.new_name,
894
- location: member.location
895
- )
1098
+ DuplicatedMethodDefinitionError.check!(
1099
+ decl: declaration,
1100
+ methods: definition.methods,
1101
+ name: member.new_name,
1102
+ location: member.location
1103
+ )
896
1104
 
897
- # FIXME: may cause a problem if #old_name has super type
898
- definition.methods[member.new_name] = definition.methods[member.old_name]
1105
+ # FIXME: may cause a problem if #old_name has super type
1106
+ definition.methods[member.new_name] = definition.methods[member.old_name]
1107
+ end
899
1108
  end
900
1109
  end
901
1110
  end
902
1111
 
903
- def absolute_type(type, namespace:)
904
- env.absolute_type(type, namespace: namespace) do |type|
905
- NoTypeFoundError.check!(type.name.absolute!, env: env, location: type.location)
906
- end
907
- end
908
-
909
- def absolute_type_name(type_name, namespace:, location:)
910
- env.absolute_type_name(type_name, namespace: namespace) do |type_name|
911
- NoTypeFoundError.check!(type_name.absolute!, env: env, location: location)
912
- end
913
- end
914
-
915
1112
  def expand_alias(type_name)
916
- absolute_type(env.find_alias(type_name).type, namespace: type_name.namespace)
1113
+ entry = env.alias_decls[type_name] or raise "Unknown name for expand_alias: #{type_name}"
1114
+ entry.decl.type
917
1115
  end
918
1116
  end
919
1117
  end