One Ruby-file rule: lint gates classify changed files with Codebase#ruby? (DRY row F7) #772

Closed
opened 2026-09-27 14:53:38 +00:00 by jared · 2 comments
Owner

Problem

Two gates classify "Ruby file" by different rules. The diff-test path uses Project::RubyFile.ruby? (plugins/os-sdlc/lib/os_sdlc/adapter/project/ruby_file.rb:10-16), which accepts .rb files and extensionless files with a Ruby shebang. The lint gates use repo.changed_paths (plugins/os-sdlc/lib/os_sdlc/query/gate/commands.rb:59-61) whose default glob is "*.rb" (adapter/git/repo.rb:50). A changed bin/ script counts as code for diff-test and is invisible to rubocop. The 17 extensionless Ruby scripts in plugins/os-sdlc/bin, including the eight os-sdlc-* dispatch scripts from ADR-0232, are production code with no lint. The lint definition was never updated when the other production-code definitions were. The user ruled on 2026-09-27 (CRC slice-plan P2 behavior half, ruling S7, audit finding 9) that the shebang rule wins.

Reproduce

change plugins/os-sdlc/bin/os-sdlc-gate; run the lint gate; the file is absent from the rubocop file list while the diff-test gate lists it.

Approach

Required work:

  1. Add Project::Codebase#ruby?(path) delegating to RubyFile.ruby? with the project path joined; Changes#ruby_file? calls it.
  2. Add Changes#ruby_paths: changed paths filtered by ruby?.
  3. Set Gate::Commands#diffed_ruby_files to changes.ruby_paths; remove the "*.rb" default glob from changed_paths if it has no other sender.
  4. Run rubocop on all 17 plugins/os-sdlc/bin scripts first; fix offenses in this ticket so the gate stays green.
  5. Close DRY row F7 in docs/crc/os-sdlc/slice-plan.md.

Acceptance criteria

  1. Given a changed extensionless file with a Ruby shebang under bin/, when the lint gate runs, then rubocop receives that file.
  2. Given a changed .rb file, when the lint gate runs, then behavior is unchanged.
  3. Given the lib tree, when grepped for ".rb" and shebang checks, then exactly one classifier exists, RubyFile.ruby?, reached through Codebase#ruby?.

Owner sketch

class Project::Codebase
  def ruby?(path) = RubyFile.ruby?(File.join(@path, path))
end
class Project::Changes
  def ruby_paths = changed_paths.select { |p| @project.codebase.ruby?(p) }
end

Origin

  • Trigger: CRC session 11 user ruling, 2026-09-27
  • Session: dffd2906-eb6c-4251-a2e8-ba46af6fc54e
  • Transcript: /home/jared/.claude/projects/-home-jared-dev-cc-os--claude-worktrees-crc-pass-os-sdlc/dffd2906-eb6c-4251-a2e8-ba46af6fc54e.jsonl
  • Ticket-skeptic verdict: n/a, user-approved ticket
  • Where: plugins/os-sdlc/lib/os_sdlc/query/gate/commands.rb
## Problem Two gates classify "Ruby file" by different rules. The diff-test path uses `Project::RubyFile.ruby?` (plugins/os-sdlc/lib/os_sdlc/adapter/project/ruby_file.rb:10-16), which accepts `.rb` files and extensionless files with a Ruby shebang. The lint gates use `repo.changed_paths` (plugins/os-sdlc/lib/os_sdlc/query/gate/commands.rb:59-61) whose default glob is `"*.rb"` (adapter/git/repo.rb:50). A changed `bin/` script counts as code for diff-test and is invisible to rubocop. The 17 extensionless Ruby scripts in plugins/os-sdlc/bin, including the eight os-sdlc-* dispatch scripts from ADR-0232, are production code with no lint. The lint definition was never updated when the other production-code definitions were. The user ruled on 2026-09-27 (CRC slice-plan P2 behavior half, ruling S7, audit finding 9) that the shebang rule wins. ## Reproduce change plugins/os-sdlc/bin/os-sdlc-gate; run the lint gate; the file is absent from the rubocop file list while the diff-test gate lists it. ## Approach Required work: 1. Add `Project::Codebase#ruby?(path)` delegating to `RubyFile.ruby?` with the project path joined; `Changes#ruby_file?` calls it. 2. Add `Changes#ruby_paths`: changed paths filtered by `ruby?`. 3. Set `Gate::Commands#diffed_ruby_files` to `changes.ruby_paths`; remove the `"*.rb"` default glob from `changed_paths` if it has no other sender. 4. Run rubocop on all 17 plugins/os-sdlc/bin scripts first; fix offenses in this ticket so the gate stays green. 5. Close DRY row F7 in docs/crc/os-sdlc/slice-plan.md. ## Acceptance criteria 1. Given a changed extensionless file with a Ruby shebang under bin/, when the lint gate runs, then rubocop receives that file. 2. Given a changed `.rb` file, when the lint gate runs, then behavior is unchanged. 3. Given the lib tree, when grepped for `".rb"` and shebang checks, then exactly one classifier exists, `RubyFile.ruby?`, reached through `Codebase#ruby?`. ## Owner sketch ```ruby class Project::Codebase def ruby?(path) = RubyFile.ruby?(File.join(@path, path)) end class Project::Changes def ruby_paths = changed_paths.select { |p| @project.codebase.ruby?(p) } end ``` ## Origin - Trigger: CRC session 11 user ruling, 2026-09-27 - Session: dffd2906-eb6c-4251-a2e8-ba46af6fc54e - Transcript: /home/jared/.claude/projects/-home-jared-dev-cc-os--claude-worktrees-crc-pass-os-sdlc/dffd2906-eb6c-4251-a2e8-ba46af6fc54e.jsonl - Ticket-skeptic verdict: n/a, user-approved ticket - Where: plugins/os-sdlc/lib/os_sdlc/query/gate/commands.rb
Author
Owner

Work started on branch crc-pass-os-sdlc, session dffd2906.

Work started on branch crc-pass-os-sdlc, session dffd2906.
Author
Owner

Resolution

Done: Added Project::Codebase#ruby? (shebang-aware via RubyFile.ruby?), Changes#ruby_paths, and Gate::Commands#diffed_ruby_files now returns changes.ruby_paths; Repo#changed_paths default glob removed. DRY row F7 closed in slice-plan.md.

Evidence: Commit ebca6544 on branch crc-pass-os-sdlc; new test commands_rubocop_procman_test.rb asserts a changed extensionless shebang script reaches the lint command; suite 1311 runs, 0 failures.

Follow-ups: bin/move-map-0222 and bin/move-tests-0222 carry 31 design-level rubocop offenses; they are the finished #737 movers and are candidates for deletion, raised to the user this session rather than ticketed.

## Resolution **Done:** Added Project::Codebase#ruby? (shebang-aware via RubyFile.ruby?), Changes#ruby_paths, and Gate::Commands#diffed_ruby_files now returns changes.ruby_paths; Repo#changed_paths default glob removed. DRY row F7 closed in slice-plan.md. **Evidence:** Commit ebca6544 on branch crc-pass-os-sdlc; new test commands_rubocop_procman_test.rb asserts a changed extensionless shebang script reaches the lint command; suite 1311 runs, 0 failures. **Follow-ups:** bin/move-map-0222 and bin/move-tests-0222 carry 31 design-level rubocop offenses; they are the finished #737 movers and are candidates for deletion, raised to the user this session rather than ticketed.
jared closed this issue 2026-09-27 14:59:06 +00:00
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set

Reference
jared/cc-os#772
No description provided.