QA runs a suite of standard tools contained in the includes/generic folder. These are run from the bin/qa script via the runTool function.
The tools are run in a specific order across four phases, designed to modify code first (Phase 1), then validate (Phase 2), analyse (Phase 3), and test (Phase 4). The pipeline fails as quickly as possible.
In local development, a failed tool can be retried indefinitely. In CI, a failed tool fails the whole process.
Each tool is run by calling the runTool function.
The runTool function takes into account the platform that PHPQA detected via the detectPlatform function.
You can override any tool for your project by copying it into qaConfig/tools and editing as you see fit.
- It will first check for project level overrides in
/project/root/qaConfig/tools/{toolName}.inc.bash - Then it will look inside
includes/{detectedPlatform}/{toolName}.inc.bash - If none is found, it will fall back to
includes/generic/{toolName}.inc.bash
The platform-specific script will be run instead of the generic script. You can choose to source the generic tool in your script:
source $DIR/../includes/generic/setConfig.inc.bash
... platform-specific script contents ...These tools can modify your source files.
Rector performs automated refactoring and code upgrades. It is delivered as a committed, self-contained PHAR (vendor-phar/rector.phar) built by scripts/build-rector-phar.bash. The PHAR bundles its own extracted phpstan/phpstan, so Rector's PHPStan dependency never leaks into any consuming project's dependencies (and, being its own process, never collides with the pipeline's phpstan.phar).
The pipeline runs Rector in three stages:
- Safe Functions -- Converts standard PHP functions to their thecodingmachine/safe equivalents (which throw exceptions instead of returning false). Requires
thecodingmachine/safeas a production dependency. - PHPUnit -- Applies PHPUnit-specific rector rules to the test directory.
- PHP 8.4 -- Applies PHP 8.4 migration rules (skipped if a project-specific
rector.phporqaConfig/rector.phpis found, as it is assumed those handle version upgrades).
Default configurations:
PHP CS Fixer automatically fixes code style issues according to modern PHP standards. It runs as a PHAR from vendor-phar/php-cs-fixer.phar (not as a Composer dependency).
The default configuration includes @PHP8x4Migration rules for PHP 8.4 compatibility, including nullable type declarations.
Please see the PHPQA Coding Standards docs for configuration details.
See the PHP CS Fixer Docs for more information.
These tools validate code without modifying it.
Checks for code whose namespaces do not comply with the PSR-4 standard.
You can specify files or directories to be ignored by the validator. This is a newline-separated list of valid regex including a valid regex delimiter. For example:
#tests/bootstrap\.php#
#tests/phpstan-bootstrap\.php#
#tests/assets/.*?asset#
- Checks that
ergebnis/composer-normalizeplugin is allowed - Runs
composer diagnoseto check for issues - Runs
composer normalizeto normalizecomposer.json - Dumps the autoloader to ensure recent code changes will not cause autoloading issues
Always-on check that requires composer.json to declare an explicit type. Runs immediately
after Composer Checks. See tools/packageType.md for details.
Scans .php and .phtml files under the checked paths for a missing declare(strict_types=1).
On a read-only run it reports every offending file and fails; on a writable run it adds the
declaration to the opening <?php tag automatically (a file with no opening tag fails the gate).
There is no interactive prompt.
Very fast PHP linting process. Checks for syntax errors in your PHP files.
See the PHP Parallel Lint project page for more information.
Ensures all code dependencies are explicitly declared in composer.json. Catches use of transitive dependencies that are not directly required.
This tool runs as a PHAR from vendor-phar/composer-require-checker.phar.
Checks your README.md file and all *.md files in the docs directory. For each link found, it ensures the link target is valid -- both internal links to project files and external links to remote web pages.
Always-on check that runs first in this phase. Enforces the PR branch-naming convention (a PR
branch must use an allowed prefix — feature/, bugfix/, chore/, hotfix/ — never plan/*);
the repo's detected default branch is exempt. See CLAUDE/branch-policy.md.
Static analysis of your PHP code. Runs as a PHAR from vendor-phar/phpstan.phar.
The default configuration runs at level: max.
PHP-QA-CI bundles custom PHPStan rules (auto-loaded via extension installer) and ships with phpstan-strict-rules and phpstan-phpunit as Composer dependencies.
Please see the PHPQA PHPStan docs for full details.
See the PHPStan project page for more information about PHPStan in general.
Architecture rules (class naming, namespace layering, dependency direction). On by default; runs as
a PHAR from vendor-phar/phparkitect.phar. Disable per-project with export useArkitect=0. See
the PHPArkitect section in the README.
Always-on security baseline: fails if the native #[\SensitiveParameter] attribute is used nowhere
in src/. Opt out per-project with export useSensitiveParameterCheck=0. See
tools/sensitiveParameterUsage.md.
Runs your PHPUnit tests. PHPUnit is installed as a Composer dependency.
Please see the PHPQA PHPUnit docs for full details.
Mutation testing -- runs your PHPUnit tests but deliberately mutates your code in ways that should make your tests fail. If they don't, you "failed to kill the mutant".
Runs as a PHAR from vendor-phar/infection.phar. Requires Xdebug and code coverage enabled (useInfection=1).
Please see the PHPQA Infection docs for full details.
Generates code statistics (lines of code, complexity). Informational only -- cannot fail the pipeline.