solargraph 0.53.3 → 0.54.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 (49) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +29 -0
  3. data/lib/solargraph/api_map/cache.rb +2 -12
  4. data/lib/solargraph/api_map/store.rb +11 -6
  5. data/lib/solargraph/api_map.rb +80 -26
  6. data/lib/solargraph/complex_type/type_methods.rb +62 -30
  7. data/lib/solargraph/complex_type/unique_type.rb +117 -66
  8. data/lib/solargraph/complex_type.rb +41 -25
  9. data/lib/solargraph/doc_map.rb +19 -3
  10. data/lib/solargraph/gem_pins.rb +9 -1
  11. data/lib/solargraph/language_server/host/dispatch.rb +8 -1
  12. data/lib/solargraph/language_server/host/sources.rb +1 -61
  13. data/lib/solargraph/language_server/host.rb +39 -68
  14. data/lib/solargraph/language_server/message/base.rb +1 -1
  15. data/lib/solargraph/language_server/message/initialize.rb +14 -0
  16. data/lib/solargraph/language_server/message/text_document/formatting.rb +1 -0
  17. data/lib/solargraph/language_server/progress.rb +118 -0
  18. data/lib/solargraph/language_server.rb +1 -0
  19. data/lib/solargraph/library.rb +136 -96
  20. data/lib/solargraph/parser/node_processor/base.rb +3 -2
  21. data/lib/solargraph/parser/node_processor.rb +1 -0
  22. data/lib/solargraph/parser/parser_gem/class_methods.rb +3 -7
  23. data/lib/solargraph/parser/parser_gem/node_methods.rb +0 -4
  24. data/lib/solargraph/parser/parser_gem/node_processors/masgn_node.rb +47 -0
  25. data/lib/solargraph/parser/parser_gem/node_processors/send_node.rb +5 -3
  26. data/lib/solargraph/parser/parser_gem/node_processors.rb +2 -0
  27. data/lib/solargraph/pin/base_variable.rb +34 -5
  28. data/lib/solargraph/pin/block.rb +62 -7
  29. data/lib/solargraph/pin/delegated_method.rb +5 -1
  30. data/lib/solargraph/pin/documenting.rb +2 -0
  31. data/lib/solargraph/pin/method.rb +4 -2
  32. data/lib/solargraph/pin/parameter.rb +5 -28
  33. data/lib/solargraph/rbs_map/conversions.rb +12 -6
  34. data/lib/solargraph/rbs_map/core_fills.rb +4 -1
  35. data/lib/solargraph/rbs_map.rb +11 -3
  36. data/lib/solargraph/shell.rb +18 -13
  37. data/lib/solargraph/source/chain.rb +20 -0
  38. data/lib/solargraph/source/updater.rb +1 -0
  39. data/lib/solargraph/source.rb +0 -44
  40. data/lib/solargraph/source_map/clip.rb +1 -0
  41. data/lib/solargraph/source_map/mapper.rb +3 -2
  42. data/lib/solargraph/source_map.rb +10 -0
  43. data/lib/solargraph/type_checker.rb +44 -18
  44. data/lib/solargraph/version.rb +1 -1
  45. data/lib/solargraph/workspace/config.rb +2 -1
  46. data/lib/solargraph/workspace.rb +13 -0
  47. data/lib/solargraph/yard_map/mapper/to_method.rb +5 -2
  48. metadata +4 -3
  49. data/lib/solargraph/language_server/host/cataloger.rb +0 -57
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: c5f84e528dd40d7638e36189ca6b4dceccdfd1722a07bd1c1f060bf0265aa815
4
- data.tar.gz: 39d6938ccabce6dda403c709711f6136472def5982222e73d89310eaeb906ee1
3
+ metadata.gz: 39ad27afe3afb59299f8701f9a7ea3f25a9f95379ef68e53ac0e22eb60f50e21
4
+ data.tar.gz: 1f01a9d5cdf4aec5b50c245a25b1f7d83e5d6762e5b8f65bc9ce3555654e21ed
5
5
  SHA512:
