Метадокумент PSR-4
1. Краткое содержание
Цель состоит в том, чтобы указать правила для интероперабельного автозагрузчика PHP, который сопоставляет пространства имен с путями файловой системы и может сосуществовать с любым другим SPL. зарегистрированный автозагрузчик. Это будет дополнением, а не заменой, ПСР-0.
2. Зачем беспокоиться?
История PSR-0
Стандарт именования и автозагрузки классов PSR-0 вырос из широкого принятие соглашения Horde/PEAR в условиях ограничений PHP 5.2 и предыдущий. При таком соглашении существовала тенденция помещать все исходные классы PHP в одном главном каталоге, используя символы подчеркивания в имени класса для обозначения псевдопространства имен, например:
/path/to/src/
VendorFoo/
Bar/
Baz.php # VendorFoo_Bar_Baz
VendorDib/
Zim/
Gir.php # Vendor_Dib_Zim_Gir
С выпуском PHP 5.3 и наличием собственных пространств имен PSR-0 был введен, чтобы разрешить как старый режим подчеркивания Horde/PEAR *, так и * использование новой нотации пространства имен. Подчеркивания по-прежнему разрешены в классе имя, чтобы упростить переход от старого именования пространства имен к новому именованию, и тем самым способствовать более широкому внедрению.
/path/to/src/
VendorFoo/
Bar/
Baz.php # VendorFoo_Bar_Baz
VendorDib/
Zim/
Gir.php # VendorDib_Zim_Gir
Irk_Operation/
Impending_Doom/
V1.php
V2.php # Irk_Operation\Impending_Doom\V2
Эта структура во многом обусловлена тем фактом, что установщик PEAR переместился исходные файлы из пакетов PEAR в один центральный каталог.
А вот и composer
В Composer источники пакетов больше не копируются в один глобальный расположение. Они используются из места их установки и не перемещаются вокруг. Это означает, что в Composer нет «единого главного каталога» для Исходники PHP как с PEAR. Вместо этого есть несколько каталогов; каждый package находится в отдельном каталоге для каждого проекта.
Чтобы соответствовать требованиям PSR-0, это приводит к тому, что пакеты Composer выглядят так:
vendor/
vendor_name/
package_name/
src/
Vendor_Name/
Package_Name/
ClassName.php # Vendor_Name\Package_Name\ClassName
tests/
Vendor_Name/
Package_Name/
ClassNameTest.php # Vendor_Name\Package_Name\ClassNameTest
Каталоги «src» и «tests» должны включать имена каталогов поставщиков и пакетов. Это артефакт соответствия PSR-0.
Многие находят эту структуру более глубокой и более повторяющейся, чем необходимо. Это предложение предполагает, что дополнительный или заменяющий PSR был бы полезен, чтобы мы могли иметь пакеты, которые больше похожи на следующие:
vendor/
vendor_name/
package_name/
src/
ClassName.php # Vendor_Name\Package_Name\ClassName
tests/
ClassNameTest.php # Vendor_Name\Package_Name\ClassNameTest
Это потребовало бы реализации того, что первоначально называлось «автозагрузкой, ориентированной на пакеты» (в отличие от традиционной «автозагрузки напрямую из класса в файл»).
Пакетно-ориентированная автозагрузка
Сложно реализовать пакетно-ориентированную автозагрузку с помощью расширения или поправки к PSR-0, потому что PSR-0 не допускает промежуточного пути между любыми частями имени класса. Это означает, что реализация пакетно-ориентированного автозагрузчика будет сложнее, чем PSR-0. Тем не менее, это позволит использовать более чистые пакеты.
Первоначально были предложены следующие правила:
-
Разработчики ДОЛЖНЫ использовать как минимум два уровня пространства имен: имя поставщика и имя пакета внутри этого поставщика. (Эта комбинация двух имен верхнего уровня далее называется именем пакета поставщика или пространством имен пакета поставщика.)
-
Разработчики ДОЛЖНЫ разрешать инфикс пути между пространством имен пакета поставщика и остатком полного имени класса.
-
Пространство имен vendor-package МОЖЕТ сопоставляться с любым каталогом. Оставшаяся часть полного имени класса ДОЛЖНА сопоставлять имена пространств имен с каталогами с одинаковыми именами и ДОЛЖНА сопоставлять имя класса с файлом с таким же именем, оканчивающимся на .php.
Обратите внимание, что это означает конец символа подчеркивания в качестве разделителя каталогов в имени класса. Кто-то может подумать, что символы подчеркивания должны соблюдаться, как и в PSR-0, но, учитывая, что их присутствие в этом документе относится к переходу от PHP 5.2 и предыдущего псевдопространства имен, их также можно удалить здесь.
3. Масштаб
3.1 Цели
-
Сохраните правило PSR-0, согласно которому разработчики ДОЛЖНЫ использовать как минимум два уровня пространства имен: имя поставщика и имя пакета внутри этого поставщика.
-
Разрешить инфикс пути между пространством имен пакета поставщика и оставшейся частью полного имени класса.
-
Разрешить пространство имен поставщика-пакета МОЖЕТ сопоставляться с любым каталогом, возможно, с несколькими каталогами.
-
Завершить использование знаков подчеркивания в именах классов в качестве разделителей каталогов.
3.2 Нецели
- Предоставьте общий алгоритм преобразования для неклассовых ресурсов
4. Подходы
4.1 Выбранный подход
Этот подход сохраняет ключевые характеристики PSR-0, но устраняет необходимость в более глубоких структурах каталогов. Кроме того, он определяет некоторые дополнительные правила, которые явно делают реализации более совместимыми.
Хотя это и не связано с отображением каталогов, окончательный проект также указывает, как автозагрузчики должны обрабатывать ошибки. В частности, он запрещает создавать исключения или вызывать ошибки. Причина двоякая.
-
Автозагрузчики в PHP специально спроектированы так, чтобы их можно было стекировать, поэтому, если один автозагрузчик не может загрузить класс, у другого есть шанс это сделать. Если автозагрузчик запускает критическое состояние ошибки, это нарушает эту совместимость.
-
class_exists()
иinterface_exists()
разрешают «не найдено даже после попытки автозагрузки» как законный, нормальный вариант использования. Автозагрузчик, выбрасывающий исключения, делаетclass_exists()
непригодным для использования, что совершенно неприемлемо с точки зрения совместимости. Автозагрузчики, которые хотят предоставить дополнительную отладочную информацию в случае, если класс не найден, должны вместо этого делать это с помощью ведения журнала либо в совместимом с PSR-3 регистраторе, либо иным образом.
Плюсы:
-
Более мелкие структуры каталогов
-
Более гибкое расположение файлов
-
Предотвращает использование подчеркивания в имени класса в качестве разделителя каталогов.
-
Делает реализации более интероперабельными
Минусы:
- Больше невозможно, как в PSR-0, просто проверить имя класса, чтобы определить, где оно находится в файловой системе (соглашение «класс-файл», унаследованное от Horde/PEAR).
4.2 Альтернатива: оставайтесь только с PSR-0
Оставаться только с PSR-0, хотя это и разумно, оставляет нас с относительно более глубокими структурами каталогов.
Плюсы:
- Нет необходимости менять чьи-либо привычки или реализации
Минусы:
-
Оставляет нас с более глубокими структурами каталогов
-
Оставляет нас с символами подчеркивания в имени класса, которые считаются разделителями каталогов.
4.3 Альтернатива: разделить автозагрузку и трансформацию
Бо Сименсен и другие предположили, что алгоритм преобразования может быть отделен от предложения по автозагрузке, чтобы на правила преобразования можно было ссылаться в других предложениях. После выполнения работы по их разделению, последующего опроса и некоторого обсуждения, комбинированная версия (т. е. правила преобразования, встроенные в предложение автозагрузчика) была признана предпочтительной.
Плюсы:
- На правила преобразования можно ссылаться отдельно в других предложениях.
Минусы:
- Не соответствует пожеланиям респондентов опроса и некоторых сотрудников
4.4 Альтернатива: используйте более императивную и описательную речь
После того, как Спонсор отозвал второе голосование после того, как услышал от нескольких избирателей +1, что они поддержали идею, но не согласились (или не поняли) с формулировкой предложения, был период, в течение которого предложение, за которое проголосовали, было расширено за счет большего повествования и несколько более императивных формулировок. Этот подход был осужден громким меньшинством участников. Через некоторое время Бо Сименсен начал экспериментальную доработку с прицелом на PSR-0; Редактор и спонсоры поддержали этот более краткий подход и отдали предпочтение версии, которая сейчас находится на рассмотрении, написанной Полом М. Джонсом и подготовленной многими.
Примечание о совместимости с PHP 5.3.2 и ниже
Версии PHP до 5.3.3 не удаляют начальный разделитель пространств имен, поэтому ответственность за это ложится на реализацию. Если не удалить начальный разделитель пространства имен, это может привести к непредвиденному поведению.
5. Люди
5.1 Редактор
- Пол М. Джонс, Солар/Аура
5.2 Спонсоры
- Фил Стерджен, PyroCMS (координатор)
- Ларри Гарфилд, Drupal
5.3 Участники
- Андреас Хеннингс
- Бернхард Шусек
- Бо Сименсен
- Дональд Гилберт
- Майк ван Риэль
- Пол Драгонис
- Слишком много других, чтобы назвать и сосчитать
6. Голоса
-
Входное голосование: https://groups.google.com/d/msg/php-fig/_LYBgfcEoFE/ZwFTvVTIl4AJ
-
Голосование за принятие:
-
1-я попытка: https://groups.google.com/forum/#!topic/php-fig/Ua46E344_Ls, представлен перед новым рабочим процессом; прервано из-за случайного изменения предложения
-
2-я попытка: https://groups.google.com/forum/#!topic/php-fig/NWfyAeF7Psk, отменено по усмотрению спонсора https://groups.google.com/forum/#!topic/php-fig/t4mW2TQF7iE
-
3-я попытка: TBD
7. Соответствующие ссылки
- Autoloader, round 4
- POLL: Autoloader: Split or Combined?
- PSR-X autoloader spec: Loopholes, ambiguities
- Autoloader: Combine Proposals?
- Package-Oriented Autoloader, Round 2
- Autoloader: looking again at namespace
- DISCUSSION: Package-Oriented Autoloader - vote against
- VOTE: Package-Oriented Autoloader
- Proposal: Package-Oriented Autoloader
- Towards a Package Oriented Autoloader
- List of Alternative PSR-4 Proposals
- Summary of [post-Acceptance Vote pull] PSR-4 discussions