dead_code_terminator 0.2.0 → 0.3.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: '0594405128f563ed209b13acac45f6d1dcfebb56c36f51bee071cab04e208ecf'
4
- data.tar.gz: 3c16615d8ed48a12d1284908a35e580d90c008eb85ec4e7c3aa94a133fe0e775
3
+ metadata.gz: 30f177ea46b025d82a1647deb392a82ea79bf7d188180b01db1d3b7c9914772f
4
+ data.tar.gz: a1e654d7c848fea862cf3c3fdbf07e42096457e4994beb76f7b8c0fe6b83580a
5
5
  SHA512:
6
- metadata.gz: 215e88c2977706899fb2d312b483cd46e8d9311f1cb411f62d9cce8a3d64fce29891ebdaf02497fb9e200efc805830af06104840a9e9da0bdc825f3a2085933b
7
- data.tar.gz: aeb91248beb05727ae810e98833a70c19df8e6b34f6641a40d477a3f71773943453cdcf8aa706387002ba04db471acdb33c15afcf234b3a93f6aadac4d845c19
6
+ metadata.gz: 01d433228fbd4f63be908d7b0841d42514442f6fdf4d5c1ba54c241b4746284a430594d19061eb2a4926c0e7639cdc5694cdf12b16a498f41bb131ce2ff0bdc4
7
+ data.tar.gz: 4405404ec2c1e561177c7a3780d8b8511fbae3a1545d02231bc5b261845d4eb1925e081f1a1f439d482314785868ee9b2b7dacd8a472e9e9b698f855d13f26b5
data/.rubocop.yml CHANGED
@@ -26,3 +26,7 @@ Lint/BooleanSymbol:
26
26
  Metrics/BlockLength:
27
27
  Exclude:
28
28
  - spec/**/*rb
29
+
30
+ Naming/VariableNumber:
31
+ Exclude:
32
+ - spec/**/*rb
data/README.md CHANGED
@@ -27,8 +27,6 @@ So if you have hotfix patches from upstream - they'll be applied without conflic
27
27
 
28
28
  ## TODO
29
29
 
30
- - `unless`
31
- - `x ? a : b`
32
30
  - builtin file tree processing
33
31
  ## License
34
32
 
@@ -14,6 +14,24 @@ module DeadCodeTerminator
14
14
  class Error < StandardError; end
15
15
 
16
16
  def self.strip(io, env: {})
17
- Ast.new(env: env, ast: Unparser.parse(io)).process
17
+ replaces = on_node(Unparser.parse(io)) do |ast|
18
+ Ast.new(env: env, ast: ast).process if ast.type == :if
19
+ end
20
+
21
+ rewrite(Parser::Source::Buffer.new("buffer-or-filename", source: io), replaces)
22
+ end
23
+
24
+ def self.rewrite(buffer, replaces)
25
+ Parser::Source::TreeRewriter.new(buffer).tap do |rewriter|
26
+ replaces.each do |replace|
27
+ rewriter.replace(*replace)
28
+ end
29
+ end.process
30
+ end
31
+
32
+ def self.on_node(node, &block)
33
+ Array(yield(node)) + node.children.flat_map do |elem|
34
+ on_node(elem, &block) if elem.is_a?(Parser::AST::Node)
35
+ end.compact
18
36
  end
19
37
  end
@@ -2,35 +2,46 @@
2
2
 
3
3
  module DeadCodeTerminator
4
4
  class Ast
5
- attr_reader :env, :ast
5
+ attr_reader :env, :ast, :buf, :cond, :then_branch, :else_branch
6
6
 
7
7
  def initialize(env:, ast:)
8
8
  @env = env
9
9
  @ast = ast
10
+ @buf = @ast.loc.expression.source_buffer
11
+ @cond, @then_branch, @else_branch = @ast.children
12
+
13
+ # handle single brackets around: `if (ENV['X'])`
14
+ @cond = @cond.children[0] if (@cond.type == :begin) && (@cond.children.size == 1)
10
15
  end
11
16
 
12
17
  def process
13
- erase_before!
14
- erase_after!
15
- rewriter.process
18
+ static_if_branch ? [erase_before_args, erase_after_args] : []
16
19
  end
17
20
 
18
21
  private
19
22
 
