PHP-CS-Fixer для PHP: полное руководство с примерами
1. Что это и зачем нужна
PHP-CS-Fixer (PHP Coding Standards Fixer) — это мощный инструмент для автоматического форматирования PHP-кода в соответствии с заданными стандартами кодирования. Он анализирует исходный код, находит нарушения правил форматирования (отступы, пробелы, переносы строк, порядок импортов, использование коротких синтаксисов и т.д.) и исправляет их автоматически. Библиотека является незаменимым помощником в современных PHP-проектах, особенно при командной разработке.
Зачем это нужно? Во-первых, единый стиль кода в команде. Когда несколько разработчиков работают над одним проектом, каждый может иметь свои привычки форматирования. PHP-CS-Fixer устраняет эту проблему, приводя весь код к единому стандарту. Во-вторых, это экономит время на code review: вместо обсуждения отступов и пробелов разработчики могут сосредоточиться на логике и архитектуре. В-третьих, автоматическое форматирование предотвращает появление "шумовых" изменений в коммитах, когда правка одной строки приводит к изменению форматирования всего файла.
PHP-CS-Fixer поддерживает множество встроенных правил (более 100), а также позволяет создавать собственные правила. Инструмент легко интегрируется в CI/CD пайплайны, системы контроля версий (через pre-commit хуки) и IDE. Он совместим с PSR-1, PSR-2, PSR-12, Symfony, Doctrine и другими популярными стандартами кодирования.
2. Установка
PHP-CS-Fixer устанавливается через Composer — менеджер зависимостей для PHP. Рекомендуется устанавливать его глобально или как dev-зависимость в проекте.
# Установка глобально (рекомендуется для использования в любом проекте)
composer global require friendsofphp/php-cs-fixer
# Установка как dev-зависимость в конкретном проекте
composer require --dev friendsofphp/php-cs-fixer
# Проверка установки
php-cs-fixer --version
После установки глобально убедитесь, что директория ~/.composer/vendor/bin (или %USERPROFILE%\AppData\Roaming\Composer\vendor\bin на Windows) добавлена в переменную окружения PATH.
3. Быстрый старт — минимальный рабочий пример
Создайте файл example.php с "грязным" кодом:
<?php
$name = "John";
$age=25;
function greet($name){
echo "Hello, ".$name;
}
greet($name);
Теперь отформатируйте его с помощью PHP-CS-Fixer:
php-cs-fixer fix example.php --rules=@PSR12
После выполнения файл будет выглядеть так:
<?php
$name = 'John';
$age = 25;
function greet($name): void
{
echo 'Hello, '.$name;
}
greet($name);
Как видите, PHP-CS-Fixer добавил пробелы вокруг оператора присваивания, заменил двойные кавычки на одинарные (если нет интерполяции), добавил тип возврата : void, отформатировал фигурные скобки и добавил пустые строки для улучшения читаемости.
4. Основные методы/функции/классы
4.1. PhpCsFixer\Config::create()
Сигнатура: public static Config::create(): Config
Что делает: Создаёт новый экземпляр конфигурации для настройки правил форматирования.
<?php
use PhpCsFixer\Config;
$config = Config::create()
->setRules([
'@PSR12' => true,
'array_syntax' => ['syntax' => 'short'],
])
->setFinder(
PhpCsFixer\Finder::create()
->in(__DIR__ . '/src')
);
4.2. PhpCsFixer\Finder::create()
Сигнатура: public static Finder::create(): Finder
Что делает: Создаёт объект для поиска PHP-файлов, которые нужно отформатировать.
<?php
use PhpCsFixer\Finder;
$finder = Finder::create()
->in(__DIR__ . '/src') // директория для поиска
->exclude('vendor') // исключить vendor
->name('*.php') // только PHP-файлы
->notName('*.blade.php') // исключить шаблоны Blade
->ignoreDotFiles(true) // игнорировать скрытые файлы
->ignoreVCS(true); // игнорировать .git и другие VCS
4.3. PhpCsFixer\Config::setRules()
Сигнатура: public Config::setRules(array $rules): Config
Что делает: Устанавливает набор правил форматирования. Можно комбинировать готовые наборы (пресеты) и отдельные правила.
<?php
use PhpCsFixer\Config;
$config = Config::create()
->setRules([
'@PSR12' => true,
'@PhpCsFixer' => true,
'strict_param' => true,
'array_syntax' => ['syntax' => 'short'],
'ordered_imports' => ['sort_algorithm' => 'alpha'],
'no_unused_imports' => true,
'not_operator_with_successor_space' => true,
'trailing_comma_in_multiline' => ['elements' => ['arrays']],
]);
4.4. PhpCsFixer\Config::setFinder()
Сигнатура: public Config::setFinder(Finder $finder): Config
Что делает: Привязывает объект Finder к конфигурации, определяя, какие файлы будут обрабатываться.
<?php
use PhpCsFixer\Config;
use PhpCsFixer\Finder;
$finder = Finder::create()->in(__DIR__);
$config = Config::create()
->setFinder($finder)
->setRules(['@PSR12' => true]);
4.5. PhpCsFixer\Config::setFormat()
Сигнатура: public Config::setFormat(string $format): Config
Что делает: Устанавливает формат вывода отчёта о проделанной работе. Доступные форматы: 'txt', 'xml', 'json', 'junit'.
<?php
use PhpCsFixer\Config;
$config = Config::create()
->setRules(['@PSR12' => true])
->setFormat('json'); // вывод в JSON для интеграции с CI
4.6. PhpCsFixer\Config::setIndent()
Сигнатура: public Config::setIndent(string $indent): Config
Что делает: Устанавливает символ отступа. По умолчанию — 4 пробела. Можно изменить на табуляцию.
<?php
use PhpCsFixer\Config;
$config = Config::create()
->setRules(['@PSR12' => true])
->setIndent("\t"); // использовать табуляцию вместо пробелов
4.7. PhpCsFixer\Config::setLineEnding()
Сигнатура: public Config::setLineEnding(string $lineEnding): Config
Что делает: Устанавливает тип окончания строки. Возможные значения: "\n" (Unix), "\r\n" (Windows), "\r" (Mac).
<?php
use PhpCsFixer\Config;
$config = Config::create()
->setRules(['@PSR12' => true])
->setLineEnding("\r\n"); // для Windows-совместимости
4.8. PhpCsFixer\Config::setCacheFile()
Сигнатура: public Config::setCacheFile(string $cacheFile): Config
Что делает: Указывает путь к файлу кэша для ускорения повторных запусков. Кэш хранит информацию о том, какие файлы уже были отформатированы.
<?php
use PhpCsFixer\Config;
$config = Config::create()
->setRules(['@PSR12' => true])
->setCacheFile(__DIR__ . '/.php-cs-fixer.cache');
4.9. PhpCsFixer\Config::setRiskyAllowed()
Сигнатура: public Config::setRiskyAllowed(bool $isRiskyAllowed): Config
Что делает: Разрешает использование "рискованных" правил, которые могут изменить поведение кода (например, строгая типизация, удаление неиспользуемых переменных).
<?php
use PhpCsFixer\Config;
$config = Config::create()
->setRules([
'@PSR12' => true,
'declare_strict_types' => true, // рискованное правило
])
->setRiskyAllowed(true);
4.10. PhpCsFixer\Config::setUsingLinter()
Сигнатура: public Config::setUsingLinter(bool $usingLinter): Config
Что делает: Включает или отключает синтаксическую проверку PHP-файлов перед форматированием. По умолчанию включено.
<?php
use PhpCsFixer\Config;
$config = Config::create()
->setRules(['@PSR12' => true])
->setUsingLinter(false); // отключить линтер для ускорения
5. Реальный практический пример (100-200 строк кода)
Создадим полный конфигурационный файл .php-cs-fixer.dist.php для реального проекта и продемонстрируем его использование.
<?php
/**
* Конфигурация PHP-CS-Fixer для проекта "MyApp"
*
* @see https://github.com/PHP-CS-Fixer/PHP-CS-Fixer
*/
use PhpCsFixer\Config;
use PhpCsFixer\Finder;
// Настройка поиска файлов
$finder = Finder::create()
->in([
__DIR__ . '/src',
__DIR__ . '/tests',
__DIR__ . '/config',
])
->exclude([
'vendor',
'var',
'node_modules',
'storage',
])
->notName([
'*.blade.php',
'*.twig',
'*.html.twig',
'*.xml',
'*.yml',
'*.yaml',
])
->notPath([
'tests/Fixtures',
'tests/Support',
])
->ignoreDotFiles(true)
->ignoreVCS(true);
// Определение правил
$rules = [
// Базовые стандарты PSR
'@PSR12' => true,
'@PSR12:risky' => true,
'@PhpCsFixer' => true,
'@PhpCsFixer:risky' => true,
// Строгая типизация
'declare_strict_types' => true,
// Импорты
'ordered_imports' => [
'sort_algorithm' => 'alpha',
'imports_order' => [
'class',
'function',
'const',
],
],
'no_unused_imports' => true,
'single_import_per_statement' => true,
'global_namespace_import' => [
'import_classes' => true,
'import_constants' => true,
'import_functions' => true,
],
// Массивы
'array_syntax' => ['syntax' => 'short'],
'trailing_comma_in_multiline' => [
'elements' => ['arrays', 'arguments', 'parameters'],
],
'no_multiline_whitespace_around_double_arrow' => true,
// Строки
'single_quote' => true,
'heredoc_indentation' => true,
'escape_implicit_backslashes' => true,
// Пробелы и отступы
'no_extra_blank_lines' => [
'tokens' => [
'break',
'case',
'continue',
'curly_brace_block',
'default',
'extra',
'parenthesis_brace_block',
'return',
'square_brace_block',
'switch',
'throw',
'use',
],
],
'no_whitespace_in_blank_line' => true,
'blank_line_before_statement' => [
'statements' => ['return', 'throw', 'try', 'if', 'declare'],
],
// Функции и методы
'void_return' => true,
'return_type_declaration' => [
'space_before' => 'none',
],
'native_function_invocation' => [
'include' =