Skip to content

Pass explicit paths to PHPCS even when project has a custom config#207

Open
mhdarffn wants to merge 1 commit into
tighten:3.xfrom
mhdarffn:fix/dirty-phpcs-custom-config
Open

Pass explicit paths to PHPCS even when project has a custom config#207
mhdarffn wants to merge 1 commit into
tighten:3.xfrom
mhdarffn:fix/dirty-phpcs-custom-config

Conversation

@mhdarffn
Copy link
Copy Markdown

@mhdarffn mhdarffn commented May 8, 2026

Since 3.4.0, PHP_CodeSniffer ignores any paths the user passes to duster lint / duster fix whenever a custom phpcs config exists at the project root (.phpcs.xml, phpcs.xml, .phpcs.xml.dist, phpcs.xml.dist). The dirty list resolved by App\Project::paths() is correctly stored in DusterConfig, but PhpCodeSniffer::lint() and fix() short-circuit on hasCustomConfig() and call process() with an empty array, so PHPCS falls back to the <file> directives in the ruleset and scans the whole project.

This silently breaks --dirty (and --diff) for any project that has a custom phpcs config — every commit re-lints the entire codebase through pre-commit hooks instead of just the changed files.

Refactors the path resolution into a single resolvePaths() helper with three outcomes:

  • null — skip PHPCS entirely (e.g. only Blade files
    were passed explicitly; preserves PR Manually exclude Blade files from calls to PHPCS #199).
  • [] — defer to the ruleset's <file> directives
    (no explicit paths, custom config present;
    preserves existing 3.4.x behaviour).
  • array<string> — pass paths through so PHPCS uses them
    instead of the ruleset's <file> list.
    Restores --dirty / --diff / explicit
    path argument behaviour for projects with
    a custom phpcs config.

Adds a regression test (it lints only the explicit paths when project has a custom phpcs config) and pins the fall-back-to-ruleset behaviour so it does not regress in future.

Fixes #206

Since 3.4.0, PHP_CodeSniffer ignores any paths the user passes to
`duster lint` / `duster fix` whenever a custom phpcs config exists at
the project root (`.phpcs.xml`, `phpcs.xml`, `.phpcs.xml.dist`,
`phpcs.xml.dist`). The dirty list resolved by `App\Project::paths()` is
correctly stored in `DusterConfig`, but `PhpCodeSniffer::lint()` and
`fix()` short-circuit on `hasCustomConfig()` and call `process()` with
an empty array, so PHPCS falls back to the `<file>` directives in the
ruleset and scans the whole project.

This silently breaks `--dirty` (and `--diff`) for any project that has
a custom phpcs config — every commit re-lints the entire codebase
through pre-commit hooks instead of just the changed files.

Refactors the path resolution into a single `resolvePaths()` helper
with three outcomes:

- `null`             — skip PHPCS entirely (e.g. only Blade files
                       were passed explicitly; preserves PR tighten#199).
- `[]`               — defer to the ruleset's `<file>` directives
                       (no explicit paths, custom config present;
                       preserves existing 3.4.x behaviour).
- `array<string>`    — pass paths through so PHPCS uses them
                       instead of the ruleset's `<file>` list.
                       Restores `--dirty` / `--diff` / explicit
                       `path` argument behaviour for projects with
                       a custom phpcs config.

Adds a regression test (`it lints only the explicit paths when project
has a custom phpcs config`) and pins the fall-back-to-ruleset
behaviour so it does not regress in future.

Fixes tighten#206

Co-authored-by: Cursor <cursoragent@cursor.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

--dirty is silently ignored by PHPCS when project has a custom phpcs config (regression in 3.4.x)

1 participant