Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Coding Standard Laravel Package

codeigniter/coding-standard

Official coding standard for CodeIgniter 4, built on PHP_CodeSniffer. It enforces consistent PHP code style and quality across CodeIgniter projects, with rules aligned to the framework's conventions and easy integration into Composer workflows.

View on GitHub
Deep Wiki
Context7

Getting Started

This is not a runtime library — there is no service provider, no publishable config, no Artisan command. It is a PHP CS Fixer ruleset (two of them: CodeIgniter4 and CodeIgniter4Risky) that you point a .php-cs-fixer.dist.php file at. For a Laravel developer the day-to-day value is either (a) a second opinionated preset to evaluate against Pint, or (b) the canonical style for code that must also live in a CodeIgniter 4 package.

1. Install as a dev dependency

composer require --dev codeigniter/coding-standard

This pulls in php-cs-fixer and nexusphp/cs-config; you get vendor/bin/php-cs-fixer for free.

2. Create a config at the repo root

<?php
// .php-cs-fixer.dist.php

use CodeIgniter\CodingStandard\CodeIgniter4;
use Nexus\CsConfig\Factory;
use PhpCsFixer\Finder;

$finder = Finder::create()
    ->files()
    ->in(__DIR__)
    ->exclude(['vendor', 'node_modules', 'storage', 'bootstrap/cache', 'public'])
    ->notName('*.blade.php')          // critical — see Gotchas
    ->notName('_ide_helper*.php')
    ->notPath('config/*.cache.php');

return Factory::create(new CodeIgniter4(), ['finder' => $finder])
    ->forProjects();

Swap new CodeIgniter4() for new CodeIgniter4Risky() if you want the aggressive set (it enables risky fixers such as declare_strict_types).

3. Look first at the diff, not the fix

Never run fix on a real branch before you have read the report:

vendor/bin/php-cs-fixer fix --dry-run --diff --using-cache=no src/

--diff shows the exact hunks per file; --using-cache=no guarantees you are seeing the true state rather than a stale cache. Start with one directory (app/Http, src/) so the output is reviewable.

4. Wire up composer scripts

"scripts": {
    "cs":       "php-cs-fixer fix",
    "cs:check": "php-cs-fixer fix --dry-run --diff --using-cache=no"
}

First use case: run composer cs:check against a single leaf directory of an existing Laravel app — typically app/Support or app/Domain — read the diff, and decide whether the preset is a wholesale replacement for Pint or a source of rules to cherry-pick.

Implementation Patterns

Pattern A — Adopt wholesale, retire Pint. Remove laravel/pint and its pint.json, keep only .php-cs-fixer.dist.php, and repoint every editor/CI hook at vendor/bin/php-cs-fixer. Cleanest if you actually like the CI4 ordering rules (ordered_class_elements, ordered_imports, PHP-Doc normalisation) — these are stricter than the Laravel preset and produce a noticeably more uniformly sorted class body.

Pattern B — Cherry-pick into pint.json. Pint is a PHP CS Fixer wrapper, so PHP CS Fixer fixer names work directly under rules. Read what the ruleset enables and copy only what you want:

# enumerate the rules and their config for a given ruleset
php -r 'require "vendor/autoload.php";
$r = (new CodeIgniter\CodingStandard\CodeIgniter4())->getRules();
foreach ($r as $k => $v) printf("%-45s %s\n", $k, json_encode($v));'

Then in pint.json:

{
    "preset": "laravel",
    "rules": {
        "ordered_class_elements": { "order": ["use_trait", "constant_public", "property_public", "construct", "method_public"] },
        "phpdoc_order": true,
        "phpdoc_separation": true,
        "no_superfluous_phpdoc_tags": false
    }
}

This is the highest-leverage pattern for a Laravel team: you keep Pint's ergonomics and Laravel preset while stealing the CI4 rules you actually miss.

Pattern C — Dual-target package (CI4 + Laravel in one repo). Keep two config files and two scripts so each subtree gets its native style, and let CI run both:

// .php-cs-fixer.ci4.php  → fixes src/CodeIgniter/ only, ruleset CodeIgniter4
// pint.json              → fixes everything else (Laravel preset)
"scripts": {
    "cs:ci4": "php-cs-fixer fix --config=.php-cs-fixer.ci4.php",
    "cs:app": "pint"
}

Use --path-mode=intersection when you pass explicit paths so the CLI arguments are still filtered by the Finder's excludes rather than overriding them.

Pattern D — CI gate with a dedicated, cache-less check. In GitHub Actions (or any CI), run the check step without a cache and with a machine-readable formatter so failures annotate the PR:

- run: composer install --no-interaction --prefer-dist
- run: vendor/bin/php-cs-fixer fix --dry-run --diff --using-cache=no --format=checkstyle

Keep the write-mode run (composer cs) local only — never let CI push formatted commits back to the branch, or you get surprise rebases.

