Implementing ToMVC

I would guess we’d need to see the calling code or ask Tom directly what the logic behind it is. But, yes. I don’t get the separation of action from the router object either. Usually the router object would hold the action too, as it must come from the HTTP request. The router would need to inspect the URL/ HTTP payload to figure out the requested action.

I’d say this was a very simplistic example just for the discussion Tom makes. He even says at the end.

This is a very simplistic approach to a front controller. In a real-world application it would be far more complex and robust.

The answer goes along with the answer to your second question. Since it is a basic example, a lot of stuff is missing.

I would say the only thing questionable is the injection of the action and route name in the front controller constructor. This would mean the actual front controller script would need something like.

<?php
$request = new Request();
$route = new Route($request);
$routeName = $route->getRouteName();
$action = $route->getAction();
$frontController = new FrontController($route, $routeName, $action);
$frontController->output();

$routeName and $action are superfluous.

The FrontController could look like this.

class FrontController {
    private $controller;
    private $view;
    private $route;
    private $action;
    
    public function __construct(Router $router) {
    
        $this->route = $router->getRoute();
        $this->action = $router->getAction();      
        $this->view = $route->getView();
        $this->controller = $route->getController();
        
        if ($this->controller) {
           //Run the controller action
            if ($this->action) {
                $this->controller->{$this->action}();
            }
        }
        
     }
    
    public function output() {
        //Finally a method for outputting the data from the view 
        //This allows for some consistent layout generation code such as a page header/footer
        $header = '<h1>Hello world example</h1>';
        return $header . '<div>' . $this->view->render() . '</div>';
    }
}

And now the front controller script would look something like,

<?php
$request = new Request();
$route = new Route($request);
$frontController = new FrontController($route);
$frontController->output();

Which, to me, is a bit cleaner.

Scott