Solved thread

This post is marked as solved. If you think the information contained on this thread must be part of the official documentation, please contribute submitting a pull request to its repository.

AutoRouting and notfound condition

I am trying to create a typical routing setting.

Use Autorouting so that domain.com/ - goes to index controller and index action domain.com/myconroller/myaction - goes and executes mycontroller and myaction - Pretty straight forawrd and works automatically with the autorouting.

Now comes the need. Any request to : domain root level should always call the index controller and index action if controller/action do not exist.

Say for example when Calling : mydomain.com/abcdxyz (controller abcdxyz does not exist and will never).

It should load up the index controller and do the index action automatically.

$router = new \Phalcon\Mvc\Router(false); //and setting up : 
$router->notFound(array(
            "controller" => "index",
            "action" => "index"
));

is not the solution, since it will break the auto trouting. I need the autorouting to work automaically based on what exists. Only when controller/action does snot exist, I would want to always use the index/index controller/function.

Any insights on how this can be achieved ?



480

Should this be done through the Dispatcher ? I believe, the controller / method not found exception happens way before the router is used ?

I would also like to know how to always use the index method of each controllers when there a spefific action asked for is not inside the controller ?

Working on a project, so a quick reply will e quite helpful.



480
Accepted
answer
edited Aug '14

The more I work on this framework, the more I understand how powerful this BEAST is.

I figured it out, posting here for other newbies in case they hit the same issue.

Requirements that were required and how to meet them :

  • If Controller not found, then always use Index Controller and Index Action
  • Within a Controller when an action is not found, always use the index action of the controller called.

Solution : in index.php add following : Picked from Dispatcher documentation and modified a bit

<?php

use Phalcon\Dispatcher, 
    Phalcon\Mvc\Dispatcher as MvcDispatcher,
    Phalcon\Events\Manager as EventsManager,
    Phalcon\Mvc\Dispatcher\Exception as DispatchException;

$di->set('dispatcher', function() {

    //Create an EventsManager
    $eventsManager = new EventsManager();

    //Attach a listener
    $eventsManager->attach("dispatch:beforeException", function($event, $dispatcher, $exception) {

        //Alternative way, controller or action doesn't exist
        if ($event->getType() == 'beforeException') {
            switch ($exception->getCode())
                {
                   /* all processing done by index controller and its index action. */
                    case \Phalcon\Dispatcher::EXCEPTION_HANDLER_NOT_FOUND:  
                        $dispatcher->forward(array(
                            'controller' => 'index',
                            'action' => 'index'
                        ));
                    /* (if controller exists but method does not, then always use the controller index action. */
                    case \Phalcon\Dispatcher::EXCEPTION_ACTION_NOT_FOUND: 
                        $dispatcher->forward(array(
                           /* 'controller' => 'index', */ 
                            'action' => 'index'
                        ));
                        return false;
                }
        }
    });

    $dispatcher = new \Phalcon\Mvc\Dispatcher();

    //Bind the EventsManager to the dispatcher
    $dispatcher->setEventsManager($eventsManager);

    return $dispatcher;

}, true);
?>

Hope I am making sense here, Please correct if there is anything wrong in it.