Class: Solargraph::Source
- Inherits:
-
Object
- Object
- Solargraph::Source
show all
- Includes:
- EncodingFixes
- Defined in:
- lib/solargraph/source.rb,
lib/solargraph/source/chain.rb,
lib/solargraph/source/change.rb,
lib/solargraph/source/cursor.rb,
lib/solargraph/source/updater.rb,
lib/solargraph/source/chain/if.rb,
lib/solargraph/source/chain/or.rb,
lib/solargraph/source/chain/call.rb,
lib/solargraph/source/chain/hash.rb,
lib/solargraph/source/chain/head.rb,
lib/solargraph/source/chain/link.rb,
lib/solargraph/source/chain/array.rb,
lib/solargraph/source/chain/q_call.rb,
lib/solargraph/source/chain/literal.rb,
lib/solargraph/source/chain/z_super.rb,
lib/solargraph/source/chain/constant.rb,
lib/solargraph/source/chain/variable.rb,
lib/solargraph/source/encoding_fixes.rb,
lib/solargraph/source/source_chainer.rb,
lib/solargraph/source/chain/block_symbol.rb,
lib/solargraph/source/chain/block_variable.rb,
lib/solargraph/source/chain/class_variable.rb,
lib/solargraph/source/chain/global_variable.rb,
lib/solargraph/source/chain/instance_variable.rb
Overview
A Ruby file that has been parsed into an AST.
Defined Under Namespace
Modules: EncodingFixes
Classes: Chain, Change, Cursor, SourceChainer, Updater
Constant Summary
collapse
- FOLDING_NODE_TYPES =
%i[
class sclass module def defs if str dstr array while unless kwbegin hash block
].freeze
Instance Attribute Summary collapse
Class Method Summary
collapse
Instance Method Summary
collapse
-
#associated_comments ⇒ Hash{Integer => String, nil}
Get a hash of comments grouped by the line numbers of the associated code.
-
#at(range) ⇒ String
-
#code ⇒ String
-
#code_for(node) ⇒ String
-
#comment_at?(position) ⇒ Boolean
-
#comments_for(node) ⇒ String?
-
#cursor_at(position) ⇒ Source::Cursor
-
#folding_ranges ⇒ Array<Range>
Get an array of ranges that can be folded, e.g., the range of a class definition or an if condition.
-
#from_to(l1, c1, l2, c2) ⇒ String
@sg-ignore Need to add nil check here.
-
#initialize(code, filename = nil, version = 0) ⇒ Source
constructor
A new instance of Source.
-
#location ⇒ Location
A location representing the file in its entirety.
-
#node_at(line, column) ⇒ AST::Node
Get the nearest node that contains the specified index.
-
#parsed? ⇒ Boolean
-
#references(name) ⇒ Array<Location>
-
#repaired? ⇒ Boolean
-
#string_at?(position) ⇒ Boolean
-
#string_ranges ⇒ ::Array<Range>
-
#synchronize(updater) ⇒ Source
Synchronize the Source with an update.
-
#synchronized? ⇒ Boolean
-
#tree_at(line, column) ⇒ Array<Parser::AST::Node>
Get an array of nodes containing the specified index, starting with the nearest node and ending with the root.
normalize
Constructor Details
#initialize(code, filename = nil, version = 0) ⇒ Source
Returns a new instance of Source.
46
47
48
49
50
51
|
# File 'lib/solargraph/source.rb', line 46
def initialize code, filename = nil, version = 0
@code = normalize(code)
@repaired = code
@filename = filename
@version = version
end
|
Instance Attribute Details
34
35
36
37
|
# File 'lib/solargraph/source.rb', line 34
def
finalize
@comments
end
|
#error_ranges ⇒ Array<Range>
187
188
189
|
# File 'lib/solargraph/source.rb', line 187
def error_ranges
@error_ranges ||= []
end
|
#filename ⇒ String?
19
20
21
|
# File 'lib/solargraph/source.rb', line 19
def filename
@filename
end
|
#node ⇒ Parser::AST::Node?
28
29
30
31
|
# File 'lib/solargraph/source.rb', line 28
def node
finalize
@node
end
|
#version ⇒ Integer
41
42
43
|
# File 'lib/solargraph/source.rb', line 41
def version
@version
end
|
Class Method Details
494
495
496
497
498
499
|
# File 'lib/solargraph/source.rb', line 494
def load filename
file = File.open(filename)
code = file.read
file.close
Source.load_string(code, filename)
end
|
.load_string(code, filename = nil, version = 0) ⇒ Solargraph::Source
505
506
507
|
# File 'lib/solargraph/source.rb', line 505
def load_string code, filename = nil, version = 0
Source.new code, filename, version
end
|
.parse_docstring(comments) ⇒ YARD::DocstringParser
511
512
513
514
515
516
517
518
519
|
# File 'lib/solargraph/source.rb', line 511
def parse_docstring
YARD::Docstring.parser.parse(, YARD::CodeObjects::Base.new(:root, 'stub'))
rescue StandardError => e
Solargraph.logger.info "YARD failed to parse docstring: [#{e.class}] #{e.message}"
Solargraph.logger.debug "Unparsed comment: #{}"
YARD::Docstring.parser
end
|
Instance Method Details
Get a hash of comments grouped by the line numbers of the associated code.
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
|
# File 'lib/solargraph/source.rb', line 253
def
@associated_comments ||= begin
result = {}
buffer = String.new('')
last = nil
.each_pair do |num, snip|
if !last || num == last + 1
buffer.concat "#{snip.text}\n"
else
result[first_not_empty_from(last + 1)] = buffer.clone
buffer.replace "#{snip.text}\n"
end
last = num
end
result[first_not_empty_from(last + 1)] = buffer unless buffer.empty? || last.nil?
result
end
end
|
#at(range) ⇒ String
55
56
57
|
# File 'lib/solargraph/source.rb', line 55
def at range
from_to range.start.line, range.start.character, range.ending.line, range.ending.character
end
|
#code ⇒ String
22
23
24
25
|
# File 'lib/solargraph/source.rb', line 22
def code
finalize
@code
end
|
171
172
173
174
175
176
177
178
|
# File 'lib/solargraph/source.rb', line 171
def position
.each do |range|
return true if range.include?(position) ||
(range.ending.line == position.line && range.ending.column < position.column)
break if range.ending.line > position.line
end
false
end
|
206
207
208
209
210
211
212
213
214
|
# File 'lib/solargraph/source.rb', line 206
def node
rng = Range.from_node(node)
[rng.start.line] ||= begin
buff = [rng.start.line]
buff ? (buff) : nil
end
end
|
115
116
117
118
|
# File 'lib/solargraph/source.rb', line 115
def cursor_at position
finalize
Cursor.new(self, position)
end
|
#folding_ranges ⇒ Array<Range>
Get an array of ranges that can be folded, e.g., the range of a class definition or an if condition.
See FOLDING_NODE_TYPES for the list of node types that can be folded.
236
237
238
239
240
241
242
243
244
|
# File 'lib/solargraph/source.rb', line 236
def folding_ranges
@folding_ranges ||= begin
result = []
inner_folding_ranges node, result
result.concat
result
end
end
|
#from_to(l1, c1, l2, c2) ⇒ String
@sg-ignore Need to add nil check here
A location representing the file in its entirety.
#node_at(line, column) ⇒ AST::Node
Get the nearest node that contains the specified index.
77
78
79
|
# File 'lib/solargraph/source.rb', line 77
def node_at line, column
tree_at(line, column).first
end
|
#parsed? ⇒ Boolean
121
122
123
124
|
# File 'lib/solargraph/source.rb', line 121
def parsed?
finalize
@parsed
end
|
#references(name) ⇒ Array<Location>
182
183
184
|
# File 'lib/solargraph/source.rb', line 182
def references name
Parser.references self, name
end
|
#repaired? ⇒ Boolean
126
127
128
|
# File 'lib/solargraph/source.rb', line 126
def repaired?
code != @repaired
end
|
#string_at?(position) ⇒ Boolean
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
|
# File 'lib/solargraph/source.rb', line 132
def string_at? position
return false if Position.to_offset(code, position) >= code.length
string_nodes.each do |node|
range = Range.from_node(node)
next if range.ending.line < position.line
break if range.ending.line > position.line
return true if node.type == :str && range.include?(position) && range.start != position
return true if %i[STR str].include?(node.type) && range.include?(position) && range.start != position
if node.type == :dstr
inner = node_at(position.line, position.column)
next if inner.nil?
inner_range = Range.from_node(inner)
next unless range.include?(inner_range.ending)
return true if inner.type == :str
inner_code = at(Solargraph::Range.new(inner_range.start, position))
return true if (inner.type == :dstr && inner_range.ending.character <= position.character && !inner_code.end_with?('}')) ||
(inner.type != :dstr && inner_range.ending.line == position.line && position.character <= inner_range.ending.character && inner_code.end_with?('}'))
end
break if range.ending.line > position.line
end
false
end
|
#string_ranges ⇒ ::Array<Range>
165
166
167
|
# File 'lib/solargraph/source.rb', line 165
def string_ranges
@string_ranges ||= Parser.string_ranges(node)
end
|
#synchronize(updater) ⇒ Source
Synchronize the Source with an update. This method applies changes to the code, parses the new code’s AST, and returns the resulting Source object.
99
100
101
102
103
104
105
106
107
108
109
110
111
|
# File 'lib/solargraph/source.rb', line 99
def synchronize updater
raise 'Invalid synchronization' unless updater.filename == filename
real_code = updater.write(@code)
if real_code == @code
@version = updater.version
return self
end
Source.new(@code, filename, updater.version).tap do |src|
src.repaired = @repaired
src.error_ranges.concat error_ranges
src.changes.concat(changes + updater.changes)
end
end
|
#synchronized? ⇒ Boolean
246
247
248
|
# File 'lib/solargraph/source.rb', line 246
def synchronized?
true
end
|
#tree_at(line, column) ⇒ Array<Parser::AST::Node>
Get an array of nodes containing the specified index, starting with the nearest node and ending with the root.
87
88
89
90
91
92
|
# File 'lib/solargraph/source.rb', line 87
def tree_at line, column
position = Position.new(line, column)
stack = []
inner_tree_at node, position, stack
stack
end
|