Class: Shirobai::Cop::Layout::EmptyLineBetweenDefs

Inherits:
RuboCop::Cop::Base
  • Object
show all
Extended by:
RuboCop::Cop::AutoCorrector
Includes:
RuboCop::Cop::RangeHelp
Defined in:
lib/shirobai/cop/layout/empty_line_between_defs.rb

Overview

Drop-in Rust reimplementation of ‘Layout/EmptyLineBetweenDefs`.

Rust walks the AST, reproduces the stock cop’s ‘on_begin` over every parser-gem `begin` group (a `StatementsNode` with >= 2 children, plus the `kwbegin` / rescue handler bodies), runs `check_defs` over each adjacent pair of definition candidates (method / class / module / `DefLikeMacros` macro), and returns, per offense, the second member’s ‘def_location` range, the formatted message and the autocorrect: an `insert` flag plus the `newline_pos` and the line count `n`. Ruby applies the correction with the same two `RangeHelp#range_between` arms stock uses (`insert_after` a `“n” * n`, or `remove` the surplus newlines).

The offenses come from the per-file bundled run (‘Shirobai::Dispatch`); the autocorrect re-passes re-investigate a fresh `ProcessedSource`, which recomputes the bundle from scratch, so this cop keeps no cross-pass state and is always bundle eligible.

Class Method Summary collapse

Instance Method Summary collapse

Class Method Details

.badgeObject



27
# File 'lib/shirobai/cop/layout/empty_line_between_defs.rb', line 27

def self.badge = RuboCop::Cop::Badge.parse(cop_name)

.bundle_args(config) ⇒ Object

Packed args for the bundled run: nums ‘[method_defs, class_defs, module_defs, allow_adjacent_one_line_defs, minimum_empty_lines, maximum_empty_lines]` and the `DefLikeMacros` list.



32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
# File 'lib/shirobai/cop/layout/empty_line_between_defs.rb', line 32

def self.bundle_args(config)
  cop_config = config.for_badge(badge)
  numbers = Array(cop_config["NumberOfEmptyLines"] || 1)
  [
    [
      cop_config["EmptyLineBetweenMethodDefs"] ? 1 : 0,
      cop_config["EmptyLineBetweenClassDefs"] ? 1 : 0,
      cop_config["EmptyLineBetweenModuleDefs"] ? 1 : 0,
      cop_config["AllowAdjacentOneLineDefs"] ? 1 : 0,
      numbers.first,
      numbers.last
    ],
    Array(cop_config.fetch("DefLikeMacros", [])).map(&:to_s)
  ]
end

.cop_nameObject



26
# File 'lib/shirobai/cop/layout/empty_line_between_defs.rb', line 26

def self.cop_name = "Layout/EmptyLineBetweenDefs"

Instance Method Details

#on_new_investigationObject



48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
# File 'lib/shirobai/cop/layout/empty_line_between_defs.rb', line 48

def on_new_investigation
  buffer = processed_source.buffer
  off = SourceOffsets.for(processed_source.raw_source)

  offenses_for_source.each do |start, fin, message, insert, pos, n|
    range = Parser::Source::Range.new(buffer, off[start], off[fin])
    add_offense(range, message: message) do |corrector|
      # `Layout/EmptyLineBetweenDefs#autocorrect`. `pos` is the byte
      # `newline_pos`; convert through `SourceOffsets` so the
      # `range_between` indices are character offsets like the stock
      # corrector's.
      cpos = off[pos]
      if insert
        where_to_insert = range_between(cpos, cpos + 1)
        corrector.insert_after(where_to_insert, "\n" * n)
      else
        corrector.remove(range_between(cpos, cpos + n))
      end
    end
  end
end