2

我目前正在学习/试验 ZF2 的稳定版本。最近几天一直在尝试找到解决我的问题的方法,即:我希望能够为一组控制器编写一些通用的设置逻辑。在采埃孚!然后,我将编写一个通用控制器并从中派生,使用 init() 方法作为我的设置逻辑。经过一番搜索,我发现 init() 方法已在 ZF2 中删除,并且有其他方法可以获得相同的功能。

我试图遵循 MW O'Phinney 的指南:http: //mwop.net/blog/2012-07-30-the-new-init.html

在我的情况下,我必须能够检索和检查我的设置逻辑的路由参数,因此覆盖替代方法的方法不起作用,因为此时无法访问 MvcEvent。所以,我尝试了 Update: serviceManager 解决方案,这就是我卡住的地方。首先,我只是尝试将指南中的代码复制到我的 Module 类中并回显一些文本以查看是否调用了回调。它不是。

在网上进行了更多搜索后,我找到了一个可能的解决方案;在通用控制器的构造函数中附加回调。同样的问题似乎也在这里。构造函数当然会被调用,但回调要么未附加或未正确触发(或根本没有)。

我将附上来自两种不同解决方案的一些代码:

在 Module.php 中:

public function getControllerConfig() {
    return array(
        'factories' => array(
            'Game\Controller\Mapsquare' => function($controllers) {
                $serviceManager = $controllers->getServiceLocator();
                $eventManager = $serviceManager->get('EventManager');
                $controller = new Controller\MapsquareController();

                echo "this text is echoed";

                $eventManager->attach('dispatch', function ($e) use ($controller) {
                    echo "this text is NOT echoed";
                    $request = $e->getRequest();
                    $method  = $request->getMethod();
                    if (!in_array($method, array('PUT', 'DELETE', 'PATCH'))) {
                        // nothing to do
                        return;
                    }

                    if ($controller->params()->fromRoute('id', false)) {
                        // nothing to do
                        return;
                    }

                    // Missing identifier! Redirect.
                    return $controller->redirect()->toRoute(/* ... */);
                }, 100); // execute before executing action logic

                $controller->setEventManager($eventManager);

                return $controller;
            }
        )
    );
}

在 MapsquareController.php(通用控制器)中:

public function __construct() {
    $this->getEventManager()->attach('dispatch', array($this, 'preDispatch'), 1000);
    echo "construct";
}

public function preDispatch() {
    echo "This is preDispatch()!";
}

有没有人可以帮助我解决这个问题,最终告诉我在这里误解了什么?任何帮助表示赞赏:)

4

3 回答 3

1

Evan Coury 关于 Zend Framework 2 中特定于模块的布局的帖子似乎提供了一个解决方案,它对我有用。

http://web.archive.org/web/20140623024023/http://blog.evan.pro/module-specific-layouts-in-zend-framework-2

于 2012-10-24T06:45:33.990 回答
1

您不能从工厂附加到调度,因为在处理调度后很长时间调用工厂。

为了让它工作,打开你的 Module.php 并编辑 onBootstrap(),这样你就可以附加到那里。例如:

public function onBootstrap($e)
{
    ...
    $eventManager = $e->getApplication()->getEventManager();
    $eventManager->attach("dispatch", function($e) {
        echo "Dispatch!";
    });
}

或者,您也可以从特定控制器执行此操作。不在构造函数中,而是通过覆盖 setEventManager:

public function setEventManager(EventManagerInterface $events) {
    parent::setEventManager($events);
    $controller = $this;
    $events->attach("dispatch", function($e) use ($controller) {
        echo "Dispatch!";
    });
}

希望这可以帮助!

于 2012-12-19T12:48:09.940 回答
1

请注意,接受的不正确。OP发布的代码根本不起作用。永远不要用横切关注点污染你的 onBootstrap。原因如下:

public function __construct() {
    $this->getEventManager()->attach('dispatch', array($this, 'preDispatch'), 1000);
    echo "construct";
}

没有工作是因为事件管理器在构造后被附加,并在调度时触发。

关于“工厂在发货后很长一段时间内被调用”的评论也没有意义。你知道工厂是做什么的吗?

“O'phinney 先生”的建议是正确的方法,下次您可能会更好地阅读手册,然后再决定让像 Matthew 这样的人让您失望。

解决方案在这里: http: //mwop.net/blog/2012-07-30-the-new-init.html

于 2013-11-21T21:48:20.523 回答