💅 Automatically Format PHP Code
I love to have everything organized and to keep the code as clean as possible. And to do this by hand it’s just really boring… And let’s be honest it’s also something from the past century because there are a lot of useful tools to beautifully help us keeping our beautiful code organized! 🙌
In this post, I’ll show you how do I setup my PHP projects to be automatically formatted. 👀
1. Setup Formatter
1.1. Install the package php-cs-fixer
composer require friendsofphp/php-cs-fixer
1.2. Create a .php_cs file on the root of your project
<?php
$finder = \PhpCsFixer\Finder::create()
->in(__DIR__)
->exclude(['bootstrap', 'storage', 'vendor'])
->name('*.php')
->ignoreDotFiles(true)
->ignoreVCS(true);
return PhpCsFixer\Config::create()
->setRules([
'@PSR2' => true,
'array_syntax' => ['syntax' => 'short'],
'ordered_imports' => ['sortAlgorithm' => 'length'],
'no_unused_imports' => true,
])
->setFinder($finder);
In this example, here’s what will happen:
- bootstrap, storage and vendor directories will not be formatted.
- All
*.php
files will be considered. - PRS2 rules are the ones that are going to be used!
- Arrays like
array()
will be transformed to[]
. - Import statements will be ordered by their length to give that pyramid effect.
- Unused imports will be removed.
Check the package documentation and change according your needs!
1.3. Add a script to your composer.json file
"scripts": {
"format": "vendor/bin/php-cs-fixer fix"
}
1.4. Run it
composer format
Check the following basic example!
<?phpnamespace Package\\Services;// Unwanted space here!
use Package\\Box;
// This should be the last!
use Illuminate\\Support\\Facades\\Session as LaravelSession;
use Package\\Contracts\\SomeInterface;class SessionService implements SomeInterface
{
// Unwanted space here!
public function load(): Box
{
return LaravelSession::has(Box::class)
? LaravelSession::get(Box::class)
: new Box();
}
}
- Only 1 space after namespace.
LaravelSession
use line moved to the final import because of its length.- Removed an empty line before
load
function. - Added an empty line to the end of the file.
<?phpnamespace Package\\Services;use Package\\Box;
use Package\\Contracts\\SomeInterface;
use Illuminate\\Support\\Facades\\Session as LaravelSession;class SessionService implements SomeInterface
{
public function load(): Box
{
return LaravelSession::has(Box::class)
? LaravelSession::get(Box::class)
: new Box();
}
}
2. Make it run automatically
Now you can run it using composer. But that only means you can run the command… by hand! Ideally would be to add this to your CI/CD pipeline alongside your tests! But most of the times, at least for me, I don’t have a pipeline setup for really small projects like packages.
So I just use husky-php! This is a package for PHP to work with git hooks just like NPM’s husky.
2.1. Install husky-php
composer require --dev ccinn/composer-husky-plugin ccinn/husky-php
2.2. Add the hooks to composer.json
Check the package’s documentation if you want to use other hooks! Normally I just use pre-commit
for formatting and pre-push
for testing.
{
"hooks": {
"pre-commit": "composer format",
}
}
Now when you commit your code, composer format
will run automatically! 🚀
I really hope that this is as useful for you as it was for me! 👋