您的位置:首页 > 其它

彻底解决'Invalid controller specified'(转载)

2011-04-15 22:13 281 查看
这几天学习zend,卡在了'Invalid controller specified'的问题上,我不是个随便放弃的人,所以我还是要刨根问底,下面是我这几天通过查手册,做实验得出的解决'Invalid controller specified'错误的几种方法。



首先是这个错误的起因,这个错误其实来源特别简单:

如果请求一个无效的控制器,Zend_Controller_Dispatcher::dispatch() 默认会抛出一个异常。就是没有找到对应的请求控制器,或者控制器的代码有错误。



以下是我得出的解决方法:

1.)$front->setParam('useDefaultControllerAlways', true);

通过设置$front->setParam('useDefaultControllerAlways', true);控制器会自动寻找与之对应的模型,所以你需要按照错误中所描述的路径,建立对应的模型,如果没有模型会继续报错。

2.)对前端开启错误捕获

原理是把dispatch装进错误捕获中,类似c#的错误捕获原理,出错就引导它去别处

$front->throwExceptions(true);
try {
$front->dispatch();
} catch (Exception $e) {
// handle exceptions yourself
}

3.)对前端开启消息返回

$front->returnResponse(true);
$response = $front->dispatch();
if ($response->isException()) {
$exceptions = $response->getException();
// handle exceptions ...
} else {
$response->sendHeaders();
$response->outputBody();
}

4.)重写__call方法,如果没有对应的动作就指向默认动作

解决方法:

class My_Controller_Action extends Zend_Controller_Action
{
public function __call($methodName, $args)
{
if ('Action' == substr($methodName, -6)) {
$controller = $this->getRequest()->getControllerName();
$url = '/' . $controller . '/index';
return $this->_redirect($url);
}
//throw new Zend_Controller_Action_Exception(sprintf('Method "%s" does not exist and was not trapped in __call()', $methodName), 500);
//throw new Exception('Invalid method');
}

}

这样就能先判断控制器名称,如果不存在,就去默认动作,这个地方其实我很想给之前加一个默认的动作名称设置的函数,这个里面调用它,就不必做成固定的了。不过又偷了个懒,还是留给大家研究讨论,哈哈。比较改源码还是慎重一点好

5.)与上面这个类似,但是是重构分发器

class My_Controller_PreDispatchPlugin extends Zend_Controller_Plugin_Abstract
{
public function preDispatch(Zend_Controller_Request_Abstract $request)
{
$dispatcher = Zend_Controller_Front::getInstance()->getDispatcher();
$controller = $dispatcher->getController($request);
if (!$controller) {
$controller = $dispatcher->getDefaultControllerName($request);
}
$action = $dispatcher->getAction($request);

if (!method_exists($controller, $action)) {
$defaultAction = $dispatcher->getDefaultAction();
$controllerName = $request->getControllerName();
$response =
Zend_Controller_Front::getInstance()->getResponse();
$response->setRedirect('/' . $controllerName .
'/' . $defaultAction);
$response->sendHeaders();
exit;
}
}
}

这个我写的有点废物,因为是直接从官方摘下来的,其实它里面还有很多东西,告诉你吧,你做这样的修改仍然出错,还有很多关联的东西你可能还不知道



比如,默认的会认为你的错误控制器是存在的,在你的controller目录中,存在一个ErrorController.php,还有视图中的error/error.phtml,你创建他们才能保证你的错误处理有的放矢。

例子:

class ErrorController extends Zend_Controller_Action
{
public function errorAction()
{
//这里进行错误处理,用respons返回404等错误,不过还要处理     

}
}



当然不止是错误处理,你要把smarty装上,还需要了解分发器,还有这个问题的重要因素:ViewRenderer

$front->setParam('noViewRenderer', true);//在不用默认控制器的情况下(如smarty),这个设置好,此问题才算彻底解决

所以zend每个错误牵动着很多点,你必须对它们有所了解,我的体验,入门不好入,不过见识过强大的路由功能和ACL,再不好学也要学会,哈哈,废话了,欢迎访问我的小站http://www.sookon.com

之前的一篇废物文章只是让你找找成就感http://www.sookon.com/it/php/188.html,不要当真哦,这样处理问题不行

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: 
相关文章推荐