6
- metadata.gz: cf06b94032becde9f26b7d5cedcecbc0fd7d6bde539a980c748328f11165f91398605e7ff49af502b83a70a4aa9b32406c5846cda96f5246d20c97d17220700b
7
- data.tar.gz: bdddccf5d52efd2a9be2b00ac473065ecca21d76646d59d247c5cb93b14de137ebfc16ec4ffbc3ed0d6e9de9f271e9763808775d6aa271496e6328bf70b443bf
6
+ metadata.gz: 788f17e92a54e782ea1dcf03cb44245df823ba33b4fe866d1afa5d06c7171b40a4e1f93c97c8b26c13b58be7478b9b07cd75d6735da65ecef21ab6a4a61dbb0e
7
+ data.tar.gz: 742f43fcdce4a592a80ebe8e3acbd020f39f569cf323621a527e626ae8c6154f7dedb32739b8b62f38e98997ed414ec30471160332ecfb4a2fe5d5052e871333
data/CHANGELOG.md CHANGED
@@ -1,3 +1,32 @@
1
+ ## 0.54.0 - April 14, 2025
2
+ - Add support for simple block argument destructuring (#821)
3
+ - Benchmark the typecheck command (#852)
4
+ - Send Gem Caching Progress Notifications to LSP Clients (#855)
5
+ - [breaking] Fix more complex_type_spec.rb cases (#813)
6
+ - Mass assignment support - e.g., a, b = ['1', '2'] (#843)
7
+ - Memoize result of Chain#infer (#857)
8
+ - Ignore malformed mixins and overloads (#862)
9
+ - Drop Parser::ParserGem::ClassMethods#returns_from_node (#866)
10
+ - Refactor TypeChecker#argument_problems_for for type safety (#867)
11
+ - Specify more type behavior for variable reassignment (#863)
12
+ - One-step source synchronization (#871)
13
+ - Show cache progress in shell commands (#874)
14
+ - Fix miscellaneous scan errors (#875)
15
+ - Synchronous libraries (#876)
16
+ - Fix parsing of Set#classify method signature from RBS (#878)
17
+ - Sync Library#diagnose (#882)
18
+ - Doesn't false-alarm over splatted non-final args in typechecking (#883)
19
+ - Remove accidental inclusion of Module's methods in objects (#884)
20
+ - Remove another splat-related false alarm in strict typechecking (#889)
21
+ - Change require path `warn` to `debug` (#897)
22
+
23
+ ## 0.53.4 - March 30, 2025
24
+ - [regression] Restore 'Unresolved call' typecheck for stdlib objects (#849)
25
+ - Lazy dynamic rebinding (#851)
26
+ - Restore fill for Class#allocate (#848)
27
+ - [regression] Ensure YardMap gems have return type for Class<T>.new (#850)
28
+ - Create implicit .new pins in namespace method queries (#853)
29
+
1
30
  ## 0.53.3 - March 29, 2025
2
31
  - Remove redundant core fills (#824, #841)
3
32
  - Resolve self type in variable assignments (#839)
@@ -78,20 +78,10 @@ module Solargraph
78
78
  @receiver_definitions[path] = pin
79
79
  end
80
80
 
81
- # @param cursor [Source::Cursor]
82
- # @return [SourceMap::Clip, nil]
83
- def get_clip(cursor)
84
- @clips["#{cursor.filename}|#{cursor.range.inspect}|#{cursor.node&.to_sexp}"]
85
- end
86
-
87
- # @param cursor [Source::Cursor]
88
- # @param clip [SourceMap::Clip]
89
- def set_clip(cursor, clip)
90
- @clips["#{cursor.filename}|#{cursor.range.inspect}|#{cursor.node&.to_sexp}"] = clip
91
- end
92
-
93
81
  # @return [void]
94
82
  def clear
83
+ return if empty?
84
+
95
85
  all_caches.each(&:clear)
96
86
  end
97
87
 
@@ -65,6 +65,10 @@ module Solargraph
65
65
  path_pin_hash[path] || []
66
66
  end
67
67
 
68
+ def cacheable_pins
69
+ @cacheable_pins ||= pins_by_class(Pin::Namespace) + pins_by_class(Pin::Constant) + pins_by_class(Pin::Method) + pins_by_class(Pin::Reference)
70
+ end
71
+
68
72
  # @param fqns [String]
69
73
  # @param scope [Symbol] :class or :instance
70
74
  # @return [Enumerable<Solargraph::Pin::Base>]
@@ -96,7 +100,7 @@ module Solargraph
96
100
  @namespaces ||= Set.new
97
101
  end
98
102
 
99
- # @return [Enumerable<Solargraph::Pin::Base>]
103
+ # @return [Array<Solargraph::Pin::Base>]
100
104
  def namespace_pins
101
105
  pins_by_class(Solargraph::Pin::Namespace)
102
106
  end
@@ -140,8 +144,9 @@ module Solargraph
140
144
  to_s
141
145
  end
142
146
 
143
- # @param klass [Class]
144
- # @return [Enumerable<Solargraph::Pin::Base>]
147
+ # @generic T
148
+ # @param klass [Class<T>]
149
+ # @return [Array<T>]
145
150
  def pins_by_class klass
146
151
  # @type [Set<Solargraph::Pin::Base>]
147
152
  s = Set.new
@@ -165,7 +170,7 @@ module Solargraph
165
170
 
166
171
  private
167
172
 
168
- # @return [Hash{Array(String, String) => Array<Pin::Namespace>}]
173
+ # @return [Hash{::Array(String, String) => ::Array<Pin::Namespace>}]
169
174
  def fqns_pins_map
170
175
  @fqns_pins_map ||= Hash.new do |h, (base, name)|
171
176
  value = namespace_children(base).select { |pin| pin.name == name && pin.is_a?(Pin::Namespace) }
@@ -178,7 +183,7 @@ module Solargraph
178
183
  pins_by_class(Pin::Symbol)
179
184
  end
180
185
 
181
- # @return [Hash{String => Enumerable<String>}]
186
+ # @return [Hash{String => Array<String>}]
182
187
  def superclass_references
183
188
  @superclass_references ||= {}
184
189
  end
@@ -243,7 +248,7 @@ module Solargraph
243
248
  def index
244
249
  set = pins.to_set
245
250
  @pin_class_hash = set.classify(&:class).transform_values(&:to_a)
246
- # @type [Hash{Class => Enumerable<Solargraph::Pin::Base>}]
251
+ # @type [Hash{Class => ::Array<Solargraph::Pin::Base>}]
247
252
  @pin_select_cache = {}
248
253
  @namespace_map = set.classify(&:namespace)
249
254
  @path_pin_hash = set.classify(&:path)
@@ -29,6 +29,25 @@ module Solargraph
29
29
  index pins
30
30
  end
31
31
 
32
+ #
33
+ # This is a mutable object, which is cached in the Chain class -
34
+ # if you add any fields which change the results of calls (not
35
+ # just caches), please also change `equality_fields` below.
36
+ #
37
+
38
+ def eql?(other)
39
+ self.class == other.class &&
40
+ equality_fields == other.equality_fields
41
+ end
42
+
43
+ def ==(other)
44
+ self.eql?(other)
45
+ end
46
+
47
+ def hash
48
+ equality_fields.hash
49
+ end
50
+
32
51
  # @param pins [Array<Pin::Base>]
33
52
  # @return [self]
34
53
  def index pins
@@ -56,22 +75,31 @@ module Solargraph
56
75
  # @param bench [Bench]
57
76
  # @return [self]
58
77
  def catalog bench
59
- implicit.clear
60
- @cache.clear
78
+ old_api_hash = @source_map_hash&.values&.map(&:api_hash)
79
+ need_to_uncache = (old_api_hash != bench.source_maps.map(&:api_hash))
61
80
  @source_map_hash = bench.source_maps.map { |s| [s.filename, s] }.to_h
62
- pins = bench.source_maps.map(&:pins).flatten
81
+ pins = bench.source_maps.flat_map(&:pins).flatten
82
+ implicit.clear
63
83
  source_map_hash.each_value do |map|
64
84
  implicit.merge map.environ
65
85
  end
66
- unresolved_requires = (bench.external_requires + implicit.requires + bench.workspace.config.required).uniq
67
- @doc_map = DocMap.new(unresolved_requires, []) # @todo Implement gem preferences
86
+ unresolved_requires = (bench.external_requires + implicit.requires + bench.workspace.config.required).to_a.compact.uniq
87
+ if @unresolved_requires != unresolved_requires || @doc_map&.uncached_gemspecs&.any?
88
+ @doc_map = DocMap.new(unresolved_requires, [], bench.workspace.rbs_collection_path) # @todo Implement gem preferences
89
+ @unresolved_requires = unresolved_requires
90
+ need_to_uncache = true
91
+ end
68
92
  @store = Store.new(@@core_map.pins + @doc_map.pins + implicit.pins + pins)
69
- @unresolved_requires = @doc_map.unresolved_requires
93
+ @cache.clear if need_to_uncache
94
+
70
95
  @missing_docs = [] # @todo Implement missing docs
71
- store.block_pins.each { |blk| blk.rebind(self) }
72
96
  self
73
97
  end
74
98
 
99
+ protected def equality_fields
100
+ [self.class, @source_map_hash, implicit, @doc_map, @unresolved_requires, @missing_docs]
101
+ end
102
+
75
103
  # @return [::Array<Gem::Specification>]
76
104
  def uncached_gemspecs
77
105
  @doc_map&.uncached_gemspecs || []
@@ -134,14 +162,19 @@ module Solargraph
134
162
  # Create an ApiMap with a workspace in the specified directory and cache
135
163
  # any missing gems.
136
164
  #
165
+ #
166
+ # @todo IO::NULL is incorrectly inferred to be a String.
167
+ # @sg-ignore
168
+ #
137
169
  # @param directory [String]
170
+ # @param out [IO] The output stream for messages
138
171
  # @return [ApiMap]
139
- def self.load_with_cache directory
172
+ def self.load_with_cache directory, out = IO::NULL
140
173
  api_map = load(directory)
141
174
  return api_map if api_map.uncached_gemspecs.empty?
142
175
 
143
176
  api_map.uncached_gemspecs.each do |gemspec|
144
- Solargraph.logger.info "Caching #{gemspec.name} #{gemspec.version}..."
177
+ out.puts "Caching gem #{gemspec.name} #{gemspec.version}"
145
178
  pins = GemPins.build(gemspec)
146
179
  Solargraph::Cache.save('gems', "#{gemspec.name}-#{gemspec.version}.ser", pins)
147
180
  end
@@ -222,10 +255,15 @@ module Solargraph
222
255
  # @return [String, nil] fully qualified tag
223
256
  def qualify tag, context_tag = ''
224
257
  return tag if ['self', nil].include?(tag)
225
- context_type = ComplexType.parse(context_tag)
226
- type = ComplexType.parse(tag)
258
+ context_type = ComplexType.try_parse(context_tag)
259
+ return unless context_type
260
+
261
+ type = ComplexType.try_parse(tag)
262
+ return unless type
263
+
227
264
  fqns = qualify_namespace(type.rooted_namespace, context_type.rooted_namespace)
228
- return nil if fqns.nil?
265
+ return unless fqns
266
+
229
267
  fqns + type.substring
230
268
  end
231
269
 
@@ -312,8 +350,28 @@ module Solargraph
312
350
  result.concat inner_get_methods('Kernel', :instance, visibility, deep, skip)
313
351
  else
314
352
  result.concat inner_get_methods(rooted_tag, scope, visibility, deep, skip)
353
+ unless %w[Class Class<Class>].include?(rooted_tag)
354
+ result.map! do |pin|
355
+ next pin unless pin.path == 'Class#new'
356
+ init_pin = get_method_stack(rooted_tag, 'initialize').first
357
+ next pin unless init_pin
358
+
359
+ type = ComplexType.try_parse(ComplexType.try_parse(rooted_tag).namespace)
360
+ Pin::Method.new(
361
+ name: 'new',
362
+ scope: :class,
363
+ location: init_pin.location,
364
+ parameters: init_pin.parameters,
365
+ signatures: init_pin.signatures.map { |sig| sig.proxy(type) },
366
+ return_type: type,
367
+ comments: init_pin.comments,
368
+ closure: init_pin.closure
369
+ # @todo Hack to force TypeChecker#internal_or_core?
370
+ ).tap { |pin| pin.source = :rbs }
371
+ end
372
+ end
315
373
  result.concat inner_get_methods('Kernel', :instance, [:public], deep, skip) if visibility.include?(:private)
316
- result.concat inner_get_methods('Module', scope, visibility, deep, skip)
374
+ result.concat inner_get_methods('Module', scope, visibility, deep, skip) if scope == :module
317
375
  end
318
376
  resolved = resolve_method_aliases(result, visibility)
319
377
  cache.set_methods(rooted_tag, scope, visibility, deep, resolved)
@@ -447,9 +505,6 @@ module Solargraph
447
505
  def clip cursor
448
506
  raise FileNotFoundError, "ApiMap did not catalog #{cursor.filename}" unless source_map_hash.key?(cursor.filename)
449
507
 
450
- # @todo Clip caches are disabled pending resolution of a stale cache bug
451
- # cache.get_clip(cursor) ||
452
- # SourceMap::Clip.new(self, cursor).tap { |clip| cache.set_clip(cursor, clip) }
453
508
  SourceMap::Clip.new(self, cursor)
454
509
  end
455
510
 
@@ -554,8 +609,8 @@ module Solargraph
554
609
  # namespaces; resolving the generics in the method pins is this
555
610
  # class' responsibility
556
611
  raw_methods = store.get_methods(fqns, scope: scope, visibility: visibility).sort{ |a, b| a.name <=> b.name }
557
- namespace_pin = store.get_path_pins(fqns).select{|p| p.is_a?(Pin::Namespace)}.first
558
- methods = if rooted_tag != fqns
612
+ namespace_pin = store.get_path_pins(fqns).select { |p| p.is_a?(Pin::Namespace) }.first
613
+ methods = if namespace_pin && rooted_tag != fqns
559
614
  methods = raw_methods.map do |method_pin|
560
615
  method_pin.resolve_generics(namespace_pin, rooted_type)
561
616
  end
@@ -725,23 +780,22 @@ module Solargraph
725
780
  # @param visibility [Enumerable<Symbol>]
726
781
  # @return [Array<Pin::Base>]
727
782
  def resolve_method_aliases pins, visibility = [:public, :private, :protected]
728
- result = []
729
- pins.each do |pin|
783
+ pins.map do |pin|
730
784
  resolved = resolve_method_alias(pin)
731
- next if resolved.respond_to?(:visibility) && !visibility.include?(resolved.visibility)
732
- result.push resolved
733
- end
734
- result
785
+ next pin if resolved.respond_to?(:visibility) && !visibility.include?(resolved.visibility)
786
+ resolved
787
+ end.compact
735
788
  end
736
789
 
737
790
  # @param pin [Pin::MethodAlias, Pin::Base]
738
791
  # @return [Pin::Method]
739
792
  def resolve_method_alias pin
740
- return pin if !pin.is_a?(Pin::MethodAlias) || @method_alias_stack.include?(pin.path)
793
+ return pin unless pin.is_a?(Pin::MethodAlias)
794
+ return nil if @method_alias_stack.include?(pin.path)
741
795
  @method_alias_stack.push pin.path
742
796
  origin = get_method_stack(pin.full_context.tag, pin.original, scope: pin.scope).first
743
797
  @method_alias_stack.pop
744
- return pin if origin.nil?
798
+ return nil if origin.nil?
745
799
  args = {
746
800
  location: pin.location,
747
801
  closure: pin.closure,
@@ -22,14 +22,18 @@ module Solargraph
22
22
  # @return [String]
23
23
  attr_reader :name
24
24
 
25
- # @return [String]
26
- attr_reader :substring
25
+ # @return [Array<ComplexType>]
26
+ attr_reader :subtypes
27
27
 
28
28
  # @return [String]
29
- attr_reader :tag
29
+ def tag
30
+ @tag ||= "#{name}#{substring}"
31
+ end
30
32
 
31
- # @return [Array<ComplexType>]
32
- attr_reader :subtypes
33
+ # @return [String]
34
+ def rooted_tag
35
+ @rooted_tag ||= rooted_name + rooted_substring
36
+ end
33
37
 
34
38
  # @return [Boolean]
35
39
  def duck_type?
@@ -46,6 +50,10 @@ module Solargraph
46
50
  !substring.empty?
47
51
  end
48
52
 
53
+ def tuple?
54
+ @tuple_type ||= (name == 'Tuple') || (name == 'Array' && subtypes.length >= 1 && fixed_parameters?)
55
+ end
56
+
49
57
  def void?
50
58
  name == 'void'
51
59
  end
@@ -74,19 +82,28 @@ module Solargraph
74
82
  end
75
83
  end
76
84
 
85
+ # @return [Symbol, nil]
86
+ attr_reader :parameters_type
87
+
88
+ PARAMETERS_TYPE_BY_STARTING_TAG = {
89
+ '{' => :hash,
90
+ '(' => :fixed,
91
+ '<' => :list
92
+ }.freeze
93
+
77
94
  # @return [Boolean]
78
95
  def list_parameters?
79
- substring.start_with?('<')
96
+ parameters_type == :list
80
97
  end
81
98
 
82
99
  # @return [Boolean]
83
100
  def fixed_parameters?
84
- substring.start_with?('(')
101
+ parameters_type == :fixed
85
102
  end
86
103
 
87
104
  # @return [Boolean]
88
105
  def hash_parameters?
89
- substring.start_with?('{')
106
+ parameters_type == :hash
90
107
  end
91
108
 
92
109
  # @return [Array<ComplexType>]
@@ -121,6 +138,33 @@ module Solargraph
121
138
  "::#{name}"
122
139
  end
123
140
 
141
+ # @return [String]
142
+ def substring
143
+ @substring ||= generate_substring_from(&:tags)
144
+ end
145
+
146
+ # @return [String]
147
+ def rooted_substring
148
+ @rooted_substring = generate_substring_from(&:rooted_tags)
149
+ end
150
+
151
+ # @return [String]
152
+ def generate_substring_from(&to_str)
153
+ key_types_str = key_types.map(&to_str).join(', ')
154
+ subtypes_str = subtypes.map(&to_str).join(', ')
155
+ if key_types.none?(&:defined?) && subtypes.none?(&:defined?)
156
+ ''
157
+ elsif key_types.empty? && subtypes.empty?
158
+ ''
159
+ elsif hash_parameters?
160
+ "{#{key_types_str} => #{subtypes_str}}"
161
+ elsif fixed_parameters?
162
+ "(#{subtypes_str})"
163
+ else
164
+ "<#{subtypes_str}>"
165
+ end
166
+ end
167
+
124
168
  # @return [::Symbol] :class or :instance
125
169
  def scope
126
170
  @scope ||= :instance if duck_type? || nil_type?
@@ -143,28 +187,16 @@ module Solargraph
143
187
  # @param context [String] The namespace from which to resolve names
144
188
  # @return [self, ComplexType, UniqueType] The generated ComplexType
145
189
  def qualify api_map, context = ''
146
- return self if name == GENERIC_TAG_NAME
147
- return ComplexType.new([self]) if duck_type? || void? || undefined?
148
- recon = (rooted? ? '' : context)
149
- fqns = api_map.qualify(name, recon)
150
- if fqns.nil?
151
- return UniqueType::BOOLEAN if tag == 'Boolean'
152
- return UniqueType::UNDEFINED
153
- end
154
- fqns = "::#{fqns}" # Ensure the resulting complex type is rooted
155
- all_ltypes = key_types.map { |t| t.qualify api_map, context }.uniq
156
- all_rtypes = value_types.map { |t| t.qualify api_map, context }
157
- if list_parameters?
158
- rtypes = all_rtypes.uniq
159
- Solargraph::ComplexType.parse("#{fqns}<#{rtypes.map(&:tag).join(', ')}>")
160
- elsif fixed_parameters?
161
- Solargraph::ComplexType.parse("#{fqns}(#{all_rtypes.map(&:tag).join(', ')})")
162
- elsif hash_parameters?
163
- ltypes = all_ltypes.uniq
164
- rtypes = all_rtypes.uniq
165
- Solargraph::ComplexType.parse("#{fqns}{#{ltypes.map(&:tag).join(', ')} => #{rtypes.map(&:tag).join(', ')}}")
166
- else
167
- Solargraph::ComplexType.parse(fqns)
190
+ transform do |t|
191
+ next t if t.name == GENERIC_TAG_NAME
192
+ next t if t.duck_type? || t.void? || t.undefined?
193
+ recon = (t.rooted? ? '' : context)
194
+ fqns = api_map.qualify(t.name, recon)
195
+ if fqns.nil?
196
+ next UniqueType::BOOLEAN if t.tag == 'Boolean'
197
+ next UniqueType::UNDEFINED
198
+ end
199
+ t.recreate(new_name: fqns, make_rooted: true)
168
200
  end
169
201
  end
170
202