Class: Solargraph::ComplexType::UniqueType
- Inherits:
-
Object
- Object
- Solargraph::ComplexType::UniqueType
show all
- Includes:
- TypeMethods
- Defined in:
- lib/solargraph/complex_type/unique_type.rb
Overview
An individual type signature. A complex type can consist of multiple unique types.
Constant Summary
collapse
- UNDEFINED =
UniqueType.new('undefined')
- BOOLEAN =
UniqueType.new('Boolean')
Instance Attribute Summary collapse
Attributes included from TypeMethods
#name, #substring, #tag
Instance Method Summary
collapse
-
#generic? ⇒ Boolean
-
#initialize(name, substring = '') ⇒ UniqueType
constructor
Create a UniqueType with the specified name and an optional substring.
-
#items ⇒ Array<UniqueType>
-
#map {|t| ... } ⇒ Array<self>
-
#parameters_as_rbs ⇒ String
-
#rbs_name ⇒ String
-
#recreate(new_name: nil, new_key_types: nil, new_subtypes: nil) ⇒ self
-
#resolve_generics(definitions, context_type) ⇒ UniqueType, ComplexType
Probe the concrete type for each of the generic type parameters used in this type, and return a new type if possible.
-
#resolve_generics_from_context(generics_to_resolve, context_type, resolved_generic_values: {}) ⇒ UniqueType, ComplexType
-
#resolve_param_generics_from_context(generics_to_resolve, context_type, resolved_generic_values) ⇒ Array<ComplexType>
-
#self_to(dst) ⇒ UniqueType
Transform references to the ‘self’ type to the specified concrete namespace.
-
#selfy? ⇒ Boolean
-
#to_a ⇒ Array<UniqueType>
-
#to_rbs ⇒ String
-
#to_s ⇒ Object
-
#transform(new_name = nil) {|t| ... } ⇒ self
Apply the given transformation to each subtype and then finally to this type.
#==, #defined?, #duck_type?, #each_unique_type, #erase_generics, #fixed_parameters?, #hash_parameters?, #list_parameters?, #namespace, #nil_type?, #parameters?, #qualify, #rooted?, #rooted_name, #rooted_namespace, #scope, #undefined?, #value_types, #void?
Constructor Details
#initialize(name, substring = '') ⇒ UniqueType
Create a UniqueType with the specified name and an optional substring. The substring is the parameter section of a parametrized type, e.g., for the type ‘Array<String>`, the name is `Array` and the substring is `<String>`.
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 20
def initialize name, substring = ''
if name.start_with?('::')
@name = name[2..-1]
@rooted = true
else
@name = name
@rooted = false
end
@substring = substring
@tag = @name + substring
@key_types = []
@subtypes = []
@all_params = []
return unless parameters?
subs = if @substring.start_with?('<(') && @substring.end_with?(')>')
ComplexType.parse(substring[2..-3], partial: true)
else
ComplexType.parse(substring[1..-2], partial: true)
end
if hash_parameters?
raise ComplexTypeError, "Bad hash type" unless !subs.is_a?(ComplexType) and subs.length == 2 and !subs[0].is_a?(UniqueType) and !subs[1].is_a?(UniqueType)
@key_types.concat subs[0].map { |u| ComplexType.new([u]) }
@subtypes.concat subs[1].map { |u| ComplexType.new([u]) }
else
@subtypes.concat subs
end
@all_params.concat @key_types
@all_params.concat @subtypes
end
|
Instance Attribute Details
#all_params ⇒ Object
Returns the value of attribute all_params.
11
12
13
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 11
def all_params
@all_params
end
|
#key_types ⇒ Object
Returns the value of attribute key_types.
11
12
13
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 11
def key_types
@key_types
end
|
#subtypes ⇒ Object
Returns the value of attribute subtypes.
11
12
13
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 11
def subtypes
@subtypes
end
|
Instance Method Details
#generic? ⇒ Boolean
98
99
100
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 98
def generic?
name == GENERIC_TAG_NAME || all_params.any?(&:generic?)
end
|
64
65
66
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 64
def items
[self]
end
|
#map {|t| ... } ⇒ Array<self>
175
176
177
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 175
def map &block
[block.yield(self)]
end
|
#parameters_as_rbs ⇒ String
94
95
96
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 94
def parameters_as_rbs
parameters? ? "[#{all_params.map { |s| s.to_rbs }.join(', ')}]" : ''
end
|
#rbs_name ⇒ String
69
70
71
72
73
74
75
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 69
def rbs_name
if name == 'undefined'
'untyped'
else
rooted_name
end
end
|
#recreate(new_name: nil, new_key_types: nil, new_subtypes: nil) ⇒ self
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 188
def recreate(new_name: nil, new_key_types: nil, new_subtypes: nil)
new_name ||= name
new_key_types ||= @key_types
new_subtypes ||= @subtypes
if new_key_types.none?(&:defined?) && new_subtypes.none?(&:defined?)
UniqueType.new(new_name)
elsif new_key_types.empty? && new_subtypes.empty?
UniqueType.new(new_name)
elsif hash_parameters?
UniqueType.new(new_name, "{#{new_key_types.join(', ')} => #{new_subtypes.join(', ')}}")
elsif @substring.start_with?('<(')
UniqueType.new(new_name, "<(#{new_subtypes.join(', ')})>")
elsif fixed_parameters?
UniqueType.new(new_name, "(#{new_subtypes.join(', ')})")
else
UniqueType.new(new_name, "<#{new_subtypes.join(', ')}>")
end
end
|
#resolve_generics(definitions, context_type) ⇒ UniqueType, ComplexType
Probe the concrete type for each of the generic type parameters used in this type, and return a new type if possible.
158
159
160
161
162
163
164
165
166
167
168
169
170
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 158
def resolve_generics definitions, context_type
return self if definitions.nil? || definitions.generics.empty?
transform(name) do |t|
if t.name == GENERIC_TAG_NAME
idx = definitions.generics.index(t.subtypes.first&.name)
next t if idx.nil?
context_type.all_params[idx] || ComplexType::UNDEFINED
else
t
end
end
end
|
#resolve_generics_from_context(generics_to_resolve, context_type, resolved_generic_values: {}) ⇒ UniqueType, ComplexType
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 107
def resolve_generics_from_context generics_to_resolve, context_type, resolved_generic_values: {}
if name == ComplexType::GENERIC_TAG_NAME
type_param = subtypes.first&.name
return self unless generics_to_resolve.include? type_param
unless context_type.nil? || !resolved_generic_values[type_param].nil?
new_binding = true
resolved_generic_values[type_param] = context_type
end
if new_binding
resolved_generic_values.transform_values! do |complex_type|
complex_type.resolve_generics_from_context(generics_to_resolve, nil, resolved_generic_values: resolved_generic_values)
end
end
return resolved_generic_values[type_param] || self
end
new_key_types = resolve_param_generics_from_context(generics_to_resolve, context_type, resolved_generic_values, &:key_types)
new_subtypes = resolve_param_generics_from_context(generics_to_resolve, context_type, resolved_generic_values, &:subtypes)
recreate(new_key_types: new_key_types, new_subtypes: new_subtypes)
end
|
#resolve_param_generics_from_context(generics_to_resolve, context_type, resolved_generic_values) ⇒ Array<ComplexType>
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 134
def resolve_param_generics_from_context(generics_to_resolve, context_type, resolved_generic_values)
types = yield self
types.each_with_index.flat_map do |ct, i|
ct.items.flat_map do |ut|
context_params = yield context_type if context_type
if context_params && context_params[i]
type_arg = context_params[i]
type_arg.map do |new_unique_context_type|
ut.resolve_generics_from_context generics_to_resolve, new_unique_context_type, resolved_generic_values: resolved_generic_values
end
else
ut.resolve_generics_from_context generics_to_resolve, nil, resolved_generic_values: resolved_generic_values
end
end
end
end
|
Transform references to the ‘self’ type to the specified concrete namespace
237
238
239
240
241
242
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 237
def self_to dst
transform do |t|
next t if t.name != 'self'
t.recreate(new_name: dst, new_key_types: [], new_subtypes: [])
end
end
|
#selfy? ⇒ Boolean
244
245
246
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 244
def selfy?
@name == 'self' || @key_types.any?(&:selfy?) || @subtypes.any?(&:selfy?)
end
|
180
181
182
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 180
def to_a
[self]
end
|
#to_rbs ⇒ String
78
79
80
81
82
83
84
85
86
87
88
89
90
91
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 78
def to_rbs
if ['Tuple', 'Array'].include?(name) && fixed_parameters?
if substring == '()'
'Array[]'
else
parameters_as_rbs
end
else
"#{rbs_name}#{parameters_as_rbs}"
end
end
|
#to_s ⇒ Object
59
60
61
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 59
def to_s
tag
end
|
Apply the given transformation to each subtype and then finally to this type
227
228
229
230
231
232
|
# File 'lib/solargraph/complex_type/unique_type.rb', line 227
def transform(new_name = nil, &transform_type)
new_key_types = @key_types.flat_map { |ct| ct.map { |ut| ut.transform(&transform_type) } }.compact
new_subtypes = @subtypes.flat_map { |ct| ct.map { |ut| ut.transform(&transform_type) } }.compact
new_type = recreate(new_name: new_name || rooted_name, new_key_types: new_key_types, new_subtypes: new_subtypes)
yield new_type
end
|