20
- def erase_before!
21
- rewriter.replace(range(end_pos, (total_end - end_pos)), "\n" * (total_lines - to_line))
23
+ def erase_before_args
24
+ [range(total_begin, begin_pos_before_spaces), "\n" * (from_line - total_first_line)]
25
+ end
26
+
27
+ def erase_after_args
28
+ [range(end_pos, total_end), "\n" * (total_lines - to_line)]
22
29
  end
23
30
 
24
- def erase_after!
25
- rewriter.replace(range(0, begin_pos), "\n" * (from_line - 1))
31
+ def begin_pos_before_spaces
32
+ begin_pos - count_spaces_before_first_line_of_static_if_branch
26
33
  end
27
34
 
28
35
  def begin_pos
29
- new_ast.loc.expression.begin_pos
36
+ static_if_branch.loc.expression.begin_pos
30
37
  end
31
38
 
32
39
  def end_pos
33
- new_ast.loc.expression.end_pos
40
+ static_if_branch.loc.expression.end_pos
41
+ end
42
+
43
+ def total_begin
44
+ ast.loc.expression.begin_pos
34
45
  end
35
46
 
36
47
  def total_end
@@ -38,47 +49,47 @@ module DeadCodeTerminator
38
49
  end
39
50
 
40
51
  def from_line
41
- new_ast.loc.expression.source_buffer.line_for_position(begin_pos)
52
+ @from_line ||= line_for_position_of_static_if_branch(begin_pos)
42
53
  end
43
54
 
44
55
  def to_line
45
- new_ast.loc.expression.source_buffer.line_for_position(end_pos)
56
+ line_for_position_of_static_if_branch(end_pos)
46
57
  end
47
58
 
48
59
  def total_lines
49
60
  ast.loc.last_line
50
61
  end
51
62
 
52
- def rewriter
53
- @rewriter ||= Parser::Source::TreeRewriter.new(buf)
63
+ def total_first_line
64
+ ast.loc.first_line
54
65
  end
55
66
 
56
- def range(from, len)
57
- Parser::Source::Range.new(buf, from, from + len)
67
+ def range(from, to)
68
+ Parser::Source::Range.new(buf, from, to)
58
69
  end
59
70
 
60
- def buf
61
- @buf ||= ast.loc.expression.source_buffer
71
+ # :(
72
+ def count_spaces_before_first_line_of_static_if_branch
73
+ (begin_pos - 1).downto(0).take_while do |pos|
74
+ line_for_position_of_static_if_branch(pos) == from_line
75
+ end.size
62
76
  end
63
77
 
64
- def new_ast
65
- @new_ast ||= case ast.type
66
- when :if then if_ast
67
- else ast
68
- end
78
+ def line_for_position_of_static_if_branch(pos)
79
+ static_if_branch.loc.expression.source_buffer.line_for_position(pos)
69
80
  end
70
81
 
71
- def if_ast
72
- cond, then_branch, else_branch = ast.children
82
+ def static_if_branch
83
+ return @static_if_branch if defined? @static_if_branch
73
84
 
74
85
  Cond.nodes.each do |klass|
75
86
  if (value = klass.new(env: env, ast: cond).value)
76
- return then_branch if value == Cond::Base::THEN
77
- return else_branch if value == Cond::Base::ELSE
87
+ return (@static_if_branch = then_branch) if value == Cond::Base::THEN
88
+ return (@static_if_branch = else_branch) if value == Cond::Base::ELSE
78
89
  end
79
90
  end
80
91
 
81
- ast
92
+ @static_if_branch = nil
82
93
  end
83
94
  end
84
95
  end
@@ -3,6 +3,8 @@
3
3
  module DeadCodeTerminator
4
4
  module Cond
5
5
  class Base
6
+ include ::AST::Sexp
7
+
6
8
  THEN = :then
7
9
  ELSE = :else
8
10
 
@@ -14,12 +16,6 @@ module DeadCodeTerminator
14
16
  end
15
17
 
16
18
  def value; end
17
-
18
- private
19
-
20
- def s(type, *children)
21
- Parser::AST::Node.new(type, children)
22
- end
23
19
  end
24
20
  end
25
21
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module DeadCodeTerminator
4
- VERSION = "0.2.0"
4
+ VERSION = "0.3.0"
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: dead_code_terminator
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 0.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Vlad Bokov