如何在所有控制器中提供一次定义的方法?
在我的UsersController应用程序中,我有一个名为getAuthService的方法(它提取身份验证服务),但我希望能够从其他控制器访问身份验证实例(因此我可以访问它的存储)。下面是我在UsersController中的方法:
class UsersController {
protected $authService
.
.
.
protected function getAuthService() {
if (! $this->authService) {
$dbAdapter = $this->getServiceLocator()->get('\Zend\Db\Adapter\Adapter');
$dbTableAuthAdapter = new DbTableAuthAdapter($dbAdapter, 'users', 'email', 'password', 'MD5(?)');
$authService = new AuthenticationService();
$authService->setAdapter($dbTableAuthAdapter);
$this->authService = $authService;
}
return $this->authService;
}
}
..但是,我不能在我的ApplicationController中访问它,除非我在那里复制方法?我可以在其他地方定义此方法吗?或者,另一种方式?
在Rails中,我将此方法放入应用程序控制器,因为其他控制器从那里扩展。是Zend方法创建一个包含扩展AbstractActionController和其他控制器扩展的共享方法的控制器,或者扩展其他模块'来自Application \ Controller \ IndexController的控制器:
- Zend\Mvc\Controller\AbstractActionController (abstract)
- Application\Controller\IndexController (containing my getAuthService method)
- Users\Controller\UsersController (extends the above so getAuthService is available)
由于
答案 0 :(得分:2)
您可以编写一个Controller插件。由于您需要authservice以及dbadapter,因此编写一个检索它们的工厂可能是个好主意。在application/src/Controller
中,我们添加了一个名为Plugin
的文件夹。完成后,我们创建工厂,获取所需的服务等。
namespace Application\Controller\Plugin;
use Zend\ServiceManager\FactoryInterface;
use Zend\ServiceManager\ServiceLocatorInterface;
/**
*
* Your factory
*
* @package Application
*/
class AuthFactory implements FactoryInterface
{
/**
* Create Service Factory
*
* @param ServiceLocatorInterface $serviceLocator
*/
public function createService(ServiceLocatorInterface $serviceLocator)
{
$sm = $serviceLocator->getServiceLocator();
$adapter = $sm->get('\Zend\Db\Adapter\Adapter');
$plugin = new Auth();
$plugin->setAdapter($adapter);
return $plugin;
}
}
插件可能如下:
namespace Application\Controller\Plugin;
use Zend\Mvc\Controller\Plugin\AbstractPlugin;
class Auth extends AbstractPlugin
{
protected $adapter;
protected $authService;
public function setAdapter($adapter)
{
$this->adapter = $adapter;
}
public function getAdapter()
{
return $this->adapter;
}
public function getService()
{
if (! $this->authService) {
$dbAdapter = $this->getAdapter();
$dbTableAuthAdapter = new DbTableAuthAdapter($dbAdapter, 'users', 'email', 'password', 'MD5(?)');
$authService = new AuthenticationService();
$authService->setAdapter($dbTableAuthAdapter);
$this->authService = $authService;
}
return $this->authService;
}
}
现在我们必须将工厂添加到module.config文件中,如下所示:
'controller_plugins' => array(
'factories' => array(
'auth' => 'Application\Controller\Plugin\AuthFactory',
),
),
完成后,您可以像控制器一样在控制器中调用控制器插件:
$this->auth()->getService();
//or the alternative syntax
$this->plugin('auth')->getService();