solargraph 0.14.2 → 0.14.3
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/lib/solargraph.rb +0 -1
- data/lib/solargraph/api_map.rb +168 -123
- data/lib/solargraph/api_map/config.rb +41 -26
- data/lib/solargraph/api_map/source.rb +48 -31
- data/lib/solargraph/code_map.rb +22 -19
- data/lib/solargraph/live_map.rb +2 -1
- data/lib/solargraph/pin.rb +11 -10
- data/lib/solargraph/pin/base_variable.rb +4 -0
- data/lib/solargraph/pin/namespace.rb +23 -0
- data/lib/solargraph/plugin/process.rb +7 -5
- data/lib/solargraph/server.rb +57 -33
- data/lib/solargraph/shell.rb +4 -2
- data/lib/solargraph/suggestion.rb +1 -1
- data/lib/solargraph/version.rb +1 -1
- data/lib/solargraph/yard_map.rb +8 -5
- metadata +3 -17
- data/lib/solargraph/yard_methods.rb +0 -56
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 9b19cc5d128d5ad59344c60240530466594888a3
|
4
|
+
data.tar.gz: db5e6a4c0f05e070c1b14d1c22d6ae32f1ac61e6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 12d90c3ac837e6a3669e91dbdcc3101edfac58010f1dde7471caf7f6808529c64fbfcb31cf28859e6f11d52b91040cbd4929124295016e999a03627f6e2295af
|
7
|
+
data.tar.gz: 3fe26bbd2699603487702b765734ae63df345d4afced95b1139e7bafdb2eef419fcd19e1778268b91b84193ea30da0b96ef609aabcb95a26abce46545f8e4e34
|
data/lib/solargraph.rb
CHANGED
@@ -11,7 +11,6 @@ module Solargraph
|
|
11
11
|
autoload :Snippets, 'solargraph/snippets'
|
12
12
|
autoload :Server, 'solargraph/server'
|
13
13
|
autoload :YardMap, 'solargraph/yard_map'
|
14
|
-
autoload :YardMethods, 'solargraph/yard_methods'
|
15
14
|
autoload :Pin, 'solargraph/pin'
|
16
15
|
autoload :LiveMap, 'solargraph/live_map'
|
17
16
|
autoload :ServerMethods, 'solargraph/server_methods'
|
data/lib/solargraph/api_map.rb
CHANGED
@@ -23,7 +23,6 @@ module Solargraph
|
|
23
23
|
].freeze
|
24
24
|
|
25
25
|
include NodeMethods
|
26
|
-
include YardMethods
|
27
26
|
|
28
27
|
# The root directory of the project. The ApiMap will search here for
|
29
28
|
# additional files to parse and analyze.
|
@@ -35,20 +34,14 @@ module Solargraph
|
|
35
34
|
def initialize workspace = nil
|
36
35
|
@workspace = workspace.gsub(/\\/, '/') unless workspace.nil?
|
37
36
|
clear
|
38
|
-
# @todo Instead of requiring extensions to be listed in the config,
|
39
|
-
# we're experimenting with automatically loading them.
|
40
|
-
#self.config.extensions.each do |ext|
|
41
|
-
# require ext
|
42
|
-
#end
|
43
37
|
require_extensions
|
44
|
-
@workspace_files = []
|
45
38
|
unless @workspace.nil?
|
46
|
-
|
47
|
-
|
39
|
+
workspace_files.concat (self.config.included - self.config.excluded)
|
40
|
+
workspace_files.each do |wf|
|
48
41
|
begin
|
49
42
|
@@source_cache[wf] ||= Source.load(wf)
|
50
|
-
rescue
|
51
|
-
STDERR.puts "Failed to load #{wf}"
|
43
|
+
rescue Exception => e
|
44
|
+
STDERR.puts "Failed to load #{wf}: #{e.message}"
|
52
45
|
end
|
53
46
|
end
|
54
47
|
end
|
@@ -60,10 +53,21 @@ module Solargraph
|
|
60
53
|
yard_map
|
61
54
|
end
|
62
55
|
|
63
|
-
|
64
|
-
|
56
|
+
# @return [Solargraph::ApiMap::Config]
|
57
|
+
def config reload = false
|
58
|
+
@config = ApiMap::Config.new(@workspace) if @config.nil? or reload
|
59
|
+
@config
|
65
60
|
end
|
66
61
|
|
62
|
+
# An array of all workspace files included in the map.
|
63
|
+
#
|
64
|
+
# @return[Array<String>]
|
65
|
+
def workspace_files
|
66
|
+
@workspace_files ||= []
|
67
|
+
end
|
68
|
+
|
69
|
+
# An array of required paths in the workspace.
|
70
|
+
#
|
67
71
|
# @return [Array<String>]
|
68
72
|
def required
|
69
73
|
@required ||= []
|
@@ -83,16 +87,36 @@ module Solargraph
|
|
83
87
|
@live_map ||= Solargraph::LiveMap.new(self)
|
84
88
|
end
|
85
89
|
|
90
|
+
# @todo Get rid of the cursor parameter. Tracking stubbed lines is the
|
91
|
+
# better option.
|
92
|
+
#
|
93
|
+
# @param code [String]
|
94
|
+
# @param filename [String]
|
86
95
|
# @return [Solargraph::ApiMap::Source]
|
87
96
|
def virtualize code, filename = nil, cursor = nil
|
88
|
-
|
89
|
-
|
97
|
+
workspace_files.delete_if do |f|
|
98
|
+
if File.exist?(f)
|
99
|
+
false
|
100
|
+
else
|
101
|
+
eliminate f
|
102
|
+
true
|
103
|
+
end
|
104
|
+
end
|
105
|
+
if filename.nil? or filename.end_with?('.rb')
|
106
|
+
eliminate @virtual_filename unless @virtual_source.nil? or @virtual_filename == filename or workspace_files.include?(@virtual_filename)
|
107
|
+
@virtual_filename = filename
|
108
|
+
@virtual_source = Source.fix(code, filename, cursor)
|
109
|
+
unless filename.nil? or workspace_files.include?(filename)
|
110
|
+
current_files = @workspace_files
|
111
|
+
@workspace_files = config(true).calculated
|
112
|
+
(current_files - @workspace_files).each { |f| eliminate f }
|
113
|
+
end
|
114
|
+
process_virtual
|
115
|
+
else
|
116
|
+
unless filename.nil?
|
117
|
+
# @todo Handle special files like .solargraph.yml
|
118
|
+
end
|
90
119
|
end
|
91
|
-
#refresh
|
92
|
-
@virtual_filename = filename
|
93
|
-
@virtual_source = Source.fix(code, filename, cursor)
|
94
|
-
process_virtual
|
95
|
-
#@stale = true
|
96
120
|
@virtual_source
|
97
121
|
end
|
98
122
|
|
@@ -109,12 +133,17 @@ module Solargraph
|
|
109
133
|
#
|
110
134
|
# @param node [AST::Node]
|
111
135
|
# @return [YARD::Docstring]
|
112
|
-
def
|
136
|
+
def get_docstring_for node
|
113
137
|
filename = get_filename_for(node)
|
114
138
|
return nil if @sources[filename].nil?
|
115
139
|
@sources[filename].docstring_for(node)
|
116
140
|
end
|
117
141
|
|
142
|
+
# @deprecated Use get_docstring_for instead.
|
143
|
+
def get_comment_for node
|
144
|
+
get_docstring_for node
|
145
|
+
end
|
146
|
+
|
118
147
|
# @return [Array<Solargraph::Suggestion>]
|
119
148
|
def self.get_keywords
|
120
149
|
@keyword_suggestions ||= KEYWORDS.map{ |s|
|
@@ -122,6 +151,7 @@ module Solargraph
|
|
122
151
|
}.freeze
|
123
152
|
end
|
124
153
|
|
154
|
+
# @return [Array<String>]
|
125
155
|
def namespaces
|
126
156
|
refresh
|
127
157
|
namespace_map.keys
|
@@ -131,14 +161,9 @@ module Solargraph
|
|
131
161
|
!find_fully_qualified_namespace(name, root).nil?
|
132
162
|
end
|
133
163
|
|
164
|
+
# @deprecated Use get_constants instead.
|
134
165
|
def namespaces_in name, root = ''
|
135
|
-
|
136
|
-
result = []
|
137
|
-
result += inner_namespaces_in(name, root, [])
|
138
|
-
result += yard_map.get_constants name, root
|
139
|
-
strings = result.map(&:to_s)
|
140
|
-
result.concat live_map.get_constants(name, root)
|
141
|
-
result
|
166
|
+
get_constants name, root
|
142
167
|
end
|
143
168
|
|
144
169
|
# @return [Array<Solargraph::Pin::Constant>]
|
@@ -148,16 +173,32 @@ module Solargraph
|
|
148
173
|
end
|
149
174
|
|
150
175
|
# @return [Array<Solargraph::Suggestion>]
|
151
|
-
def get_constants namespace, root
|
176
|
+
def get_constants namespace, root = ''
|
152
177
|
result = []
|
178
|
+
skip = []
|
153
179
|
fqns = find_fully_qualified_namespace(namespace, root)
|
154
|
-
|
155
|
-
|
156
|
-
|
157
|
-
|
180
|
+
if fqns.empty?
|
181
|
+
result.concat inner_get_constants('', skip, false)
|
182
|
+
else
|
183
|
+
parts = fqns.split('::')
|
184
|
+
resolved = find_namespace_pins(parts.join('::'))
|
185
|
+
resolved.each do |pin|
|
186
|
+
result.concat inner_get_constants(pin.path, skip, true)
|
158
187
|
end
|
159
188
|
end
|
160
189
|
result.concat yard_map.get_constants(fqns)
|
190
|
+
result
|
191
|
+
end
|
192
|
+
|
193
|
+
def find_namespace_pins fqns
|
194
|
+
set = nil
|
195
|
+
if fqns.include?('::')
|
196
|
+
set = @namespace_pins[fqns.split('::')[0..-2].join('::')]
|
197
|
+
else
|
198
|
+
set = @namespace_pins['']
|
199
|
+
end
|
200
|
+
return [] if set.nil?
|
201
|
+
set.select{|p| p.path == fqns}
|
161
202
|
end
|
162
203
|
|
163
204
|
# @return [String]
|
@@ -218,9 +259,7 @@ module Solargraph
|
|
218
259
|
result = []
|
219
260
|
ip = @ivar_pins[namespace]
|
220
261
|
unless ip.nil?
|
221
|
-
ip.select{ |pin| pin.scope == scope }
|
222
|
-
result.push pin_to_suggestion(pin)
|
223
|
-
end
|
262
|
+
result.concat suggest_unique_variables(ip.select{ |pin| pin.scope == scope })
|
224
263
|
end
|
225
264
|
result
|
226
265
|
end
|
@@ -235,11 +274,9 @@ module Solargraph
|
|
235
274
|
def get_class_variables(namespace)
|
236
275
|
refresh
|
237
276
|
result = []
|
238
|
-
|
239
|
-
unless
|
240
|
-
|
241
|
-
result.push pin_to_suggestion(pin)
|
242
|
-
end
|
277
|
+
cp = @cvar_pins[namespace]
|
278
|
+
unless cp.nil?
|
279
|
+
result.concat suggest_unique_variables(cp)
|
243
280
|
end
|
244
281
|
result
|
245
282
|
end
|
@@ -258,6 +295,14 @@ module Solargraph
|
|
258
295
|
nil
|
259
296
|
end
|
260
297
|
|
298
|
+
# @return [Solargraph::ApiMap::Source]
|
299
|
+
def get_source_for(node)
|
300
|
+
@sources.each do |filename, source|
|
301
|
+
return source if source.include?(node)
|
302
|
+
end
|
303
|
+
nil
|
304
|
+
end
|
305
|
+
|
261
306
|
# @return [String]
|
262
307
|
def infer_instance_variable(var, namespace, scope)
|
263
308
|
refresh
|
@@ -281,20 +326,18 @@ module Solargraph
|
|
281
326
|
|
282
327
|
# @return [Array<Solargraph::Suggestion>]
|
283
328
|
def get_global_variables
|
284
|
-
|
329
|
+
globals = []
|
285
330
|
@sources.values.each do |s|
|
286
|
-
s.global_variable_pins
|
287
|
-
result.push pin_to_suggestion(p)
|
288
|
-
end
|
331
|
+
globals.concat s.global_variable_pins
|
289
332
|
end
|
290
|
-
|
333
|
+
suggest_unique_variables globals
|
291
334
|
end
|
292
335
|
|
293
336
|
# @return [String]
|
294
337
|
def infer_assignment_node_type node, namespace
|
295
338
|
type = cache.get_assignment_node_type(node, namespace)
|
296
339
|
if type.nil?
|
297
|
-
cmnt =
|
340
|
+
cmnt = get_docstring_for(node)
|
298
341
|
if cmnt.nil?
|
299
342
|
name_i = (node.type == :casgn ? 1 : 0)
|
300
343
|
sig_i = (node.type == :casgn ? 2 : 1)
|
@@ -321,6 +364,7 @@ module Solargraph
|
|
321
364
|
|
322
365
|
# @return [String]
|
323
366
|
def infer_signature_type signature, namespace, scope: :class
|
367
|
+
namespace ||= ''
|
324
368
|
if cache.has_signature_type?(signature, namespace, scope)
|
325
369
|
return cache.get_signature_type(signature, namespace, scope)
|
326
370
|
end
|
@@ -453,13 +497,14 @@ module Solargraph
|
|
453
497
|
meths
|
454
498
|
end
|
455
499
|
|
500
|
+
# @return [Array<String>]
|
456
501
|
def get_include_strings_from *nodes
|
457
502
|
arr = []
|
458
503
|
nodes.each { |node|
|
459
504
|
next unless node.kind_of?(AST::Node)
|
460
505
|
arr.push unpack_name(node.children[2]) if (node.type == :send and node.children[1] == :include)
|
461
506
|
node.children.each { |n|
|
462
|
-
arr += get_include_strings_from(n) if n.kind_of?(AST::Node) and n.type != :class and n.type != :module
|
507
|
+
arr += get_include_strings_from(n) if n.kind_of?(AST::Node) and n.type != :class and n.type != :module and n.type != :sclass
|
463
508
|
}
|
464
509
|
}
|
465
510
|
arr
|
@@ -467,16 +512,27 @@ module Solargraph
|
|
467
512
|
|
468
513
|
def update filename
|
469
514
|
filename.gsub!(/\\/, '/')
|
470
|
-
|
471
|
-
|
472
|
-
|
473
|
-
|
515
|
+
if filename.end_with?('.rb')
|
516
|
+
if @workspace_files.include?(filename)
|
517
|
+
eliminate filename
|
518
|
+
@@source_cache[filename] = Source.load(filename)
|
519
|
+
rebuild_local_yardoc #if @workspace_files.include?(filename)
|
520
|
+
@stale = true
|
521
|
+
else
|
522
|
+
@workspace_files = config(true).calculated
|
523
|
+
update filename if @workspace_files.include?(filename)
|
524
|
+
end
|
525
|
+
elsif File.basename(filename) == '.solargraph.yml'
|
526
|
+
# @todo Finish refreshing the map
|
527
|
+
@workspace_files = config(true).calculated
|
528
|
+
end
|
474
529
|
end
|
475
530
|
|
476
531
|
def sources
|
477
532
|
@sources.values
|
478
533
|
end
|
479
534
|
|
535
|
+
# @return [Array<String>]
|
480
536
|
def get_path_suggestions path
|
481
537
|
refresh
|
482
538
|
result = []
|
@@ -490,9 +546,10 @@ module Solargraph
|
|
490
546
|
result = get_methods(parts[0], '', visibility: [:public, :private, :protected]).select{|s| s.label == parts[1]}
|
491
547
|
else
|
492
548
|
# It's a class or module
|
493
|
-
|
494
|
-
|
495
|
-
|
549
|
+
parts = path.split('::')
|
550
|
+
np = @namespace_pins[parts[0..-2].join('::')]
|
551
|
+
unless np.nil?
|
552
|
+
result.concat np.select{|p| p.name == parts.last}.map{|p| pin_to_suggestion(p)}
|
496
553
|
end
|
497
554
|
result.concat yard_map.objects(path)
|
498
555
|
end
|
@@ -506,17 +563,10 @@ module Solargraph
|
|
506
563
|
@namespace_map ||= {}
|
507
564
|
end
|
508
565
|
|
509
|
-
# @return [Hash]
|
510
|
-
def namespace_tree
|
511
|
-
@namespace_tree ||= {}
|
512
|
-
end
|
513
|
-
|
514
566
|
def clear
|
515
567
|
@stale = false
|
516
|
-
@parent_stack = {}
|
517
568
|
namespace_map.clear
|
518
|
-
|
519
|
-
required.clear
|
569
|
+
@required = config.required.clone
|
520
570
|
end
|
521
571
|
|
522
572
|
def process_maps
|
@@ -530,10 +580,9 @@ module Solargraph
|
|
530
580
|
@attr_pins = {}
|
531
581
|
@namespace_includes = {}
|
532
582
|
@superclasses = {}
|
533
|
-
@
|
583
|
+
@namespace_pins = {}
|
534
584
|
namespace_map.clear
|
535
|
-
|
536
|
-
@required = []
|
585
|
+
@required = config.required.clone
|
537
586
|
@pin_suggestions = {}
|
538
587
|
unless @virtual_source.nil?
|
539
588
|
@sources[@virtual_filename] = @virtual_source
|
@@ -542,7 +591,6 @@ module Solargraph
|
|
542
591
|
s.namespace_nodes.each_pair do |k, v|
|
543
592
|
namespace_map[k] ||= []
|
544
593
|
namespace_map[k].concat v
|
545
|
-
add_to_namespace_tree k.split('::')
|
546
594
|
end
|
547
595
|
end
|
548
596
|
@sources.values.each { |s|
|
@@ -561,13 +609,13 @@ module Solargraph
|
|
561
609
|
|
562
610
|
def process_workspace_files
|
563
611
|
@sources.clear
|
564
|
-
|
612
|
+
workspace_files.each do |f|
|
565
613
|
if File.file?(f)
|
566
614
|
begin
|
567
615
|
@@source_cache[f] ||= Source.load(f)
|
568
616
|
@sources[f] = @@source_cache[f]
|
569
|
-
rescue
|
570
|
-
STDERR.puts "Failed to load #{f}"
|
617
|
+
rescue Exception => e
|
618
|
+
STDERR.puts "Failed to load #{f}: #{e.message}"
|
571
619
|
end
|
572
620
|
end
|
573
621
|
end
|
@@ -577,13 +625,11 @@ module Solargraph
|
|
577
625
|
unless @virtual_source.nil?
|
578
626
|
cache.clear
|
579
627
|
namespace_map.clear
|
580
|
-
namespace_tree.clear
|
581
628
|
@sources[@virtual_filename] = @virtual_source
|
582
629
|
@sources.values.each do |s|
|
583
630
|
s.namespace_nodes.each_pair do |k, v|
|
584
631
|
namespace_map[k] ||= []
|
585
632
|
namespace_map[k].concat v
|
586
|
-
add_to_namespace_tree k.split('::')
|
587
633
|
end
|
588
634
|
end
|
589
635
|
eliminate @virtual_filename
|
@@ -592,7 +638,7 @@ module Solargraph
|
|
592
638
|
end
|
593
639
|
|
594
640
|
def eliminate filename
|
595
|
-
[@ivar_pins.values, @cvar_pins.values, @const_pins.values, @method_pins.values, @attr_pins.values].each do |pinsets|
|
641
|
+
[@ivar_pins.values, @cvar_pins.values, @const_pins.values, @method_pins.values, @attr_pins.values, @namespace_pins.values].each do |pinsets|
|
596
642
|
pinsets.each do |pins|
|
597
643
|
pins.delete_if{|pin| pin.filename == filename}
|
598
644
|
end
|
@@ -632,6 +678,10 @@ module Solargraph
|
|
632
678
|
source.superclasses.each_pair do |cls, sup|
|
633
679
|
@superclasses[cls] = sup
|
634
680
|
end
|
681
|
+
source.namespace_pins.each do |pin|
|
682
|
+
@namespace_pins[pin.namespace] ||= []
|
683
|
+
@namespace_pins[pin.namespace].push pin
|
684
|
+
end
|
635
685
|
source.required.each do |r|
|
636
686
|
required.push r
|
637
687
|
end
|
@@ -707,50 +757,6 @@ module Solargraph
|
|
707
757
|
meths.uniq
|
708
758
|
end
|
709
759
|
|
710
|
-
def inner_namespaces_in name, root, skip
|
711
|
-
result = []
|
712
|
-
fqns = find_fully_qualified_namespace(name, root)
|
713
|
-
unless fqns.nil? or skip.include?(fqns)
|
714
|
-
skip.push fqns
|
715
|
-
nodes = get_namespace_nodes(fqns)
|
716
|
-
unless nodes.empty?
|
717
|
-
cursor = namespace_tree
|
718
|
-
parts = fqns.split('::')
|
719
|
-
parts.each { |p|
|
720
|
-
cursor = cursor[p]
|
721
|
-
}
|
722
|
-
unless cursor.nil?
|
723
|
-
cursor.keys.each { |k|
|
724
|
-
type = get_namespace_type("#{fqns == '' ? '' : fqns + '::'}#{k}")
|
725
|
-
kind = nil
|
726
|
-
detail = nil
|
727
|
-
if type == :class
|
728
|
-
kind = Suggestion::CLASS
|
729
|
-
detail = 'Class'
|
730
|
-
elsif type == :module
|
731
|
-
kind = Suggestion::MODULE
|
732
|
-
detail = 'Module'
|
733
|
-
end
|
734
|
-
result.push Suggestion.new(k, kind: kind, detail: detail)
|
735
|
-
}
|
736
|
-
cp = @const_pins[fqns]
|
737
|
-
unless cp.nil?
|
738
|
-
cp.each do |pin|
|
739
|
-
result.push pin_to_suggestion(pin)
|
740
|
-
end
|
741
|
-
end
|
742
|
-
inc = @namespace_includes[fqns]
|
743
|
-
unless inc.nil?
|
744
|
-
inc.each do |i|
|
745
|
-
result.concat inner_namespaces_in(i, fqns, skip)
|
746
|
-
end
|
747
|
-
end
|
748
|
-
end
|
749
|
-
end
|
750
|
-
end
|
751
|
-
result
|
752
|
-
end
|
753
|
-
|
754
760
|
# Get a fully qualified namespace for the given signature.
|
755
761
|
# The signature should be in the form of a method chain, e.g.,
|
756
762
|
# method1.method2
|
@@ -804,12 +810,31 @@ module Solargraph
|
|
804
810
|
type
|
805
811
|
end
|
806
812
|
|
807
|
-
def
|
808
|
-
|
809
|
-
|
810
|
-
|
811
|
-
|
812
|
-
|
813
|
+
def inner_get_constants here, skip = [], deep = true
|
814
|
+
return [] if skip.include?(here)
|
815
|
+
skip.push here
|
816
|
+
result = []
|
817
|
+
cp = @const_pins[here]
|
818
|
+
unless cp.nil?
|
819
|
+
cp.each do |pin|
|
820
|
+
result.push pin_to_suggestion(pin)
|
821
|
+
end
|
822
|
+
end
|
823
|
+
np = @namespace_pins[here]
|
824
|
+
unless np.nil?
|
825
|
+
np.each do |pin|
|
826
|
+
result.push pin_to_suggestion(pin)
|
827
|
+
if deep
|
828
|
+
get_include_strings_from(pin.node).each do |i|
|
829
|
+
result.concat inner_get_constants(i, skip, false)
|
830
|
+
end
|
831
|
+
end
|
832
|
+
end
|
833
|
+
end
|
834
|
+
get_include_strings_from(*get_namespace_nodes(here)).each do |i|
|
835
|
+
result.concat inner_get_constants(i, skip, false)
|
836
|
+
end
|
837
|
+
result
|
813
838
|
end
|
814
839
|
|
815
840
|
def file_nodes
|
@@ -837,5 +862,25 @@ module Solargraph
|
|
837
862
|
require n.match(/^(solargraph\-[a-z0-9_\-]*?\-ext)\-[0-9\.]*$/)[1]
|
838
863
|
end
|
839
864
|
end
|
865
|
+
|
866
|
+
def suggest_unique_variables pins
|
867
|
+
result = []
|
868
|
+
nil_pins = []
|
869
|
+
val_names = []
|
870
|
+
pins.each do |pin|
|
871
|
+
if pin.nil_assignment? and pin.return_type.nil?
|
872
|
+
nil_pins.push pin
|
873
|
+
else
|
874
|
+
unless val_names.include?(pin.name)
|
875
|
+
result.push pin_to_suggestion(pin)
|
876
|
+
val_names.push pin.name
|
877
|
+
end
|
878
|
+
end
|
879
|
+
end
|
880
|
+
nil_pins.reject{|p| val_names.include?(p.name)}.each do |pin|
|
881
|
+
result.push pin_to_suggestion(pin)
|
882
|
+
end
|
883
|
+
result
|
884
|
+
end
|
840
885
|
end
|
841
886
|
end
|