For example, I need to check the correctness of git branch naming - it should contain ticket ID similarly to this:
module Rails
class GitBranchName < RuboCop::Cop::Cop
MSG = "Use correct branch name by pattern '{TicketID}-{Description}'. TicketID is mandatory for linking with the task tracker and should be at least 2 digits"
def on_send(node = nil)
branch = `git rev-parse --abbrev-ref HEAD`
return if starts_from_ticket_number?(branch)
p "Current branch name: '#{branch}'"
# add_offense(node, severity: :warning)
end
private
def starts_from_ticket_number?(name)
gitflow_prefixes = [:bug, :bugfix, :feature, :fix, :hotfix, :origin, :release, :wip]
name.match?(/(#{gitflow_prefixes.join('/|')})?\d{2,}/)
end
end
end
But as I see, Rubocop processes only text nodes and checks only text lines. So, is it possible to define a rule that will be run only once to check one custom check not related to code but only to business logic?
Also I've created discussion here https://github.com/rubocop/rubocop/discussions/10470
As you point out, rubocop analyzes code, either as AST nodes, or lines of text / entire files. Therefore, the answer is: it might be possible, but don't do this.
I'd recommend keeping these things separate, e.g. having rake check that runs rubocop and also runs rake check_commits, and the later checks your git commits.
I've ended up adding a custom script for checking branch naming and adding it to the CI pipeline:
bin/git_check
#!/usr/bin/env ruby
# frozen_string_literal: true
# :nocov:
class GitBranchNameValidator
MSG = "Use correct branch name by pattern '{TicketID}-{Description}'. TicketID is mandatory for linking with the task tracker and should be at least 2 digits"
class << self
def call
branch = `git rev-parse --abbrev-ref HEAD`.split("\n").first
return if starts_from_ticket_number?(branch)
puts "Current branch name: '#{branch}'"
puts MSG
exit 1
end
private
def starts_from_ticket_number?(name)
gitflow_prefixes = [:bug, :bugfix, :feature, :fix, :hotfix, :origin, :release, :wip]
name.match?(/(#{gitflow_prefixes.join('/|')})?\d{2,}/)
end
end
end
GitBranchNameValidator.call
# :nocov: