solargraph 0.32.5 → 0.33.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.
- checksums.yaml +4 -4
- data/.gitignore +1 -0
- data/README.md +2 -11
- data/lib/solargraph.rb +1 -2
- data/lib/solargraph/api_map.rb +93 -63
- data/lib/solargraph/api_map/cache.rb +16 -1
- data/lib/solargraph/api_map/source_to_yard.rb +16 -7
- data/lib/solargraph/api_map/store.rb +55 -12
- data/lib/solargraph/complex_type.rb +58 -14
- data/lib/solargraph/complex_type/type_methods.rb +2 -2
- data/lib/solargraph/complex_type/unique_type.rb +33 -4
- data/lib/solargraph/core_fills.rb +40 -12
- data/lib/solargraph/diagnostics.rb +4 -3
- data/lib/solargraph/diagnostics/base.rb +6 -0
- data/lib/solargraph/diagnostics/require_not_found.rb +17 -10
- data/lib/solargraph/diagnostics/rubocop_helpers.rb +2 -0
- data/lib/solargraph/diagnostics/type_check.rb +51 -0
- data/lib/solargraph/diagnostics/update_errors.rb +1 -0
- data/lib/solargraph/language_server/host.rb +55 -25
- data/lib/solargraph/language_server/host/diagnoser.rb +1 -2
- data/lib/solargraph/language_server/host/dispatch.rb +4 -8
- data/lib/solargraph/language_server/host/sources.rb +1 -1
- data/lib/solargraph/language_server/message.rb +1 -0
- data/lib/solargraph/language_server/message/completion_item/resolve.rb +4 -2
- data/lib/solargraph/language_server/message/initialize.rb +9 -0
- data/lib/solargraph/language_server/message/initialized.rb +1 -0
- data/lib/solargraph/language_server/message/text_document.rb +1 -0
- data/lib/solargraph/language_server/message/text_document/code_action.rb +15 -0
- data/lib/solargraph/language_server/message/text_document/completion.rb +1 -1
- data/lib/solargraph/language_server/message/text_document/definition.rb +25 -5
- data/lib/solargraph/language_server/message/text_document/hover.rb +1 -1
- data/lib/solargraph/language_server/message/text_document/signature_help.rb +4 -0
- data/lib/solargraph/language_server/message/workspace/did_change_watched_files.rb +8 -4
- data/lib/solargraph/language_server/transport/adapter.rb +12 -15
- data/lib/solargraph/library.rb +23 -6
- data/lib/solargraph/location.rb +4 -0
- data/lib/solargraph/pin.rb +7 -3
- data/lib/solargraph/pin/attribute.rb +14 -13
- data/lib/solargraph/pin/base.rb +56 -43
- data/lib/solargraph/pin/base_method.rb +41 -18
- data/lib/solargraph/pin/base_variable.rb +17 -15
- data/lib/solargraph/pin/block.rb +22 -4
- data/lib/solargraph/pin/closure.rb +28 -0
- data/lib/solargraph/pin/common.rb +59 -0
- data/lib/solargraph/pin/constant.rb +4 -4
- data/lib/solargraph/pin/conversions.rb +8 -8
- data/lib/solargraph/pin/duck_method.rb +3 -3
- data/lib/solargraph/pin/instance_variable.rb +30 -0
- data/lib/solargraph/pin/keyword.rb +1 -1
- data/lib/solargraph/pin/local_variable.rb +3 -3
- data/lib/solargraph/pin/localized.rb +9 -5
- data/lib/solargraph/pin/method.rb +26 -40
- data/lib/solargraph/pin/method_alias.rb +9 -6
- data/lib/solargraph/pin/namespace.rb +33 -10
- data/lib/solargraph/pin/parameter.rb +150 -0
- data/lib/solargraph/pin/proxy_type.rb +8 -8
- data/lib/solargraph/pin/reference.rb +1 -12
- data/lib/solargraph/pin/reference/override.rb +18 -0
- data/lib/solargraph/pin/reference/require.rb +2 -1
- data/lib/solargraph/pin/singleton.rb +9 -0
- data/lib/solargraph/pin/symbol.rb +9 -4
- data/lib/solargraph/pin/yard_pin/constant.rb +12 -3
- data/lib/solargraph/pin/yard_pin/method.rb +18 -6
- data/lib/solargraph/pin/yard_pin/namespace.rb +13 -1
- data/lib/solargraph/position.rb +1 -1
- data/lib/solargraph/range.rb +4 -0
- data/lib/solargraph/shell.rb +83 -4
- data/lib/solargraph/source.rb +32 -12
- data/lib/solargraph/source/chain.rb +48 -28
- data/lib/solargraph/source/chain/call.rb +37 -38
- data/lib/solargraph/source/chain/constant.rb +1 -1
- data/lib/solargraph/source/chain/head.rb +2 -8
- data/lib/solargraph/source/chain/instance_variable.rb +1 -1
- data/lib/solargraph/source/chain/link.rb +2 -0
- data/lib/solargraph/source/cursor.rb +59 -24
- data/lib/solargraph/source/node_chainer.rb +0 -2
- data/lib/solargraph/source/node_methods.rb +12 -6
- data/lib/solargraph/source/source_chainer.rb +38 -44
- data/lib/solargraph/source_map.rb +11 -18
- data/lib/solargraph/source_map/clip.rb +13 -15
- data/lib/solargraph/source_map/mapper.rb +37 -26
- data/lib/solargraph/source_map/node_processor.rb +13 -8
- data/lib/solargraph/source_map/node_processor/alias_node.rb +8 -8
- data/lib/solargraph/source_map/node_processor/args_node.rb +10 -16
- data/lib/solargraph/source_map/node_processor/base.rb +47 -4
- data/lib/solargraph/source_map/node_processor/block_node.rb +9 -4
- data/lib/solargraph/source_map/node_processor/casgn_node.rb +7 -2
- data/lib/solargraph/source_map/node_processor/cvasgn_node.rb +8 -3
- data/lib/solargraph/source_map/node_processor/def_node.rb +45 -38
- data/lib/solargraph/source_map/node_processor/defs_node.rb +16 -6
- data/lib/solargraph/source_map/node_processor/gvasgn_node.rb +8 -1
- data/lib/solargraph/source_map/node_processor/ivasgn_node.rb +20 -6
- data/lib/solargraph/source_map/node_processor/lvasgn_node.rb +10 -4
- data/lib/solargraph/source_map/node_processor/namespace_node.rb +18 -12
- data/lib/solargraph/source_map/node_processor/orasgn_node.rb +1 -1
- data/lib/solargraph/source_map/node_processor/resbody_node.rb +30 -0
- data/lib/solargraph/source_map/node_processor/sclass_node.rb +7 -1
- data/lib/solargraph/source_map/node_processor/send_node.rb +102 -52
- data/lib/solargraph/source_map/node_processor/sym_node.rb +4 -1
- data/lib/solargraph/source_map/region.rb +9 -8
- data/lib/solargraph/type_checker.rb +282 -0
- data/lib/solargraph/type_checker/param_def.rb +47 -0
- data/lib/solargraph/type_checker/problem.rb +25 -0
- data/lib/solargraph/version.rb +1 -1
- data/lib/solargraph/views/environment.erb +1 -1
- data/lib/solargraph/workspace.rb +2 -2
- data/lib/solargraph/workspace/config.rb +0 -8
- data/lib/solargraph/yard_map.rb +25 -69
- data/lib/solargraph/yard_map/core_docs.rb +8 -3
- data/lib/solargraph/yard_map/core_gen.rb +1 -3
- data/lib/solargraph/yard_map/mapper.rb +85 -0
- data/lib/yard-solargraph.rb +2 -0
- metadata +14 -14
- data/lib/solargraph/diagnostics/type_not_defined.rb +0 -108
- data/lib/solargraph/live_map.rb +0 -126
- data/lib/solargraph/live_map/cache.rb +0 -38
- data/lib/solargraph/pin/block_parameter.rb +0 -103
- data/lib/solargraph/pin/method_parameter.rb +0 -40
- data/lib/solargraph/pin/plugin/method.rb +0 -25
- data/lib/solargraph/plugin.rb +0 -8
- data/lib/solargraph/plugin/base.rb +0 -41
- data/lib/solargraph/plugin/canceler.rb +0 -11
- data/lib/solargraph/plugin/process.rb +0 -172
- data/lib/solargraph/plugin/runtime.rb +0 -134
- data/lib/yard-coregen.rb +0 -16
data/lib/solargraph/live_map.rb
DELETED
@@ -1,126 +0,0 @@
|
|
1
|
-
module Solargraph
|
2
|
-
# The LiveMap allows extensions to add their own completion suggestions.
|
3
|
-
#
|
4
|
-
class LiveMap
|
5
|
-
autoload :Cache, 'solargraph/live_map/cache'
|
6
|
-
|
7
|
-
@@plugin_registry = {}
|
8
|
-
|
9
|
-
# @return [Solargraph::ApiMap]
|
10
|
-
attr_reader :api_map
|
11
|
-
|
12
|
-
# @param api_map [Solargraph::ApiMap]
|
13
|
-
def initialize api_map
|
14
|
-
@api_map = api_map
|
15
|
-
runners
|
16
|
-
end
|
17
|
-
|
18
|
-
def get_path_pin path
|
19
|
-
cache.get_path_pin(path)
|
20
|
-
end
|
21
|
-
|
22
|
-
# @return [Array<Solargraph::Pin::Base>]
|
23
|
-
def get_methods(namespace, root = '', scope = 'instance', with_private = false)
|
24
|
-
fqns = api_map.qualify(namespace, root)
|
25
|
-
params = {
|
26
|
-
namespace: namespace, root: root, scope: scope, with_private: with_private
|
27
|
-
}
|
28
|
-
cached = cache.get_methods(params)
|
29
|
-
return cached unless cached.nil?
|
30
|
-
did_runtime = false
|
31
|
-
result = []
|
32
|
-
runners.each do |p|
|
33
|
-
next if did_runtime and p.runtime?
|
34
|
-
p.get_methods(namespace: namespace, root: root, scope: scope, with_private: with_private).each do |m|
|
35
|
-
result.push Solargraph::Pin::Method.new(nil, namespace, m['name'], YARD::Docstring.new('(defined at runtime)'), scope.to_sym, nil, [])
|
36
|
-
end
|
37
|
-
did_runtime = true if p.runtime?
|
38
|
-
end
|
39
|
-
cache.set_methods(params, result)
|
40
|
-
result
|
41
|
-
end
|
42
|
-
|
43
|
-
# @return [Array<Solargraph::Pin::Base>]
|
44
|
-
def get_constants(namespace, root = '')
|
45
|
-
cached = cache.get_constants(namespace, root)
|
46
|
-
return cached unless cached.nil?
|
47
|
-
did_runtime = false
|
48
|
-
result = []
|
49
|
-
runners.each do |p|
|
50
|
-
next if did_runtime and p.runtime?
|
51
|
-
result.concat p.get_constants(namespace, root)
|
52
|
-
did_runtime = true if p.runtime?
|
53
|
-
end
|
54
|
-
suggestions = []
|
55
|
-
result.uniq.each do |r|
|
56
|
-
path = (r['namespace'].empty? ? '' : "#{r['namespace']}::") + r['name']
|
57
|
-
kind = Pin::CONSTANT
|
58
|
-
if r['class'] == 'Class'
|
59
|
-
suggestions.push Pin::Namespace.new(nil, r['namespace'], r['name'], YARD::Docstring.new("(defined at runtime)"), :class, :public, nil)
|
60
|
-
elsif r['class'] == 'Module'
|
61
|
-
suggestions.push Pin::Namespace.new(nil, r['namespace'], r['name'], YARD::Docstring.new("(defined at runtime)"), :module, :public, nil)
|
62
|
-
else
|
63
|
-
suggestions.push Pin::Constant.new(nil, r['namespace'], r['name'], YARD::Docstring.new("(defined at runtime"), nil, nil, nil, :public)
|
64
|
-
end
|
65
|
-
end
|
66
|
-
cache.set_constants(namespace, root, suggestions)
|
67
|
-
suggestions
|
68
|
-
end
|
69
|
-
|
70
|
-
def get_fqns(namespace, root)
|
71
|
-
did_runtime = false
|
72
|
-
runners.each do |p|
|
73
|
-
next if did_runtime and p.runtime?
|
74
|
-
result = p.get_fqns(namespace, root)
|
75
|
-
return result unless result.nil?
|
76
|
-
did_runtime = true if p.runtime?
|
77
|
-
end
|
78
|
-
nil
|
79
|
-
end
|
80
|
-
|
81
|
-
def self.register name, klass
|
82
|
-
raise ArgumentError.new("A Solargraph plugin named #{name} already exists") if @@plugin_registry.has_key?(name)
|
83
|
-
@@plugin_registry[name] = klass
|
84
|
-
end
|
85
|
-
|
86
|
-
def refresh
|
87
|
-
changed = false
|
88
|
-
runners.each do |p|
|
89
|
-
changed ||= p.refresh
|
90
|
-
end
|
91
|
-
if changed
|
92
|
-
Solargraph::Logging.logger.debug "Resetting LiveMap cache"
|
93
|
-
cache.clear
|
94
|
-
get_constants('')
|
95
|
-
get_methods('', '', 'class')
|
96
|
-
get_methods('', '', 'instance')
|
97
|
-
get_methods('Kernel', '', 'class')
|
98
|
-
get_methods('Kernel', '', 'instance')
|
99
|
-
end
|
100
|
-
end
|
101
|
-
|
102
|
-
private
|
103
|
-
|
104
|
-
# @return [Solargraph::LiveMap::Cache]
|
105
|
-
def cache
|
106
|
-
@cache ||= Solargraph::LiveMap::Cache.new
|
107
|
-
end
|
108
|
-
|
109
|
-
# @return [Array<Solargraph::Plugin::Base>]
|
110
|
-
def runners
|
111
|
-
@runners ||= load_runners
|
112
|
-
end
|
113
|
-
|
114
|
-
# @return [Array<Solargraph::Plugin::Base>]
|
115
|
-
def load_runners
|
116
|
-
result = []
|
117
|
-
api_map.workspace.config.plugins.each do |name|
|
118
|
-
r = @@plugin_registry[name].new(api_map)
|
119
|
-
result.push r
|
120
|
-
end
|
121
|
-
result
|
122
|
-
end
|
123
|
-
end
|
124
|
-
end
|
125
|
-
|
126
|
-
Solargraph::LiveMap.register 'runtime', Solargraph::Plugin::Runtime
|
@@ -1,38 +0,0 @@
|
|
1
|
-
module Solargraph
|
2
|
-
class LiveMap
|
3
|
-
class Cache
|
4
|
-
def initialize
|
5
|
-
@method_cache = {}
|
6
|
-
@constant_cache = {}
|
7
|
-
@path_cache = {}
|
8
|
-
end
|
9
|
-
|
10
|
-
def get_methods options
|
11
|
-
@method_cache[options]
|
12
|
-
end
|
13
|
-
|
14
|
-
def set_methods options, values
|
15
|
-
@method_cache[options] = values
|
16
|
-
values.each { |pin| @path_cache[pin.path] = pin }
|
17
|
-
end
|
18
|
-
|
19
|
-
def get_constants namespace, root
|
20
|
-
@constant_cache[[namespace, root]]
|
21
|
-
end
|
22
|
-
|
23
|
-
def set_constants namespace, root, values
|
24
|
-
@constant_cache[[namespace, root]] = values
|
25
|
-
end
|
26
|
-
|
27
|
-
def get_path_pin path
|
28
|
-
@path_cache[path]
|
29
|
-
end
|
30
|
-
|
31
|
-
def clear
|
32
|
-
@method_cache.clear
|
33
|
-
@constant_cache.clear
|
34
|
-
@path_cache.clear
|
35
|
-
end
|
36
|
-
end
|
37
|
-
end
|
38
|
-
end
|
@@ -1,103 +0,0 @@
|
|
1
|
-
module Solargraph
|
2
|
-
module Pin
|
3
|
-
class BlockParameter < Base
|
4
|
-
include Localized
|
5
|
-
|
6
|
-
# @return [Pin::Block]
|
7
|
-
attr_reader :block
|
8
|
-
|
9
|
-
def initialize location, namespace, name, comments, block
|
10
|
-
super(location, namespace, name, comments)
|
11
|
-
@block = block
|
12
|
-
@presence = block.location.range
|
13
|
-
end
|
14
|
-
|
15
|
-
# @return [Integer]
|
16
|
-
def kind
|
17
|
-
Pin::BLOCK_PARAMETER
|
18
|
-
end
|
19
|
-
|
20
|
-
# @return [Integer]
|
21
|
-
def completion_item_kind
|
22
|
-
Solargraph::LanguageServer::CompletionItemKinds::VARIABLE
|
23
|
-
end
|
24
|
-
|
25
|
-
# @return [Integer]
|
26
|
-
def symbol_kind
|
27
|
-
Solargraph::LanguageServer::SymbolKinds::VARIABLE
|
28
|
-
end
|
29
|
-
|
30
|
-
# The parameter's zero-based location in the block's signature.
|
31
|
-
#
|
32
|
-
# @return [Integer]
|
33
|
-
def index
|
34
|
-
block.parameters.index(self)
|
35
|
-
end
|
36
|
-
|
37
|
-
def nearly? other
|
38
|
-
return false unless super
|
39
|
-
block.nearly?(other.block)
|
40
|
-
end
|
41
|
-
|
42
|
-
def try_merge! other
|
43
|
-
return false unless super
|
44
|
-
@block = other.block
|
45
|
-
@presence = other.block.location.range
|
46
|
-
@return_complex_type = nil
|
47
|
-
true
|
48
|
-
end
|
49
|
-
|
50
|
-
# @return [Array<Solargraph::ComplexType>]
|
51
|
-
def return_complex_type
|
52
|
-
if @return_complex_type.nil?
|
53
|
-
@return_complex_type = ComplexType.new
|
54
|
-
found = nil
|
55
|
-
params = block.docstring.tags(:param)
|
56
|
-
params.each do |p|
|
57
|
-
next unless p.name == name
|
58
|
-
found = p
|
59
|
-
break
|
60
|
-
end
|
61
|
-
if found.nil? and !index.nil?
|
62
|
-
found = params[index] if params[index] && (params[index].name.nil? || params[index].name.empty?)
|
63
|
-
end
|
64
|
-
@return_complex_type = ComplexType.try_parse(*found.types) unless found.nil? or found.types.nil?
|
65
|
-
end
|
66
|
-
super
|
67
|
-
@return_complex_type
|
68
|
-
end
|
69
|
-
|
70
|
-
def context
|
71
|
-
block
|
72
|
-
end
|
73
|
-
|
74
|
-
# @param api_map [ApiMap]
|
75
|
-
def typify api_map
|
76
|
-
# @todo Does anything need to be eliminated because it's more accurately a probe?
|
77
|
-
type = super
|
78
|
-
return type unless type.undefined?
|
79
|
-
chain = Source::NodeChainer.chain(block.receiver, filename)
|
80
|
-
clip = api_map.clip_at(location.filename, location.range.start)
|
81
|
-
locals = clip.locals - [self]
|
82
|
-
meths = chain.define(api_map, block, locals)
|
83
|
-
meths.each do |meth|
|
84
|
-
if (Solargraph::CoreFills::METHODS_WITH_YIELDPARAM_SUBTYPES.include?(meth.path))
|
85
|
-
bmeth = chain.base.define(api_map, context, locals).first
|
86
|
-
return ComplexType::UNDEFINED if bmeth.nil? or bmeth.return_complex_type.undefined? or bmeth.return_complex_type.subtypes.empty?
|
87
|
-
return bmeth.return_complex_type.subtypes.first.qualify(api_map, bmeth.context.namespace)
|
88
|
-
elsif (Solargraph::CoreFills::METHODS_WITH_YIELDPARAM_SELF.include?(meth.path))
|
89
|
-
bmeth = chain.base.define(api_map, context, locals).first
|
90
|
-
return ComplexType::UNDEFINED if bmeth.nil?
|
91
|
-
return bmeth.typify(api_map)
|
92
|
-
else
|
93
|
-
yps = meth.docstring.tags(:yieldparam)
|
94
|
-
unless yps[index].nil? or yps[index].types.nil? or yps[index].types.empty?
|
95
|
-
return ComplexType.try_parse(yps[index].types.first).qualify(api_map, meth.context.namespace)
|
96
|
-
end
|
97
|
-
end
|
98
|
-
end
|
99
|
-
ComplexType::UNDEFINED
|
100
|
-
end
|
101
|
-
end
|
102
|
-
end
|
103
|
-
end
|
@@ -1,40 +0,0 @@
|
|
1
|
-
module Solargraph
|
2
|
-
module Pin
|
3
|
-
class MethodParameter < LocalVariable
|
4
|
-
def return_complex_type
|
5
|
-
if @return_complex_type.nil?
|
6
|
-
@return_complex_type = ComplexType.new
|
7
|
-
found = nil
|
8
|
-
params = block.docstring.tags(:param)
|
9
|
-
params.each do |p|
|
10
|
-
next unless p.name == name
|
11
|
-
found = p
|
12
|
-
break
|
13
|
-
end
|
14
|
-
if found.nil? and !index.nil?
|
15
|
-
found = params[index] if params[index] && (params[index].name.nil? || params[index].name.empty?)
|
16
|
-
end
|
17
|
-
@return_complex_type = ComplexType.try_parse(*found.types) unless found.nil? or found.types.nil?
|
18
|
-
end
|
19
|
-
super
|
20
|
-
@return_complex_type
|
21
|
-
end
|
22
|
-
|
23
|
-
# The parameter's zero-based location in the block's signature.
|
24
|
-
#
|
25
|
-
# @return [Integer]
|
26
|
-
def index
|
27
|
-
block.parameter_names.index(name)
|
28
|
-
end
|
29
|
-
|
30
|
-
def try_merge! pin
|
31
|
-
return false unless super
|
32
|
-
# @todo This is a little expensive, but it's necessary because
|
33
|
-
# parameter data depends on the method's docstring.
|
34
|
-
@return_complex_type = pin.return_complex_type
|
35
|
-
reset_conversions
|
36
|
-
true
|
37
|
-
end
|
38
|
-
end
|
39
|
-
end
|
40
|
-
end
|
@@ -1,25 +0,0 @@
|
|
1
|
-
module Solargraph
|
2
|
-
module Pin
|
3
|
-
module Plugin
|
4
|
-
class Method < Base
|
5
|
-
attr_reader :name
|
6
|
-
attr_reader :path
|
7
|
-
attr_reader :return_type
|
8
|
-
attr_reader :parameters
|
9
|
-
attr_reader :scope
|
10
|
-
attr_reader :visibility
|
11
|
-
|
12
|
-
def initialize name:, path:, return_type:, parameters:
|
13
|
-
@name = name
|
14
|
-
@path = path
|
15
|
-
@return_type = return_type
|
16
|
-
@parameters = parameters
|
17
|
-
end
|
18
|
-
|
19
|
-
def completion_item_kind
|
20
|
-
Solargraph::LanguageServer::CompletionItemKinds::METHOD
|
21
|
-
end
|
22
|
-
end
|
23
|
-
end
|
24
|
-
end
|
25
|
-
end
|
data/lib/solargraph/plugin.rb
DELETED
@@ -1,41 +0,0 @@
|
|
1
|
-
module Solargraph
|
2
|
-
module Plugin
|
3
|
-
class Base
|
4
|
-
# @return [Solargraph::ApiMap]
|
5
|
-
attr_reader :api_map
|
6
|
-
|
7
|
-
def initialize api_map
|
8
|
-
@api_map = api_map
|
9
|
-
post_initialize
|
10
|
-
end
|
11
|
-
|
12
|
-
def post_initialize
|
13
|
-
end
|
14
|
-
|
15
|
-
# @return [Array<String>]
|
16
|
-
def get_methods namespace:, root:, scope:, with_private: false
|
17
|
-
[]
|
18
|
-
end
|
19
|
-
|
20
|
-
# @return [Array<String>]
|
21
|
-
def get_constants namespace, root
|
22
|
-
[]
|
23
|
-
end
|
24
|
-
|
25
|
-
# @return [String]
|
26
|
-
def get_fqns namespace, root
|
27
|
-
nil
|
28
|
-
end
|
29
|
-
|
30
|
-
# @return [Boolean]
|
31
|
-
def refresh
|
32
|
-
false
|
33
|
-
end
|
34
|
-
|
35
|
-
# @return [Boolean]
|
36
|
-
def runtime?
|
37
|
-
false
|
38
|
-
end
|
39
|
-
end
|
40
|
-
end
|
41
|
-
end
|
@@ -1,172 +0,0 @@
|
|
1
|
-
require 'json'
|
2
|
-
|
3
|
-
module Solargraph
|
4
|
-
module Plugin
|
5
|
-
class Process
|
6
|
-
def initialize
|
7
|
-
@required = []
|
8
|
-
post_initialize
|
9
|
-
end
|
10
|
-
|
11
|
-
def post_initialize
|
12
|
-
end
|
13
|
-
|
14
|
-
def run
|
15
|
-
until STDIN.closed?
|
16
|
-
input = gets
|
17
|
-
break if input.nil?
|
18
|
-
args = nil
|
19
|
-
begin
|
20
|
-
args = JSON.parse(input)
|
21
|
-
case args['command']
|
22
|
-
when 'require'
|
23
|
-
STDOUT.puts do_require args['paths']
|
24
|
-
when 'methods'
|
25
|
-
STDOUT.puts get_methods args['params']
|
26
|
-
when 'constants'
|
27
|
-
STDOUT.puts get_constants args['params']
|
28
|
-
when 'fqns'
|
29
|
-
STDOUT.puts get_fqns args['params']
|
30
|
-
else
|
31
|
-
STDOUT.puts respond_err "Unrecognized command #{args['command']}"
|
32
|
-
end
|
33
|
-
rescue JSON::ParserError => e
|
34
|
-
STDOUT.puts respond_err "Error parsing input: #{e.message}"
|
35
|
-
rescue Exception => e
|
36
|
-
STDOUT.puts respond_err "Error processing input: #{e.message}\n#{e.backtrace}"
|
37
|
-
end
|
38
|
-
STDOUT.flush
|
39
|
-
end
|
40
|
-
end
|
41
|
-
|
42
|
-
private
|
43
|
-
|
44
|
-
def do_require paths
|
45
|
-
errors = []
|
46
|
-
paths.each do |p|
|
47
|
-
begin
|
48
|
-
require p
|
49
|
-
@required.push p
|
50
|
-
rescue Exception => e
|
51
|
-
Solargraph::Logging.logger.info "Failed to require #{p}: #{e.message}"
|
52
|
-
errors.push "Failed to require #{p}: #{e.class} #{e.message}"
|
53
|
-
end
|
54
|
-
end
|
55
|
-
if errors.empty?
|
56
|
-
respond_ok
|
57
|
-
else
|
58
|
-
respond_err errors.join('; ')
|
59
|
-
end
|
60
|
-
end
|
61
|
-
|
62
|
-
def get_methods args
|
63
|
-
result = []
|
64
|
-
# @type [Class]
|
65
|
-
con = find_constant(args['namespace'], args['root'])
|
66
|
-
unless con.nil?
|
67
|
-
if (args['scope'] == 'class')
|
68
|
-
result.concat con.methods if args['with_private']
|
69
|
-
result.concat con.public_methods
|
70
|
-
elsif (args['scope'] == 'instance')
|
71
|
-
result.concat con.instance_methods if args['with_private']
|
72
|
-
result.concat con.public_instance_methods
|
73
|
-
end
|
74
|
-
end
|
75
|
-
result.keep_if{|m| m.to_s.match(/^[a-z_]/i)}
|
76
|
-
respond_ok (result.uniq.sort.map do |name|
|
77
|
-
# @type [Method]
|
78
|
-
meth = args['scope'] == 'class' ? con.method(name) : con.instance_method(name)
|
79
|
-
{
|
80
|
-
name: name,
|
81
|
-
parameters: build_parameter_array(meth.parameters)
|
82
|
-
}
|
83
|
-
end)
|
84
|
-
end
|
85
|
-
|
86
|
-
def get_constants args
|
87
|
-
result = []
|
88
|
-
con = find_constant(args['namespace'], args['root'])
|
89
|
-
unless con.nil?
|
90
|
-
#result.concat con.constants
|
91
|
-
con.constants.each do |c|
|
92
|
-
next if c == :Solargraph and !@required.include?('solargraph')
|
93
|
-
here = con.const_get(c)
|
94
|
-
item = { namespace: con.to_s, name: c.to_s }
|
95
|
-
item[:class] = here.class.to_s
|
96
|
-
result.push item
|
97
|
-
end
|
98
|
-
end
|
99
|
-
respond_ok result
|
100
|
-
end
|
101
|
-
|
102
|
-
def get_fqns args
|
103
|
-
con = find_constant(args['namespace'], args['root'])
|
104
|
-
respond_ok (con.nil? ? nil : con.to_s)
|
105
|
-
end
|
106
|
-
|
107
|
-
def find_constant(namespace, root)
|
108
|
-
result = nil
|
109
|
-
unless root.empty?
|
110
|
-
parts = root.split('::')
|
111
|
-
until parts.empty?
|
112
|
-
result = inner_find_constant("#{parts.join('::')}::#{namespace}")
|
113
|
-
parts.pop
|
114
|
-
break unless result.nil?
|
115
|
-
end
|
116
|
-
end
|
117
|
-
result = inner_find_constant(namespace) if result.nil?
|
118
|
-
result
|
119
|
-
end
|
120
|
-
|
121
|
-
def inner_find_constant(namespace)
|
122
|
-
cursor = Object
|
123
|
-
parts = namespace.split('::')
|
124
|
-
until parts.empty?
|
125
|
-
here = parts.shift
|
126
|
-
begin
|
127
|
-
cursor = cursor.const_get(here)
|
128
|
-
rescue NameError
|
129
|
-
return nil
|
130
|
-
end
|
131
|
-
end
|
132
|
-
cursor
|
133
|
-
end
|
134
|
-
|
135
|
-
def respond_ok data = []
|
136
|
-
{
|
137
|
-
status: 'ok',
|
138
|
-
message: nil,
|
139
|
-
data: data
|
140
|
-
}.to_json
|
141
|
-
end
|
142
|
-
|
143
|
-
def respond_err msg
|
144
|
-
{
|
145
|
-
status: 'err',
|
146
|
-
message: msg,
|
147
|
-
data: []
|
148
|
-
}.to_json
|
149
|
-
end
|
150
|
-
|
151
|
-
def build_parameter_array parameters
|
152
|
-
an = 1
|
153
|
-
parameters.map do |p|
|
154
|
-
if p[0] == :rest
|
155
|
-
str = (p[1] ? "*#{p[1]}" : "*args")
|
156
|
-
else
|
157
|
-
str = (p[1] ? p[1].to_s : "arg#{an}")
|
158
|
-
if p[0] == :opt
|
159
|
-
str += ' = ?'
|
160
|
-
elsif p[0] == :key
|
161
|
-
str += ':'
|
162
|
-
elsif p[0] == :keyreq
|
163
|
-
str += ': ?'
|
164
|
-
end
|
165
|
-
end
|
166
|
-
an += 1
|
167
|
-
str
|
168
|
-
end
|
169
|
-
end
|
170
|
-
end
|
171
|
-
end
|
172
|
-
end
|