如何用可以退出的东西替换这个_forward()?

时间:2012-07-22 16:32:25

标签: zend-framework

我在zend框架应用程序中反复使用以下代码。在action() 中使用来检查文章是否存在。如果没有,用户将看到一条错误消息:

$article = ArticleQuery::create()->findOneByUrl($this->_getParam('url', ''));

if (!$article) {
    $this->getResponse()
         ->setRawHeader('HTTP/1.1 404 Not Found');
    return $this->_forward('error', null, null, array(
        'message' => 'Article not found',
    ));
}

我想知道如何将其纳入自己的方法以减少所有操作中的代码负载

我来到这样的事情:

protected function myAction() {
    $article = $this->getArticleIfExists($this->_getParam('url', ''));
    if ($article == null) {
        return;
    }
}

protected function getArticleIfExists($url) {
    $article = ArticleQuery::create()->findOneByUrl($this->_getParam('url', ''));

    if ($article) {
        return $article;
    } else {
        $this->getResponse()
             ->setRawHeader('HTTP/1.1 404 Not Found');
        $this->_forward('error', null, null, array(
            'message' => 'Article not found',
        ));
        return nulL;
    }
}

我仍然希望摆脱ifmyAction()的情况,但_forward()不允许退出执行(当然,因为它仍然需要执行另一个动作)。

另一种可能性(我已在其他一些控制器中实现)是:

protected function myAction() {
    $article = ArticleQuery::create()->findOneByUrl($this->_getParam('url', ''));

    if (!$article) {
        return $this->notFound('Article does not exist');
    }
}

protected function notFound($message) {
    $this->getResponse()
         ->setRawHeader('HTTP/1.1 404 Not Found');
    return $this->_forward('error', null, null, array(
        'message' => $message,
    ));
}

我们再次检查此操作if。它已经比以前更好了,但我们可以做得更好吗?

我该怎样绕过这个?是否有可能在不丢失当前URL的情况下执行此操作?使用Redirector我当然可以退出,但之后我会丢失当前的网址(/controller/myaction/url/hello -> /error/error/message/Article%20not%20found

2 个答案:

答案 0 :(得分:1)

可能的方法是抛出异常。由于Zend_Controller_Plugin_ErrorHandler,这将自动将您重定向到ErrorController而不执行任何进一步的代码。

如果您不想访问ErrorController而只想访问当前控制器的错误操作,您只需在控制器的init方法中修改插件:

public function init()
{
    $plugin = Zend_Controller_Front::getInstance()->getPlugin('Zend_Controller_Plugin_ErrorHandler');
    $plugin->setErrorHandlerModule('default')
       ->setErrorHandlerController('MyController')
       ->setErrorHandlerAction('error');
}

但是当然你也可以编写自己的ErrorHandler插件来进行更细粒度的错误处理。这在Zend Framework Manual on Plugins

中有所描述

答案 1 :(得分:1)

对于像针对用户请求只显示“*不存在”这样简单的事情,我更喜欢将用户留在应用程序中,只需使用flashmessenger通知点击它们并将它们留在页面上以发出另一个请求(如果适当):

public function indexAction() {

        //get form and pass to view
        $form = new Form();

        $this->view->form = $form;

        try {
            //get form values from request object
            if ($this->getRequest()->isPost()) {
                if ($form->isValid($this->getRequest()->getPost())) {

                    $data = $form->getValues();

                   // Do some stuff
                }
            }
        } catch (Zend_Exception $e) {

            $this->_helper->flashMessenger->addMessage($e->getMessage());//add message to flashmessenger
            $this->_redirect($this->getRequest()->getRequestUri());//perform redirect to originating page so the messenger will flash
        }
    }

这很简单,当存在不正确的用户输入的可能性时效果很好。