Pattern E — Pre-commit on changed files only. Full-repo runs get slow past a few thousand files. Restrict to staged PHP:

vendor/bin/php-cs-fixer fix --path-mode=intersection $(git diff --cached --name-only --diff-filter=ACM | grep -E '\.php$')

Hook this into captainhook, Husky, or a PhpStorm file watcher (point PhpStorm's PHP CS Fixer inspection at .php-cs-fixer.dist.php; it honours the same file).

Pattern F — Big-bang adoption without wrecking git blame. Run the fixer once on a branch, commit only the formatting change, then record the SHA:

echo "<sha>" >> .git-blame-ignore-revs
git config blame.ignoreRevsFile .git-blame-ignore-revs

Also add /.php-cs-fixer.cache to .gitignore — the fixer writes a serialized cache of file hashes by default.

Gotchas and Tips

  • Blade templates match *.php. foo.blade.php satisfies a *.php glob, and the fixer will happily rewrite your template directives as though they were expressions. Always add ->notName('*.blade.php') (and ->notName('*.blade.php')-style rules for any generated stubs) before the first run. This is the single most common way people corrupt a Laravel repo with any PHP CS Fixer setup.
  • Pint and this package will fight each other. Both drive PHP CS Fixer with different rule sets and different caches; running pint then php-cs-fixer fix produces an endless edit war and noisy diffs in every PR. Pick one as the writer, and if you keep both, give them separate configs and separate scopes (--path-mode=intersection + distinct directories), never the same file.
  • ->forProjects() inserts a file header. The header_comment fixer rewrites the docblock at the top of every file, so your "just formatting" PR touches the whole repo. Either accept it as a one-off commit, or neutralise it: pass your own header via the options array / ->withHeader(...), or override with ->withRules(['header_comment' => false]). ->forLibrary() is the lighter alternative when you don't want a banner.
  • Risky rules need an explicit opt-in. The CodeIgniter4Risky ruleset changes runtime behaviour (declare_strict_types is the one that bites — adding it to legacy code turns silent coercions into TypeErrors). Run risky adoption as its own PR, with the full test suite green, never bundled with the cosmetic commit. If you copy risky fixers into pint.json, you must also set "risky": true there.
  • Ordering fixers create enormous diffs and merge conflicts. ordered_class_elements, ordered_imports, method_argument_space (on_multiline: ensure_fully_multiline), and class_attributes_separation will rewrite method bodies' argument lists. Land them on a quiet branch, right after a release, and tell the team to rebase or re-run the fixer rather than hand-resolving.
  • The cache lies to you. .php-cs-fixer.cache is keyed on file mtime + config hash; after a PHP upgrade, a dependency bump, or a config edit made outside the file, it can report "0 files fixed" on code that is still non-compliant. Whenever behaviour surprises you, re-run with --using-cache=no before investigating anything else.
  • Exit codes are specific, not just 0/1. --dry-run exits 8 when files need fixing (distinct from 1 for a general error, 16/32 for fixer/config failures). If you wrap the command in your own shell script, test for 8 explicitly instead of != 0, otherwise a genuine crash reads as "just needs formatting".
  • Dependency conflicts with existing fixer tooling. The package pins a php-cs-fixer major line. If your project already constrains php-cs-fixer or an older Pint, Composer will either refuse or silently downgrade you to a fixer version missing rules the ruleset references. Install it first in a scratch branch and read composer why php-cs-fixer before rolling out.
  • Debug a single rule in isolation instead of guessing. vendor/bin/php-cs-fixer describe <rule_name> prints the rule's options and examples, and vendor/bin/php-cs-fixer fix --rules=<rule_name> --dry-run --diff path/to/File.php applies just that rule. This is far faster than bisecting the whole preset when one file keeps flip-flopping.
  • Extension point is withRules() / the options array, not forking. Add or disable fixers in your own config (Factory::create(new CodeIgniter4(), $options)->withRules([...])) so upgrades stay painless. If you fork the ruleset class you inherit every upstream change as a merge conflict.
  • It is dev-only — keep it out of production images. Install with --dev and build deploy artefacts with composer install --no-dev; the fixer and its rulesets should never ship in vendor/ on a web server.
  • Don't point it at generated or vendored code. Exclude _ide_helper*.php, bootstrap/cache, storage/framework/views, and any published package stubs; the fixer will reformat them and your next php artisan ide-helper:generate will undo it, producing churn on every build.
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
abbasudo/artisan-route
mirvan/ippanel
ignibyte/aic-framework
glavweb/data-schema-bundle
glavweb/datagrid-bundle
tacticmedia/scim-server
uni-method/frame
neika-ai/sdk
adachsoft/php-code-style
pharaonic/laravel-notification-dependencies
beautinow/translug
dev-brainiac/bot-cloaked
octoberrain/html
octoberrain/extension
octoberrain/exception
octoberrain/contracts
adachsoft/api-version-bundle
cgv/localized-resource
noith/settings
kda/laravel-package