Class: RuboCop::Cop::Style::RbsInline::RequireRbsInlineComment

Inherits:
Base
  • Object
show all
Extended by:
AutoCorrector
Includes:
RangeHelp
Defined in:
lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb,
sig/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rbs

Overview

Checks for the presence or absence of # rbs_inline: magic comment.

RBS::Inline supports two modes: opt-in (requires # rbs_inline: enabled) and opt-out (processes all files by default). This cop enforces consistency in which mode your codebase uses.

Examples:

EnforcedStyle: always (default)

# bad
# (no rbs_inline comment)
class Foo
end

# good
# rbs_inline: enabled
class Foo
end

# good
# rbs_inline: disabled
class Foo
end

EnforcedStyle: never

# bad
# rbs_inline: enabled
class Foo
end

# good
# rbs_inline: disabled
class Foo
end

# good
# (no rbs_inline comment)
class Foo
end

Constant Summary collapse

MSG_MISSING =

Returns:

  • (::String)
'Missing `# rbs_inline:` magic comment.'
MSG_FORBIDDEN =

Returns:

  • (::String)
'Remove `# rbs_inline:` magic comment.'

Instance Method Summary collapse

Instance Method Details

#check_always_style(magic_comment) ⇒ void

This method returns an undefined value.

Parameters:



79
80
81
82
83
84
85
86
87
88
89
90
# File 'lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb', line 79

def check_always_style(magic_comment) #: void
  # disabled is already filtered out by early return
  # magic_comment is either nil or enabled
  return if magic_comment

  # Insert after the first comment block or at the beginning of the file
  insert_position = find_insert_position
  add_offense(first_line_range, message: MSG_MISSING) do |corrector|
    insert_range = Parser::Source::Range.new(processed_source.buffer, insert_position, insert_position)
    corrector.insert_before(insert_range, "# rbs_inline: enabled\n")
  end
end

#check_never_style(magic_comment) ⇒ void

This method returns an undefined value.

Parameters:



93
94
95
96
97
98
99
100
101
102
103
# File 'lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb', line 93

def check_never_style(magic_comment) #: void
  # disabled is already filtered out by early return
  # magic_comment is either nil or enabled
  return unless magic_comment

  add_offense(magic_comment.source_range, message: MSG_FORBIDDEN) do |corrector|
    # Remove the entire line including newline
    range = range_with_surrounding_space(magic_comment.source_range, side: :right, newlines: true)
    corrector.remove(range)
  end
end

#disabled?(magic_comment) ⇒ Boolean

Parameters:

Returns:

  • (Boolean)


74
75
76
# File 'lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb', line 74

def disabled?(magic_comment) #: bool
  magic_comment&.text&.match?(/\A# rbs_inline: disabled\R?\z/) || false
end

#find_insert_positionInteger

: Integer

Returns:

  • (Integer)


105
106
107
108
109
110
111
112
113
114
# File 'lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb', line 105

def find_insert_position #: Integer
  # Find the end of the first comment block (e.g., magic comments)
  # and insert after it
  first_comment = processed_source.comments.first
  # If the first comment doesn't exist or doesn't start at line 1, insert at the beginning
  return 0 unless first_comment&.source_range&.first_line == 1

  last_comment_in_block = find_last_comment_in_first_block
  last_comment_in_block.source_range.end_pos + 1
end

#find_last_comment_in_first_blockParser::Source::Comment

: Parser::Source::Comment



116
117
118
119
120
121
122
123
124
125
126
127
128
# File 'lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb', line 116

def find_last_comment_in_first_block #: Parser::Source::Comment
  comments = processed_source.comments
  last_idx = 0

  comments.each_cons(2).with_index do |pair, idx|
    current, following = pair #: [Parser::Source::Comment, Parser::Source::Comment]
    break unless current.source_range.last_line + 1 == following.source_range.first_line

    last_idx = idx + 1
  end

  comments[last_idx] || raise
end

#find_rbs_inline_magic_commentParser::Source::Comment?

: Parser::Source::Comment?

Returns:



67
68
69
70
71
# File 'lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb', line 67

def find_rbs_inline_magic_comment #: Parser::Source::Comment?
  processed_source.comments.find do |comment|
    comment.text.match?(/\A# rbs_inline: (enabled|disabled)\R?\z/)
  end
end

#first_line_rangeParser::Source::Range

: Parser::Source::Range

Returns:

  • (Parser::Source::Range)


134
135
136
137
138
139
# File 'lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb', line 134

def first_line_range #: Parser::Source::Range
  # Find the first line of actual code (not comment-only lines)
  # If there's no AST (e.g., file with only comments), use the first line
  first_line = processed_source.ast&.source_range&.first_line || 1
  processed_source.buffer.line_range(first_line)
end

#on_new_investigationvoid

This method returns an undefined value.

: void



52
53
54
55
56
57
58
59
60
61
62
63
# File 'lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb', line 52

def on_new_investigation #: void
  return if processed_source.buffer.source.empty?

  magic_comment = find_rbs_inline_magic_comment
  return if disabled?(magic_comment)

  if style == :always
    check_always_style(magic_comment)
  elsif style == :never
    check_never_style(magic_comment)
  end
end

#styleSymbol

: Symbol

Returns:

  • (Symbol)


130
131
132
# File 'lib/rubocop/cop/style/rbs_inline/require_rbs_inline_comment.rb', line 130

def style #: Symbol
  cop_config['EnforcedStyle']&.to_sym || :always
end