By default the page is set like this in the Application
module.config array:
'template_map' => array(
'error/404' => __DIR__ . '/../view/error/404.phtml'
I want to change the page. I want new ViewModel
for it full of variables. It means that simply to change the template is not enough:
'error/404' => __DIR__ . '/../view/error/my_new_404_template.phtml'
But I can't understand how to make it. I can't see the way the request comes to the 'error/404'
.
How to create new ViewModel
for it?
How to attach variables to it?
How the route comes to 'error/404'
to catch it to change?
For example, I have such a method for 'error/404'
page:
public function pageNotFoundAction() {
$view = new ViewModel();
$view->setTemplate('error/404'); // set my template
$sm = $this->getServiceLocator()->get('SessionManager');
$cont = new Container('SomeNamespace', $sm);
$view->var1 = $cont->offsetGet('someValue1'); // the "error/404" template
$view->var2 = $cont->offsetGet('someValue2'); // is full of variables
$view->var3 = $cont->offsetGet('someValue3');
$view->var4 = "One more view variable";
// And now I return it somewhere and want it to be called
// in case of "the page is not found"
return $view;
}
How to make such a change? I can't get the system they've created to deal with things like 'error/404'
. Please help.
UPD 1
Even more complicated task. How to have several 'error/404'
pages?
Would like to ask guys who created the framework whether they know that 'not_found_template'
cannot have an array of 'error/404'
pages. How it can be? If I set this option like this:
'template_map' => array(
'error/404' => __DIR__ . '/../view/error/404.phtml',
'my-page/one_more_error404' => __DIR__ . '/../view/my-page/my-page/one_more_error404.phtml',
'other_page/second_404' => __DIR__ . '/../view/other-page/one_more_error404.phtml',
'not_found_template' => array(
'error/404',
'my-page/one_more_error404',
'other-page/second_404',
);
it throws an error. 'not_found_template'
force you to have only one 'error/404'
template?
There is another way. To catch an EVENT_DISPATCH_ERROR
and totally rebuild viewModel
. Cavern is that layout – is a root viewModel
, and content appended into layout by default is another viewModel
(child). These points are not such clear described in official docs.
Here is how it can look like in your Module.php
:
public function onBootstrap(MvcEvent $event)
{
$app = $event->getParam( 'application' );
$eventManager = $app->getEventManager();
/** attach Front layout for 404 errors */
$eventManager->attach( MvcEvent::EVENT_DISPATCH_ERROR, function( MvcEvent $event ){
/** here you can retrieve anything from your serviceManager */
$serviceManager = $event->getApplication()->getServiceManager();
$someVar = $serviceManager->get( 'Some\Factory' )->getSomeValue();
/** here you redefine layout used to publish an error */
$layout = $serviceManager->get( 'viewManager' )->getViewModel();
$layout->setTemplate( 'layout/start' );
/** here you redefine template used to the error exactly and pass custom variable into ViewModel */
$viewModel = $event->getViewModel();
$viewModel->setVariables( array( 'someVar' => $someVar ) )
->setTemplate( 'error/404' );
});
}