我一直在使用ZendFramework和Doctrine2进行一个项目,并注意到我的动作控制器的问题不是很“干”。鉴于以下示例,在我的所有控制器中几乎完全相同,这将是分解重复的最佳方法。我认为baseController是迄今为止最简单的,但似乎扩展Zend_Controller_Action是不受欢迎的。我倾向于另外两个选项是创建一个动作助手或控制器插件(但控制器插件对我来说仍然是一个模糊的概念)。
所以我的问题是,最好的方法是什么?为什么?
class Job_JobController extends Zend_Controller_Action
{
protected $_service;
public function init()
{
$ajaxContext = $this->_helper->getHelper('AjaxContext');
$ajaxContext->addActionContext('create', 'html')
->addActionContext('update', 'html')
->addActionContext('view', 'html')
->addActionContext('delete', 'html')
->addActionContext('message', 'html')
->initContext();
$this->_service = $this->_helper->service('job');
}
public function indexAction()
{
$this->_forward('list');
}
public function listAction()
{
$grid = $this->_service->getGrid();
$this->view->list = $grid->render();
}
public function createAction()
{
$request = $this->getRequest();
$formMediator = $this->_service->getFormMediator();
if ($request->isPost() && $formMediator->isValid($request->getPost()))
{
$this->_service->saveEntity($formMediator->transfer());
$this->_helper->flashMessenger->addMessage(array('statusCode' => 'Create::Success'));
$this->_forward('message');
}
$this->view->entity = $formMediator->getForm();
}
public function updateAction()
{
$request = $this->getRequest();
$formMediator = $this->_service->getFormMediator();
$entity = $this->_service->findEntity($request->getParam('id'));
if ($request->isPost() && $formMediator->isValid($request->getPost()))
{
$this->_service->saveEntity($formMediator->transfer($entity));
$this->_helper->flashMessenger->addMessage(array('statusCode' => 'Update::Success'));
$this->_forward('message');
}
else
{
$formMediator->populate($entity);
}
$this->view->entity = $formMediator->getForm();
}
public function viewAction()
{
$request = $this->getRequest();
$this->view->entity = $this->_service->getEntity($request->getParam('id'));
}
public function deleteAction()
{
$request = $this->getRequest();
$id = $request->getParam('id');
if ($this->getRequest()->isPost())
{
$this->_service->delete($request->getParam('id'));
$this->_helper->flashMessenger->addMessage(array('statusCode' => 'Delete::Success'));
$this->_forward('message');
}
$this->view->deleteId = $id;
}
public function messageAction()
{
$messages = array_merge((array)$this->_helper->flashMessenger->getMessages(),
(array)$this->_helper->flashMessenger->getCurrentMessages());
$this->view->messages = $messages;
}
}
答案 0 :(得分:2)
扩展Zend_Controller_Action没有任何问题。对于我们的软件,我们对其进行了扩展,并使用preDispatch()函数验证用户是否已经过身份验证,如果没有,则显示登录屏幕。现在我们所有的控制器都扩展了那个,我们不需要为我们所有的页面做任何需要登录的事情。
答案 1 :(得分:1)
不是真正的答案,但我认为两种方式(扩展Zend_Controller_Action
或Action-Helper)都是您正在寻找的解决方案。我没有看到任何理由,为什么抽象控制器有点......丑陋(?)。它是OOP的工作方式。
答案 2 :(得分:1)
我认为抽象控制器应该没问题,虽然我有时觉得它有点不优雅,因为测试抽象类的行为很棘手。
看过这段代码,你可以做的一件事是Replace Temp with Query。除了保存一些微不足道的输入(有时打字甚至比你需要的更多)之外,你正在进行临时变量赋值。有时值得键入一些额外的字符,以减少方法中有助于重构的临时/局部变量的数量。