Использование зарезервированных слов в URL Magento 2

11

Можно ли создать модуль в Magento 2, используя стандартную маршрутизацию, который отвечает на URL в виде

http://magento.example.com/namespace_module/return/index

То есть - URL, где вторым параметром является зарезервированное ключевое слово PHP. Проблема с вышеупомянутым состоит в том, чтобы создать имя класса контроллера PHP, это

Namespace\Module\Controller\Return\Index

и наличие Returnв пространстве имен является незаконным PHP. Я знаю, был ли последний параметр URL (традиционно называемый действием) зарезервированным ключевым словом

http://magento.example.com/namespace_module/foo/return

что Magento позволит мне создать класс контроллера с именем

Namespace\Module\Controller\Foo\ReturnAction

Однако это не работает для второго параметра.

Есть ли способ сделать это, используя стандартные методы маршрутизации Magento 2?

Если нет, то существует ли общепринятая лучшая практика для внедрения пользовательского объекта-маршрутизатора, чтобы получить такое поведение, или какой-то другой метод, который позволил бы мне обойти это? ( afterплагин включен Magento\Framework\App\Router\ActionList?)

Алан Сторм
источник

Ответы:

7

Я закончил тем, что добавил плагин для Magento\Framework\App\Router\ActionList

<!-- File: app/code/Package/Namespace/etc/di.xml -->
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
    <type name="Magento\Framework\App\Router\ActionList">
        <plugin name="package_module_magento_framework_app_router_actionlist" type="Package\Module\Plugin\Magento\Framework\App\Router\ActionList"/>
    </type>
</config>

а затем возился с $namespaceпараметром getметода

#File: app/code/Package/Module/Plugin/Magento/Framework/App/Router/ActionList.php
public function beforeGet($subject, $module, $area, $namespace, $action)
{
    if($namespace === 'return')
    {
        $namespace = 'returnaction';
    }
    return [$module, $area, $namespace, $action];
}

Это дало мне имя класса

Package\Module\Controller\ReturnAction\Index

Не уверен, насколько это хорошая идея, так что покупатель остерегается и т.д.

Алан Сторм
источник
Это выглядит красиво и легко. Тем более что его можно распространить на все зарезервированные слова php таким же образом, как имена действий отображаются в классы действий. Альтернативой может быть создание собственного маршрутизатора, но для этого требуется гораздо больше кода.
Мариус
2
Только пара комментариев: 1) Это изменит пространство имен для любого модуля, который пытается использовать контроллер возврата. Если вы не намеренно создаете 'catchall', лучше проверить параметр $ module на соответствие вашему собственному модулю. 2) Если мы попытаемся сохранить четность именования, возвращаемое пространство имен $, вероятно, должно быть returnController, которое затем будет искать пространство имен ReturnController / filepath. Это будет затем загрузить \Namespace\Module\Controller\ReturnController\Index- что более точно.
Джереми Римпо