Class: RuboCop::Cop::Chromebrew::RedundantVersionAdjustment

Inherits:
Base
  • Object
show all
Extended by:
AutoCorrector
Defined in:
lib/rubocop/cop/chromebrew/redundant_version_adjustment.rb

Overview

Adjustments to the version should change the version.

Examples:

# good
version '1.0.0-1'
git_hashtag version.split('-').first

# bad
version '2.3'
git_hashtag version.split('-').first

# good
version '2.3'
git_hashtag version

Constant Summary collapse

MSG =
'This version adjustment does not actually change the version.'
@@mappings =
{}

Instance Method Summary collapse

Instance Method Details

#find_package_version?(node) ⇒ Object



30
31
32
# File 'lib/rubocop/cop/chromebrew/redundant_version_adjustment.rb', line 30

def_node_matcher :find_package_version?, <<~PATTERN
  (class (const nil? $_) (const nil? {:Autotools | :CMake | :Meson | :PERL | :Package | :Pip | :Python | :Qmake | :RUBY | :RUST}) `(send nil? :version (str $_)))
PATTERN

#on_class(node) ⇒ Object

Find and store the original version variable of this package.



37
38
39
40
41
42
43
# File 'lib/rubocop/cop/chromebrew/redundant_version_adjustment.rb', line 37

def on_class(node)
  return unless find_package_version?(node)

  package, version = find_package_version?(node)

  @@mappings[package] = version
end

#on_send(node) ⇒ Object



45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
# File 'lib/rubocop/cop/chromebrew/redundant_version_adjustment.rb', line 45

def on_send(node)
  # We're only interested in nodes that are working with the version variable.
  return unless version_adjustment?(node)

  # Ensure the node we're processing here is a version adjustment in the format we expect.
  return unless node.source.start_with?('version')

  # Retrieve the original version variable of this package.
  original_version = @@mappings[node.parent_module_name&.to_sym]
  return if original_version.nil?

  # Some packages, such as gcc_lib, use version constants from other packages (gcc_build, in this case).
  # These packages are rare enough that it isn't worth the added complexity that loading those dependent packages would create,
  # so here we just catch and ignore the NameError that results from evaluating the external version constants.
  begin
    # Check if the modifications in this node actually change the version of the package.
    return unless eval(node.source.sub('version', "'#{original_version}'")) == original_version
  rescue NameError
    return
  end

  # If this node doesn't actually modify the version, remove every part of it apart from the literal 'version' at the start of it.
  add_offense(node.source_range.adjust(begin_pos: 'version'.length)) do |corrector|
    corrector.remove(node.source_range.adjust(begin_pos: 'version'.length))
  end
end

#version_adjustment?(node) ⇒ Object



25
26
27
# File 'lib/rubocop/cop/chromebrew/redundant_version_adjustment.rb', line 25

def_node_matcher :version_adjustment?, <<~PATTERN
  (send `(send nil? :version) ...)
PATTERN