Appearance
Описание стандарта
Все пункты расставлены в порядке изменения приоритета от высшего к низшему (за исключением пункта 1, его приоритет минимальный). Если какие-то пункты противоречат друг другу - нужно использовать пункт с наивысшим приоритетом.
Код должен соответствовать стандартам PSR-2, PSR-4 и Symfony coding standards.
Модификаторы доступа
- Константам классов (интерфейсов, трейтов) всегда нужно указывать модификатор доступа. Исключение - целевая версия php < 7.1.
- В классах не должно быть методов, которые не используются (или не требуются интерфейсом). Не нужно генерировать какие-нибудь геттеры заранее. Исключение - требование интерфейса.
- Модификатор доступа по умолчанию - private. Не стоит объявлять модификатор public или protected, если метод не используется в других классах (даже если планируется его использовать в будущем. Вот когда реально потребуется - модификатор доступа можно будет изменить). Исключение - требование интерфейса.
Именование переменных
- В названии переменной нужно использовать больше одной буквы.
- Не стоит писать имена переменных транслитом. Исключение - аббревиатуры.
- Не стоит сокращать слова в названии переменных. В крайнем случае допустимы общепринятые сокращения.
- Кавычки
- По умолчанию стоит использовать одинарные кавычки. Двойные кавычки стоит использовать, если:
- внутри строки обрабатываются переменные и методы объектов
- в контенте строки встречаются одинарные кавычки
- из соображений консистентности, если в рядом стоящих строчках кода используются двойные кавычки по вышеописанным причинам
- По умолчанию стоит использовать одинарные кавычки. Двойные кавычки стоит использовать, если:
Формирование строк
- По возможности, конкатенации строк следует избегать. Формировать строку лучше используя двойные кавычки и вставку переменных прямо в строку.
- При вставке переменной в строку не нужно оборачивать её в фигурные скобки, за исключением случаем конфликта с другими символами строки.
- По возможности, вызов методов и обращения к массивам тоже следует вызывать в двойных кавычках, но тут без оборачивания в фигурные скобки уже не обойтись.
Импорт классов и функций
- Если в коде нужно получить название какого-либо класса, следует обратиться к его статической константе class. Хардкодить название класса в виде строки не допускается. Исключений два:
- необходимо предотвратить загрузку данного класса
- нужно обратиться к классу не из php-кода (например в yaml-конфиге)
- По умолчанию все классы и функции должны быть импортированы ключевыми словами "use" и "use function" соответственно. Обращение по неймспейсу в остальных частях кода (включая phpdoc-блоки) не допускается. Исключение - не php-файлы (например в yaml-конфиг).
- Классы должны быть импортированы все без исключения, включая классы из глобального пространства имен (например \Exception).
- Функции из глобального пространства имен можно не импортировать.
- В случае возникновения конфликта имен стоит создать алиасы, состоящие из неймспейса + имени класса. Количество сегментов неймспейса, которые будут задействованы для формирования алиаса, определяются программистом в каждом конкретном случае. Например для Guzzle\Http\Client можно создать алиас как HttpClient, так GuzzleHttpClient, все зависит от контекста использования, например второй случай предпочтительнее, если в коде используется http-клиент другого вендора.
- Если название импортированного класса совпадает с названием класса из глобального пространства имен, то для него в любом случае стоит создать алиас, даже если одноименный класс из глобального пространства имен в данном файле не используется и конфликта имен не возникает. Например для Guzzle\Http\Exception в любом случае нежно объявить алиас, потому что в глобальном пространстве имен существует класс \Exception, не важно, используется он в данном коде или нет.
- Если в коде нужно получить название какого-либо класса, следует обратиться к его статической константе class. Хардкодить название класса в виде строки не допускается. Исключений два:
Форматирование кода
- Вызов второго метода в цепочке (включая статические) должен быть перенесен на 2ю строку.
- Условие цикла или ифа должно быть записано в одну строку.
- Строка не должна превышать 120 символов (за редким исключением, связанным в основном с длинными именами).
- Если массив записывается в несколько строчек - после последнего элемента всегда должна стоять запятая.
- Допустим только короткий синтаксис массивов (то есть квадратные скобки).
- В сигнатуре методов и функций (включая анонимные) необходимо указывать типы. Исключение - отсутствие их поддержки в целевой версии php.
- Символ конкатенации стоит отделять пробелами с обеих сторон.
- Операторы "return", "yield" и "throw" должны отделяться от основного кода переносом строки. Исключение - они идут следующей строкой после объявления цикла, условного оператора или объявления функции.
- Первая строка php-файла содержит только оператор <?php и ничего более (включая комментарии), а так же отделяется дополнительным переносом строки от остального кода.
- Каждая логическая операция должна быть отделена от других пустой строкой.
- Не допускается разделять код более, чем одной пустой строкой
Оформление doc-блоков и комментариев
- Исходные коды не должны содержать информацию об авторе, дате и т.д. Данная информация храниться в системе контроля версий.
- Если аргумент или возвращаемое значение может быть разных типов (null тоже считается типом), то их стоит указывать через |, отделяя его пробелами м обеих сторон.
- Если метод возвращает void и это указано в сигнатуре функции, то в phpdoc-блоке аннотацию "@return void" можно опустить. Если же версия php не позволяет указать void в сигнатуре функции - то данная аннотация обязательна. Так же её стоит указать в случае, если других аннотация у функции нет.
- Каждый блок документации должен выть выравнен по длине его максимального элемента (типа, названия).
- Комментарии и описание функций пишутся на русском языке.
- Для описания функции (или метода класса) МЫСЛЕННО начинайте предложение со слова "функция", и дальше пишите её назначение. Например, "[Функция] Генерирует новое значение токена".
- В конце последнего предложения точка не ставится.
- Ключевое слово TODO пишется капсом и с двоеточием после слова TODO. Сам текст пишется как обычно.
- Не желательно писать комментарий на той же строке, что и код. Точно не стоит этого делать на одной строке с:
- управляющими потоком конструкциями (if, else, switch, case, try, catch, do, while, for, foreach, throw, yield, return, etc)
- с открывающими и закрывающими скобками любых типов (круглые, квадратные, фигурный)
- Между вызовами методов в одной цепочке
- Не стоит писать комментарии между парными конструкциями (например, между if{} и else{} или try{}, catch{} и finally{})
- Классам не нужно указывать аннотацию @package.
- В phpdoc текстовое описание следует отделять от аннотаций одной пустой строкой.
- Phpdoc методов и полей класса должен быть отделен от вышестоящего кода одной пустой строкой. Исключение - phpdoc пишется сразу после объявления класса.
- Текстовое описание поля класса в phpdoc должно располагаться выше аннотации @var и отделяться от нее одной пустой строкой.
- В функциях и методах класса phpdoc-аннотации должны располагаться в таком порядку: @param, @return, @throws. Все остальные аннотации должны находиться выше @param.
- В полях класса последней аннотацией должна быть @var, все остальные должны располагаться выше.
- При описании составного типа сначала указывается array, потом ссылочные типы (сначала классы, потом интерфейсы), и далее по убыванию количества возможных значений - string, float, int, bool, null.
- Если типом является массив однотипных элементов, то тип этих элементов так же записывается через прямую черту. Например так: "@return array | User[]".
- Если типом является коллекция (итерируемый класс) однотипных элементов, то тип этих элементов так же записывается через прямую черту. Например так: "@return UserCollection | User[]".
Объявление переменных
- Не следует переопределять уже существующую переменную. Лучше создать новую.
- Если какое-то выражение встречается более одного раза (например, обращение к одному и тому же индексу массива или вызов одного и того же метода) - нужно объявить новую переменную. Исключения - Выражение имеет побочные эффекты.
- Если какое-то выражение встречается один раз - переменную объявлять не следует. Исключение - объективное улучшение читабельности кода.
- Не следует объявлять переменные внутри конструкций if, switch, isset, empty, etc (за исключением циклов for и while), а так же при вызовах функций.