Class: Glib::Test::FullSuiteRubocop
- Inherits:
-
ActiveSupport::TestCase
- Object
- ActiveSupport::TestCase
- Glib::Test::FullSuiteRubocop
- Defined in:
- lib/glib/test/full_suite_rubocop.rb
Overview
Suite-wide RuboCop auto-remediation, lifted from the per-project
test/linters/rubocop_test.rb convention (originated in neowork-str) so
projects get it from the gem via a CONSCIOUS opt-in: include
Glib::Test::RubocopGuards once in the test setup. Never auto-require
this from Glib::TestHelpers — that would enable a file-rewriting test
in every project without a decision. It lints the WHOLE repo, so files
nobody touches cannot silently accumulate offenses.
Runs rubocop -a (safe autocorrect), which REWRITES files on disk to
fix offenses, then asserts nothing remains AND nothing was rewritten.
The mutation is deliberate (the repo's auto-remediation convention —
i18n-tasks normalize runs the same way): a run that dirties a file is
reported as a FAILURE so the rewrite cannot go unnoticed — that is the
drift signal. Do NOT strip the -a; review the diff, keep the corrected
output, and re-run. If a long-passing test suddenly breaks, investigate
WHY first: usually a non-canonical file was committed, or a rubocop
version bump changed a cop's rules.
It self-registers with Minitest, so it runs on EVERY rails test
invocation, single-file runs included. That is cheap on purpose: RuboCop
caches per-file results, so a full-repo run on an unchanged tree costs
about a second on a mid-size app.
Deliberately does NOT skip under ENV: the local rails-test wrapper sets CI=true, and skipping here would silence this layer exactly where it runs. Opt out per-run with SKIP_FULL_SUITE_RUBOCOP=1.
Constant Summary collapse
- OFFENSE_LINE =
--format simpleoffense lines: "C: 12: 3: [Correctable] Cop/Name: message" (line/column right-aligned to width 3, so the padding is 0-2 spaces). /^[A-Z]: *\d+: *\d+: /
Instance Method Summary collapse
Instance Method Details
#test_rubocop_autocorrect_then_clean ⇒ Object
38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 |
# File 'lib/glib/test/full_suite_rubocop.rb', line 38 def test_rubocop_autocorrect_then_clean skip 'opted out via SKIP_FULL_SUITE_RUBOCOP' if ENV['SKIP_FULL_SUITE_RUBOCOP'] == '1' # `scrub`: stderr is merged in, and one invalid byte would turn the # scans below into an ArgumentError instead of a lint failure. output = `bundle exec rubocop -a --format simple 2>&1`.scrub clean = $CHILD_STATUS.success? # Three distinct outcomes hide in one output, and each needs a # different action — the message must say which, or an agent told # only "offenses detected" reaches for a `rubocop:disable`: # [Corrected] -a already rewrote it on disk (exit 0 if that's all) # [Correctable] survived -a because only the UNSAFE -A can fix it # neither no autocorrect exists — semantic, read the cop # Counted on the offense LINES only, so a cop message that happens to # contain a marker cannot shift a bucket. offenses = output.lines.grep(OFFENSE_LINE) corrected = offenses.count { |line| line.include?('[Corrected]') } unsafe = offenses.count { |line| line.include?('[Correctable]') } semantic = offenses.size - corrected - unsafe # A Proc message is built only on failure (Minitest calls it lazily). assert(clean && corrected.zero?, -> { (output, corrected: corrected, unsafe: unsafe, semantic: semantic) }) end |