Intereting Posts
Как получить дату истечения срока действия из файла сертификата SSL в PHP Обновить только первую запись из повторяющихся записей в MySQL Разница между array_push () и $ array = «Строка не может быть проанализирована как XML» ошибка php Список файлов с исключением папок и всех его дочерних подкаталогов Разработка базы данных MySql для программы викторины Алгоритм динамического слияния массивов Как связать произвольное количество значений с подготовленным оператором в mysqli? изменить значение узла xml с помощью simpleXML Magento: как загрузить продукт по всем его данным, поскольку он используется в админ Вычислить наивысшие повторяющиеся целые числа из двух ассоциативных массивов Простой шаблон HTML DOM в атрибуте Homestead 2 xdebug не работает Элегантные альтернативы странному множественному наследованию DATE_FORMAT, где условие активной записи Codeigniter

Zend Framework 2: Навигация

В моем контроллере я создаю объект Navigation и передаю его в представление

$navigation = new \Zend\Navigation\Navigation(array( array( 'label' => 'Album', 'controller' => 'album', 'action' => 'index', 'route' => 'album', ), )); 

Там, пытаясь использовать его

 <?php echo $this->navigation($this->navigation)->menu() ?> 

И получите ошибку:

Неустранимая ошибка: Zend \ Navigation \ Exception \ DomainException: Zend \ Navigation \ Page \ Mvc :: getHref не может выполняться, так как экземпляр Zend \ Mvc \ Router \ RouteStackInterface состоит из Zend \ View \ Helper \ Navigation \ AbstractHelper.php в строке 471

Но навигация, которую я использую в макете, так как она написана здесь: http://adam.lundrigan.ca/2012/07/quick-and-dirty-zf2-zend-navigation/ работает. Какая у меня ошибка?

Спасибо.

Проблема заключается в отсутствии Router (или, точнее, Zend\Mvc\Router\RouteStackInterface ). Стек маршрута представляет собой набор маршрутов и может использовать имя маршрута для его преобразования в URL-адрес. В основном он принимает имя маршрута и создает для вас URL-адрес:

 $url = $routeStack->assemble('my/route'); 

Это происходит и внутри страниц MVC Zend\Navigation . На странице есть параметр route и когда есть доступный маршрутизатор, страница собирает собственный URL (или в Zend\Navigation terms, href ). Если вы не предоставляете маршрутизатор, он не может собрать маршрут и, таким образом, выдает исключение.

Вы должны ввести маршрутизатор на каждую страницу навигации:

 $navigation = new Navigation($config); $router = $serviceLocator->get('router'); function injectRouter($navigation, $router) { foreach ($navigation->getPages() as $page) { if ($page instanceof MvcPage) { $page->setRouter($router); } if ($page->hasPages()) { injectRouter($page, $router); } } } 

Как вы видите, это рекурсивная функция, вводя маршрутизатор на каждую страницу. Скучная! Поэтому для вас есть завод. Для этого есть четыре простых шага .

ПЕРВЫЙ ШАГ

Сначала установите конфигурацию навигации в конфигурацию вашего модуля. Так же, как вы default навигацию по default , вы можете создать вторую secondary .

 'navigation' => array( 'secondary' => array( 'page-1' => array( 'label' => 'First page', 'route' => 'route-1' ), 'page-2' => array( 'label' => 'Second page', 'route' => 'route-2' ), ), ), 

У вас есть маршруты к первой странице ( route-1 ) и второй странице ( route-2 ).

ШАГ ВТОРОЙ

Завод преобразует это в структуру объектов навигации, вам нужно создать класс для этого. Создайте файл SecondaryNavigationFactory.php в каталоге MyModule / Navigation / Service.

 namespace MyModule\Navigation\Service; use Zend\Navigation\Service\DefaultNavigationFactory; class SecondaryNavigationFactory extends DefaultNavigationFactory { protected function getName() { return 'secondary'; } } 

См. Здесь, здесь указано имя secondary , что совпадает с вашим навигационным ключом.

ШАГ ТРЕТЬЯ

Вы должны зарегистрировать эту фабрику в диспетчере услуг. Затем фабрика может выполнить эту работу и превратить конфигурационный файл в объект Zend\Navigation . Вы можете сделать это в своем module.config.php:

 'service_manager' => array( 'factories' => array( 'secondary_navigation' => 'MyModule\Navigation\Service\SecondaryNavigationFactory' ), ) 

См., Что я сделал службу secondary_navigation здесь, где фабрика вернет экземпляр Zend\Navigation . Если вы сейчас делаете $sm->get('secondary_navigation') вы увидите, что это объект Zend\Navigation\Navigation .

ШАГ ЧЕТВЕРТЫЙ

Скажите помощнику вида использовать эту навигацию, а не по умолчанию. Помощник вида навигации принимает параметр «Навигация», где вы можете указать, какую навигацию вы хотите. В этом случае диспетчер службы имеет услугу secondary_navigation и это тот, который нам нужен.

 <?= $this->navigation('secondary_navigation')->menu() ?> 

Теперь у вас будет secondary навигационная система, используемая в этом помощнике вида.

Раскрытие: этот ответ такой же, как я дал по этому вопросу: https://stackoverflow.com/a/12973806/434223

Кстати. вам не нужно определять controller и action если вы определяете route , только если ваш маршрут является общим и контроллер / действие являются переменными сегментами.

Проблема в том, что маршруты не могут быть разрешены без маршрутизатора. Я бы ожидал, что класс навигации решит эту проблему, но, очевидно, вам нужно сделать это самостоятельно. Я просто написал помощник вида, чтобы представить маршрутизатор с страницами MVC.

Вот как я использую его в представлении:

 $navigation = $this->navigation(); $navigation->addPage( array( 'route' => 'language', 'label' => 'language.list.nav' ) ); $this->registerNavigationRouter($navigation); echo $navigation->menu()->render(); 

Помощник вида:

 <?php namespace JarJar\View\Helper; use Zend\View\Helper\AbstractHelper; use Zend\View\Helper\Navigation; use Zend\ServiceManager\ServiceLocatorAwareInterface; use Zend\ServiceManager\ServiceLocatorInterface; use Zend\Navigation\Page\Mvc; class RegisterNavigationRouter extends AbstractHelper implements ServiceLocatorAwareInterface { protected $serviceLocator; public function setServiceLocator(ServiceLocatorInterface $serviceLocator) { $this->serviceLocator = $serviceLocator; } public function getServiceLocator() { return $this->serviceLocator; } public function __invoke(Navigation $navigation) { $router = $this->getRouter(); foreach ($navigation->getPages() as $page) { if ($page instanceof Mvc) { $page->setRouter($router); } } } protected function getRouter() { $router = $this->getServiceLocator()->getServiceLocator()->get('router'); return $router; } } 

Не забудьте добавить помощник вида в свой конфиг как invokable instance:

 'view_helpers' => array( 'invokables' => array( 'registerNavigationRouter' => 'JarJar\View\Helper\RegisterNavigationRouter' ) ), 

Это не отличное решение, но оно работает.