* @package TinyMVC * @version $Id$ * */ /** * TinyMVCFrontController class * * This is default TinyMVC Framework front controller which handle all requests. * It can be instantiated in {@link index.php} bootstrap file, for example: * * * doService(); * ?> * * * @package TinyMVC */ class TinyMVCFrontController { /** * @var TinyMVCActionController */ protected $actionController; /** * @var TinyMVCViewRenderer */ protected $viewRenderer; /** * @var TinyMVCRequest */ protected $request; /** * @var string */ protected $defaultModuleName; /** * @var string */ protected $defaultActionName; /* * $var array */ protected $plugins = array(); /** * @param TinyMVCRequest $request Request object * @param TinyMVCViewRenderer $viewRenderer View renderer object * @param string $defaultModuleName Default module name * @param string $defaultActionName Default action name */ public function __construct(TinyMVCRequest $request, TinyMVCViewRenderer $viewRenderer, $defaultModuleName = 'index', $defaultActionName = 'default') { $this->request = $request; $this->viewRenderer = $viewRenderer; $this->defaultModuleName = $defaultModuleName; $this->defaultActionName = $defaultActionName; } /** * process request */ public function doService() { foreach ($this->plugins as $pl){ $pl->preDispatch($this->request); } $modelAndView = $this->getActionController()->doAction(); $this->viewRenderer->render($modelAndView); foreach ($this->plugins as $pl){ $pl->afterDispatch($this->request); } } /** * resolves and returns correct action controller for module * @return TinyMVCActionController Action controller */ protected function getActionController() { if(!$this->request->getParam('mod')) { $this->request->setParam('mod', $this->defaultModuleName); } $moduleName = strtolower($this->request->getParam('mod')); if(!empty($moduleName)) { if(preg_match("/^[a-z_]{1,}$/i", $moduleName) != 0) { $actionControllerClassFile = TinyMVC::getInstance()->getControllersPathResolver()->resolve(ucfirst($moduleName)); } else { throw new TinyMVCException("Invalid characters in module name: $moduleName"); } if(file_exists($actionControllerClassFile)) { require_once($actionControllerClassFile); $controllerClassName = ucfirst($moduleName) . 'ActionController'; } else { throw new TinyMVCException("ActionController for module: $moduleName - not found."); } // TODO: pass alternate model here, set modelAndView $controller = new $controllerClassName(new TinyMVCModelAndView(new TinyMVCView(TinyMVC::getInstance()->getViewsPathResolver(), ''), null), $this->request, $this->defaultActionName); if($controller instanceof TinyMVCActionController) { if(($controller->getModelAndView() == null) || ($controller->getRequest() == null)) { throw new TinyMVCException("parent::__construct() has not been called in $controllerClassName::__construct()"); } } else { throw new TinyMVCException(get_class($controller) . " must extends TinyMVCActionController"); } return $controller; } else { throw new TinyMVCException("Unknown module name"); } } public function registerPlugin(TinyMVCControllerPluginInterface $plugin){ $this->plugins[] = $plugin; } }