synvert-core 0.15.2 → 0.19.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +16 -2
- data/Gemfile +2 -0
- data/Guardfile +2 -0
- data/Rakefile +2 -0
- data/lib/synvert/core.rb +2 -3
- data/lib/synvert/core/configuration.rb +10 -17
- data/lib/synvert/core/engine.rb +1 -1
- data/lib/synvert/core/engine/erb.rb +31 -23
- data/lib/synvert/core/exceptions.rb +5 -3
- data/lib/synvert/core/node_ext.rb +107 -101
- data/lib/synvert/core/rewriter.rb +22 -16
- data/lib/synvert/core/rewriter/action.rb +4 -6
- data/lib/synvert/core/rewriter/action/append_action.rb +3 -3
- data/lib/synvert/core/rewriter/action/insert_action.rb +9 -5
- data/lib/synvert/core/rewriter/action/insert_after_action.rb +2 -2
- data/lib/synvert/core/rewriter/action/remove_action.rb +2 -2
- data/lib/synvert/core/rewriter/action/replace_erb_stmt_with_expr_action.rb +5 -4
- data/lib/synvert/core/rewriter/action/replace_with_action.rb +7 -5
- data/lib/synvert/core/rewriter/condition.rb +1 -1
- data/lib/synvert/core/rewriter/condition/if_exist_condition.rb +2 -2
- data/lib/synvert/core/rewriter/condition/if_only_exist_condition.rb +2 -3
- data/lib/synvert/core/rewriter/condition/unless_exist_condition.rb +2 -2
- data/lib/synvert/core/rewriter/gem_spec.rb +11 -11
- data/lib/synvert/core/rewriter/helper.rb +4 -6
- data/lib/synvert/core/rewriter/instance.rb +37 -23
- data/lib/synvert/core/rewriter/ruby_version.rb +1 -1
- data/lib/synvert/core/rewriter/scope.rb +1 -1
- data/lib/synvert/core/rewriter/scope/goto_scope.rb +2 -1
- data/lib/synvert/core/rewriter/scope/within_scope.rb +23 -7
- data/lib/synvert/core/rewriter/warning.rb +1 -1
- data/lib/synvert/core/version.rb +2 -2
- data/spec/spec_helper.rb +3 -6
- data/spec/support/parser_helper.rb +2 -0
- data/spec/synvert/core/engine/erb_spec.rb +32 -30
- data/spec/synvert/core/node_ext_spec.rb +57 -54
- data/spec/synvert/core/rewriter/action/append_action_spec.rb +2 -0
- data/spec/synvert/core/rewriter/action/insert_action_spec.rb +10 -8
- data/spec/synvert/core/rewriter/action/insert_after_action_spec.rb +5 -3
- data/spec/synvert/core/rewriter/action/remove_action_spec.rb +3 -1
- data/spec/synvert/core/rewriter/action/replace_erb_stmt_with_expr_action_spec.rb +2 -0
- data/spec/synvert/core/rewriter/action/replace_with_action_spec.rb +17 -11
- data/spec/synvert/core/rewriter/action_spec.rb +2 -0
- data/spec/synvert/core/rewriter/condition/if_exist_condition_spec.rb +19 -9
- data/spec/synvert/core/rewriter/condition/if_only_exist_condition_spec.rb +23 -12
- data/spec/synvert/core/rewriter/condition/unless_exist_condition_spec.rb +19 -9
- data/spec/synvert/core/rewriter/condition_spec.rb +2 -0
- data/spec/synvert/core/rewriter/gem_spec_spec.rb +13 -10
- data/spec/synvert/core/rewriter/helper_spec.rb +36 -31
- data/spec/synvert/core/rewriter/instance_spec.rb +118 -66
- data/spec/synvert/core/rewriter/scope/goto_scope_spec.rb +10 -6
- data/spec/synvert/core/rewriter/scope/within_scope.rb +18 -9
- data/spec/synvert/core/rewriter/scope_spec.rb +2 -0
- data/spec/synvert/core/rewriter/warning_spec.rb +2 -0
- data/spec/synvert/core/rewriter_spec.rb +106 -73
- metadata +2 -4
- data/spec/synvert/core/configuration_spec.rb +0 -10
@@ -1,4 +1,4 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# Rewriter is the top level namespace in a snippet.
|
@@ -42,7 +42,14 @@ module Synvert::Core
|
|
42
42
|
autoload :RubyVersion, 'synvert/core/rewriter/ruby_version'
|
43
43
|
autoload :GemSpec, 'synvert/core/rewriter/gem_spec'
|
44
44
|
|
45
|
-
class <<self
|
45
|
+
class << self
|
46
|
+
# Execute the temporary rewriter without group and name.
|
47
|
+
#
|
48
|
+
# @param block [Block] a block defines the behaviors of the rewriter.
|
49
|
+
def execute(&block)
|
50
|
+
Rewriter.new('', '', &block).process
|
51
|
+
end
|
52
|
+
|
46
53
|
# Register a rewriter with its group and name.
|
47
54
|
#
|
48
55
|
# @param group [String] the rewriter group.
|
@@ -65,7 +72,7 @@ module Synvert::Core
|
|
65
72
|
if exist? group, name
|
66
73
|
rewriters[group][name]
|
67
74
|
else
|
68
|
-
raise RewriterNotFound
|
75
|
+
raise RewriterNotFound, "Rewriter #{group} #{name} not found"
|
69
76
|
end
|
70
77
|
end
|
71
78
|
|
@@ -82,7 +89,7 @@ module Synvert::Core
|
|
82
89
|
rewriter.process
|
83
90
|
rewriter
|
84
91
|
else
|
85
|
-
raise RewriterNotFound
|
92
|
+
raise RewriterNotFound, "Rewriter #{group}/#{name} not found"
|
86
93
|
end
|
87
94
|
end
|
88
95
|
|
@@ -112,7 +119,7 @@ module Synvert::Core
|
|
112
119
|
rewriters.clear
|
113
120
|
end
|
114
121
|
|
115
|
-
|
122
|
+
private
|
116
123
|
|
117
124
|
def rewriters
|
118
125
|
@rewriters ||= {}
|
@@ -151,14 +158,14 @@ module Synvert::Core
|
|
151
158
|
# Process the rewriter.
|
152
159
|
# It will call the block.
|
153
160
|
def process
|
154
|
-
|
161
|
+
instance_eval &@block
|
155
162
|
end
|
156
163
|
|
157
164
|
# Process rewriter with sandbox mode.
|
158
165
|
# It will call the block but doesn't change any file.
|
159
166
|
def process_with_sandbox
|
160
167
|
@sandbox = true
|
161
|
-
|
168
|
+
process
|
162
169
|
@sandbox = false
|
163
170
|
end
|
164
171
|
|
@@ -178,7 +185,7 @@ module Synvert::Core
|
|
178
185
|
#
|
179
186
|
# @param description [String] rewriter description.
|
180
187
|
# @return rewriter description.
|
181
|
-
def description(description=nil)
|
188
|
+
def description(description = nil)
|
182
189
|
if description
|
183
190
|
@description = description
|
184
191
|
else
|
@@ -208,17 +215,16 @@ module Synvert::Core
|
|
208
215
|
# @param file_pattern [String] pattern to find files, e.g. spec/**/*_spec.rb
|
209
216
|
# @param options [Hash] instance options.
|
210
217
|
# @param block [Block] the block to rewrite code in the matching files.
|
211
|
-
def within_files(file_pattern, options={}, &block)
|
218
|
+
def within_files(file_pattern, options = {}, &block)
|
212
219
|
return if @sandbox
|
213
220
|
|
214
|
-
if (!@ruby_version || @ruby_version.match?) &&
|
215
|
-
(!@gem_spec || @gem_spec.match?)
|
221
|
+
if (!@ruby_version || @ruby_version.match?) && (!@gem_spec || @gem_spec.match?)
|
216
222
|
Rewriter::Instance.new(self, file_pattern, options, &block).process
|
217
223
|
end
|
218
224
|
end
|
219
225
|
|
220
226
|
# Parse within_file dsl, it finds a specifiled file.
|
221
|
-
|
227
|
+
alias within_file within_files
|
222
228
|
|
223
229
|
# Parses add_file dsl, it adds a new file.
|
224
230
|
#
|
@@ -227,7 +233,7 @@ module Synvert::Core
|
|
227
233
|
def add_file(filename, content)
|
228
234
|
return if @sandbox
|
229
235
|
|
230
|
-
filepath = File.join(Configuration.
|
236
|
+
filepath = File.join(Configuration.path, filename)
|
231
237
|
if File.exist?(filepath)
|
232
238
|
puts "File #{filepath} already exists."
|
233
239
|
return
|
@@ -245,7 +251,7 @@ module Synvert::Core
|
|
245
251
|
def remove_file(filename)
|
246
252
|
return if @sandbox
|
247
253
|
|
248
|
-
file_path = File.join(Configuration.
|
254
|
+
file_path = File.join(Configuration.path, filename)
|
249
255
|
File.delete(file_path) if File.exist?(file_path)
|
250
256
|
end
|
251
257
|
|
@@ -262,7 +268,7 @@ module Synvert::Core
|
|
262
268
|
# @param name [String] helper method name.
|
263
269
|
# @param block [Block] helper method block.
|
264
270
|
def helper_method(name, &block)
|
265
|
-
@helpers << {name: name, block: block}
|
271
|
+
@helpers << { name: name, block: block }
|
266
272
|
end
|
267
273
|
|
268
274
|
# Parse todo dsl, it sets todo of the rewriter.
|
@@ -270,7 +276,7 @@ module Synvert::Core
|
|
270
276
|
#
|
271
277
|
# @param todo_list [String] rewriter todo.
|
272
278
|
# @return [String] rewriter todo.
|
273
|
-
def todo(todo=nil)
|
279
|
+
def todo(todo = nil)
|
274
280
|
if todo
|
275
281
|
@todo = todo
|
276
282
|
else
|
@@ -1,9 +1,9 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# Action defines rewriter action, add, replace or remove code.
|
5
5
|
class Rewriter::Action
|
6
|
-
DEFAULT_OPTIONS = { autoindent: true }
|
6
|
+
DEFAULT_OPTIONS = { autoindent: true }.freeze
|
7
7
|
DEFAULT_INDENT = 2
|
8
8
|
|
9
9
|
# Initialize an action.
|
@@ -11,7 +11,7 @@ module Synvert::Core
|
|
11
11
|
# @param instance [Synvert::Core::Rewriter::Instance]
|
12
12
|
# @param code [String] new code to add, replace or remove.
|
13
13
|
# @param options [Hash] action options, it includes :autoindent.
|
14
|
-
def initialize(instance, code, options={})
|
14
|
+
def initialize(instance, code, options = {})
|
15
15
|
@instance = instance
|
16
16
|
@code = code
|
17
17
|
@options = DEFAULT_OPTIONS.merge(options)
|
@@ -30,9 +30,7 @@ module Synvert::Core
|
|
30
30
|
# @return [String] rewritten code.
|
31
31
|
def rewritten_code
|
32
32
|
if rewritten_source.split("\n").length > 1
|
33
|
-
"\n\n" + rewritten_source.split("\n").map { |line|
|
34
|
-
indent(@node) + line
|
35
|
-
}.join("\n")
|
33
|
+
"\n\n" + rewritten_source.split("\n").map { |line| indent(@node) + line }.join("\n")
|
36
34
|
else
|
37
35
|
"\n" + indent(@node) + rewritten_source
|
38
36
|
end
|
@@ -1,4 +1,4 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# AppendAction to append code to the bottom of node body.
|
@@ -23,14 +23,14 @@ module Synvert::Core
|
|
23
23
|
begin_pos
|
24
24
|
end
|
25
25
|
|
26
|
-
|
26
|
+
private
|
27
27
|
|
28
28
|
# Indent of the node.
|
29
29
|
#
|
30
30
|
# @param node [Parser::AST::Node]
|
31
31
|
# @return [String] n times whitesphace
|
32
32
|
def indent(node)
|
33
|
-
if [
|
33
|
+
if %i[block class].include? node.type
|
34
34
|
' ' * (node.indent + DEFAULT_INDENT)
|
35
35
|
else
|
36
36
|
' ' * node.indent
|
@@ -1,9 +1,9 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# InsertAction to insert code to the top of node body.
|
5
5
|
class Rewriter::InsertAction < Rewriter::Action
|
6
|
-
DO_LENGTH =
|
6
|
+
DO_LENGTH = ' do'.length
|
7
7
|
|
8
8
|
# Begin position to insert code.
|
9
9
|
#
|
@@ -11,7 +11,11 @@ module Synvert::Core
|
|
11
11
|
def begin_pos
|
12
12
|
case @node.type
|
13
13
|
when :block
|
14
|
-
@node.children[1].children.empty?
|
14
|
+
if @node.children[1].children.empty?
|
15
|
+
@node.children[0].loc.expression.end_pos + DO_LENGTH
|
16
|
+
else
|
17
|
+
@node.children[1].loc.expression.end_pos
|
18
|
+
end
|
15
19
|
when :class
|
16
20
|
@node.children[1] ? @node.children[1].loc.expression.end_pos : @node.children[0].loc.expression.end_pos
|
17
21
|
else
|
@@ -26,14 +30,14 @@ module Synvert::Core
|
|
26
30
|
begin_pos
|
27
31
|
end
|
28
32
|
|
29
|
-
|
33
|
+
private
|
30
34
|
|
31
35
|
# Indent of the node.
|
32
36
|
#
|
33
37
|
# @param node [Parser::AST::Node]
|
34
38
|
# @return [String] n times whitesphace
|
35
39
|
def indent(node)
|
36
|
-
if [
|
40
|
+
if %i[block class].include? node.type
|
37
41
|
' ' * (node.indent + DEFAULT_INDENT)
|
38
42
|
else
|
39
43
|
' ' * node.indent
|
@@ -1,10 +1,10 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# ReplaceErbStmtWithExprAction to replace erb stmt code to expr,
|
5
5
|
# e.g. <% form_for ... %> => <%= form_for ... %>.
|
6
6
|
class Rewriter::ReplaceErbStmtWithExprAction < Rewriter::Action
|
7
|
-
def initialize(instance, code=nil)
|
7
|
+
def initialize(instance, code = nil)
|
8
8
|
super
|
9
9
|
end
|
10
10
|
|
@@ -23,7 +23,7 @@ module Synvert::Core
|
|
23
23
|
# @return [Integer] end position.
|
24
24
|
def end_pos
|
25
25
|
node_begin_pos = @node.loc.expression.begin_pos
|
26
|
-
node_begin_pos += @node.loc.expression.source.index
|
26
|
+
node_begin_pos += @node.loc.expression.source.index 'do'
|
27
27
|
while @node.loc.expression.source_buffer.source[node_begin_pos += 1] != '@'
|
28
28
|
end
|
29
29
|
node_begin_pos
|
@@ -33,7 +33,8 @@ module Synvert::Core
|
|
33
33
|
#
|
34
34
|
# @return [String] rewritten code.
|
35
35
|
def rewritten_code
|
36
|
-
@node.loc.expression.source_buffer.source[begin_pos...end_pos]
|
36
|
+
@node.loc.expression.source_buffer.source[begin_pos...end_pos]
|
37
|
+
.sub(Engine::ERUBY_STMT_SPLITTER, '@output_buffer.append= ')
|
37
38
|
.sub(Engine::ERUBY_STMT_SPLITTER, Engine::ERUBY_EXPR_SPLITTER)
|
38
39
|
end
|
39
40
|
end
|
@@ -1,4 +1,4 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# ReplaceWithAction to replace code.
|
@@ -23,16 +23,18 @@ module Synvert::Core
|
|
23
23
|
def rewritten_code
|
24
24
|
if rewritten_source.split("\n").length > 1
|
25
25
|
new_code = []
|
26
|
-
rewritten_source
|
27
|
-
|
28
|
-
|
26
|
+
rewritten_source
|
27
|
+
.split("\n")
|
28
|
+
.each_with_index { |line, index|
|
29
|
+
new_code << (index == 0 || !@options[:autoindent] ? line : indent(@node) + line)
|
30
|
+
}
|
29
31
|
new_code.join("\n")
|
30
32
|
else
|
31
33
|
rewritten_source
|
32
34
|
end
|
33
35
|
end
|
34
36
|
|
35
|
-
|
37
|
+
private
|
36
38
|
|
37
39
|
# Indent of the node
|
38
40
|
#
|
@@ -1,4 +1,4 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# IfExistCondition checks if matching node exists in the node children.
|
@@ -7,7 +7,7 @@ module Synvert::Core
|
|
7
7
|
def match?
|
8
8
|
match = false
|
9
9
|
@instance.current_node.recursive_children do |child_node|
|
10
|
-
match
|
10
|
+
match ||= (child_node&.match?(@rules))
|
11
11
|
end
|
12
12
|
match
|
13
13
|
end
|
@@ -1,12 +1,11 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# IfExistCondition checks if node has only one child node and the child node matches rules.
|
5
5
|
class Rewriter::IfOnlyExistCondition < Rewriter::Condition
|
6
6
|
# check if only have one child node and the child node matches rules.
|
7
7
|
def match?
|
8
|
-
@instance.current_node.body.size == 1 &&
|
9
|
-
@instance.current_node.body.first.match?(@rules)
|
8
|
+
@instance.current_node.body.size == 1 && @instance.current_node.body.first.match?(@rules)
|
10
9
|
end
|
11
10
|
end
|
12
11
|
end
|
@@ -1,4 +1,4 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# UnlessExistCondition checks if matching node doesn't exist in the node children.
|
@@ -7,7 +7,7 @@ module Synvert::Core
|
|
7
7
|
def match?
|
8
8
|
match = false
|
9
9
|
@instance.current_node.recursive_children do |child_node|
|
10
|
-
match
|
10
|
+
match ||= (child_node&.match?(@rules))
|
11
11
|
end
|
12
12
|
!match
|
13
13
|
end
|
@@ -1,9 +1,9 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# GemSpec checks and compares gem version.
|
5
5
|
class Rewriter::GemSpec
|
6
|
-
OPERATORS = {eq: '==', lt: '<', gt: '>', lte: '<=', gte: '>=', ne: '!='}
|
6
|
+
OPERATORS = { eq: '==', lt: '<', gt: '>', lte: '<=', gte: '>=', ne: '!=' }.freeze
|
7
7
|
|
8
8
|
# Initialize a gem_spec.
|
9
9
|
#
|
@@ -26,16 +26,16 @@ module Synvert::Core
|
|
26
26
|
# @return [Boolean] true if matches, otherwise false.
|
27
27
|
# @raise [Synvert::Core::GemfileLockNotFound] raise if Gemfile.lock does not exist.
|
28
28
|
def match?
|
29
|
-
gemfile_lock_path = File.join(Configuration.
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
29
|
+
gemfile_lock_path = File.join(Configuration.path, 'Gemfile.lock')
|
30
|
+
|
31
|
+
# if Gemfile.lock does not exist, just ignore this check
|
32
|
+
return true unless File.exist?(gemfile_lock_path)
|
33
|
+
|
34
|
+
parser = Bundler::LockfileParser.new(File.read(gemfile_lock_path))
|
35
|
+
if spec = parser.specs.find { |spec| spec.name == @name }
|
36
|
+
Gem::Version.new(spec.version).send(OPERATORS[@operator], @version)
|
37
37
|
else
|
38
|
-
|
38
|
+
false
|
39
39
|
end
|
40
40
|
end
|
41
41
|
end
|
@@ -1,4 +1,4 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# Rewriter::Helper provides some helper methods to make it easier to write a snippet.
|
@@ -34,9 +34,9 @@ module Synvert::Core
|
|
34
34
|
# if current_node has argument, it returns "({{arguments}})"
|
35
35
|
def add_arguments_with_parenthesis_if_necessary
|
36
36
|
if node.arguments.size > 0
|
37
|
-
|
37
|
+
'({{arguments}})'
|
38
38
|
else
|
39
|
-
|
39
|
+
''
|
40
40
|
end
|
41
41
|
end
|
42
42
|
|
@@ -65,9 +65,7 @@ module Synvert::Core
|
|
65
65
|
#
|
66
66
|
# strip_brackets("(1..100)") #=> "1..100"
|
67
67
|
def strip_brackets(code)
|
68
|
-
code.sub(/^\((.*)\)$/) { $1 }
|
69
|
-
.sub(/^\[(.*)\]$/) { $1 }
|
70
|
-
.sub(/^{(.*)}$/) { $1 }
|
68
|
+
code.sub(/^\((.*)\)$/) { $1 }.sub(/^\[(.*)\]$/) { $1 }.sub(/^{(.*)}$/) { $1 }
|
71
69
|
end
|
72
70
|
end
|
73
71
|
end
|
@@ -1,4 +1,4 @@
|
|
1
|
-
#
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Synvert::Core
|
4
4
|
# Instance is an execution unit, it finds specified ast nodes,
|
@@ -8,7 +8,7 @@ module Synvert::Core
|
|
8
8
|
class Rewriter::Instance
|
9
9
|
include Rewriter::Helper
|
10
10
|
|
11
|
-
class <<self
|
11
|
+
class << self
|
12
12
|
# Cached file source.
|
13
13
|
#
|
14
14
|
# @param file_path [String] file path
|
@@ -64,7 +64,7 @@ module Synvert::Core
|
|
64
64
|
# @return current filename
|
65
65
|
attr_accessor :current_node, :current_file
|
66
66
|
|
67
|
-
DEFAULT_OPTIONS = { sort_by: 'begin_pos' }
|
67
|
+
DEFAULT_OPTIONS = { sort_by: 'begin_pos' }.freeze
|
68
68
|
|
69
69
|
# Initialize an instance.
|
70
70
|
#
|
@@ -73,30 +73,33 @@ module Synvert::Core
|
|
73
73
|
# @param options [Hash] instance options, it includes :sort_by.
|
74
74
|
# @param block [Block] block code to find nodes, match conditions and rewrite code.
|
75
75
|
# @return [Synvert::Core::Rewriter::Instance]
|
76
|
-
def initialize(rewriter, file_pattern, options={}, &block)
|
76
|
+
def initialize(rewriter, file_pattern, options = {}, &block)
|
77
77
|
@rewriter = rewriter
|
78
78
|
@actions = []
|
79
79
|
@file_pattern = file_pattern
|
80
80
|
@options = DEFAULT_OPTIONS.merge(options)
|
81
81
|
@block = block
|
82
|
-
rewriter.helpers.each { |helper|
|
82
|
+
rewriter.helpers.each { |helper| singleton_class.send(:define_method, helper[:name], &helper[:block]) }
|
83
83
|
end
|
84
84
|
|
85
85
|
# Process the instance.
|
86
86
|
# It finds all files, for each file, it executes the block code, gets all rewrite actions,
|
87
87
|
# and rewrite source code back to original file.
|
88
88
|
def process
|
89
|
-
file_pattern = File.join(Configuration.
|
90
|
-
Dir
|
91
|
-
|
89
|
+
file_pattern = File.join(Configuration.path, @file_pattern)
|
90
|
+
Dir
|
91
|
+
.glob(file_pattern)
|
92
|
+
.each do |file_path|
|
93
|
+
next if Configuration.skip_files.include? file_path
|
94
|
+
|
92
95
|
begin
|
93
96
|
conflict_actions = []
|
94
|
-
source = self.class.file_source(file_path)
|
97
|
+
source = +self.class.file_source(file_path)
|
95
98
|
ast = self.class.file_ast(file_path)
|
96
99
|
|
97
100
|
@current_file = file_path
|
98
101
|
|
99
|
-
|
102
|
+
process_with_node ast do
|
100
103
|
begin
|
101
104
|
instance_eval &@block
|
102
105
|
rescue NoMethodError
|
@@ -108,7 +111,7 @@ module Synvert::Core
|
|
108
111
|
if @actions.length > 0
|
109
112
|
@actions.sort_by! { |action| action.send(@options[:sort_by]) }
|
110
113
|
conflict_actions = get_conflict_actions
|
111
|
-
@actions.
|
114
|
+
@actions.reverse_each do |action|
|
112
115
|
source[action.begin_pos...action.end_pos] = action.rewritten_code
|
113
116
|
source = remove_code_or_whole_line(source, action.line)
|
114
117
|
end
|
@@ -121,7 +124,6 @@ module Synvert::Core
|
|
121
124
|
# do nothing, iterate next file
|
122
125
|
end while !conflict_actions.empty?
|
123
126
|
end
|
124
|
-
end
|
125
127
|
end
|
126
128
|
|
127
129
|
# Gets current node, it allows to get current node in block code.
|
@@ -146,7 +148,7 @@ module Synvert::Core
|
|
146
148
|
# @param node [Parser::AST::Node] node set to current_node
|
147
149
|
# @yield process
|
148
150
|
def process_with_other_node(node)
|
149
|
-
original_node =
|
151
|
+
original_node = current_node
|
150
152
|
self.current_node = node
|
151
153
|
yield
|
152
154
|
self.current_node = original_node
|
@@ -156,15 +158,28 @@ module Synvert::Core
|
|
156
158
|
# DSL #
|
157
159
|
#######
|
158
160
|
|
159
|
-
# Parse within_node dsl, it creates a [Synvert::Core::Rewriter::WithinScope] to find matching ast nodes,
|
161
|
+
# Parse within_node dsl, it creates a [Synvert::Core::Rewriter::WithinScope] to find recursive matching ast nodes,
|
160
162
|
# then continue operating on each matching ast node.
|
161
163
|
#
|
162
164
|
# @param rules [Hash] rules to find mathing ast nodes.
|
163
165
|
# @param block [Block] block code to continue operating on the matching nodes.
|
164
166
|
def within_node(rules, &block)
|
165
|
-
Rewriter::WithinScope.new(self, rules, &block).process
|
167
|
+
Rewriter::WithinScope.new(self, rules, { recursive: true }, &block).process
|
166
168
|
end
|
167
169
|
|
170
|
+
alias with_node within_node
|
171
|
+
|
172
|
+
# Parse within_direct_node dsl, it creates a [Synvert::Core::Rewriter::WithinScope] to find direct matching ast nodes,
|
173
|
+
# then continue operating on each matching ast node.
|
174
|
+
#
|
175
|
+
# @param rules [Hash] rules to find mathing ast nodes.
|
176
|
+
# @param block [Block] block code to continue operating on the matching nodes.
|
177
|
+
def within_direct_node(rules, &block)
|
178
|
+
Rewriter::WithinScope.new(self, rules, { recursive: false }, &block).process
|
179
|
+
end
|
180
|
+
|
181
|
+
alias with_direct_node within_direct_node
|
182
|
+
|
168
183
|
# Parse goto_node dsl, it creates a [Synvert::Core::Rewriter::GotoScope] to go to a child node,
|
169
184
|
# then continue operating on the child node.
|
170
185
|
#
|
@@ -174,8 +189,6 @@ module Synvert::Core
|
|
174
189
|
Rewriter::GotoScope.new(self, child_node_name, &block).process
|
175
190
|
end
|
176
191
|
|
177
|
-
alias_method :with_node, :within_node
|
178
|
-
|
179
192
|
# Parse if_exist_node dsl, it creates a [Synvert::Core::Rewriter::IfExistCondition] to check
|
180
193
|
# if matching nodes exist in the child nodes, if so, then continue operating on each matching ast node.
|
181
194
|
#
|
@@ -209,7 +222,7 @@ module Synvert::Core
|
|
209
222
|
#
|
210
223
|
# @param code [String] code need to be appended.
|
211
224
|
# @param options [Hash] action options.
|
212
|
-
def append(code, options={})
|
225
|
+
def append(code, options = {})
|
213
226
|
@actions << Rewriter::AppendAction.new(self, code, options)
|
214
227
|
end
|
215
228
|
|
@@ -218,7 +231,7 @@ module Synvert::Core
|
|
218
231
|
#
|
219
232
|
# @param code [String] code need to be inserted.
|
220
233
|
# @param options [Hash] action options.
|
221
|
-
def insert(code, options={})
|
234
|
+
def insert(code, options = {})
|
222
235
|
@actions << Rewriter::InsertAction.new(self, code, options)
|
223
236
|
end
|
224
237
|
|
@@ -227,7 +240,7 @@ module Synvert::Core
|
|
227
240
|
#
|
228
241
|
# @param code [String] code need to be inserted.
|
229
242
|
# @param options [Hash] action options.
|
230
|
-
def insert_after(node, options={})
|
243
|
+
def insert_after(node, options = {})
|
231
244
|
@actions << Rewriter::InsertAfterAction.new(self, node, options)
|
232
245
|
end
|
233
246
|
|
@@ -236,7 +249,7 @@ module Synvert::Core
|
|
236
249
|
#
|
237
250
|
# @param code [String] code need to be replaced with.
|
238
251
|
# @param options [Hash] action options.
|
239
|
-
def replace_with(code, options={})
|
252
|
+
def replace_with(code, options = {})
|
240
253
|
@actions << Rewriter::ReplaceWithAction.new(self, code, options)
|
241
254
|
end
|
242
255
|
|
@@ -258,7 +271,7 @@ module Synvert::Core
|
|
258
271
|
@rewriter.add_warning Rewriter::Warning.new(self, message)
|
259
272
|
end
|
260
273
|
|
261
|
-
|
274
|
+
private
|
262
275
|
|
263
276
|
# It changes source code from bottom to top, and it can change source code twice at the same time,
|
264
277
|
# So if there is an overlap between two actions, it removes the conflict actions and operate them in the next loop.
|
@@ -290,7 +303,8 @@ module Synvert::Core
|
|
290
303
|
source_arr = source.split("\n")
|
291
304
|
if source_arr[line - 1] && source_arr[line - 1].strip.empty?
|
292
305
|
source_arr.delete_at(line - 1)
|
293
|
-
if source_arr[line - 2] && source_arr[line - 2].strip.empty? && source_arr[line - 1] &&
|
306
|
+
if source_arr[line - 2] && source_arr[line - 2].strip.empty? && source_arr[line - 1] &&
|
307
|
+
source_arr[line - 1].strip.empty?
|
294
308
|
source_arr.delete_at(line - 1)
|
295
309
|
end
|
296
310
|
source_arr.join("\n") + (newline_at_end_of_line ? "\n" : '')
|