2017-03-02 83 views
0

我最近决定在使用Zend Framework 1 3年后使用Zend Framework 3。这个决定令我头痛,Zend 3让事情变得更简单,使事情变得更加困难。如何从模型或助手中获取basepath Zend Framework 3

在Zend的1,我自定义所选模板的URL数据库如下:

public function getUrl(string $file = '') 
{ 
    if($this->_helperBaseUrl === null) { 
     $this->_helperBaseUrl = new Zend_View_Helper_BaseUrl(); 
    } 
    return $this->_helperBaseUrl->baseUrl($file); 
} 

public function getSkinUrl(string $file = '') 
{ 
    $themePath = 'themes/my-theme/'; //get from database 
    return $this->getUrl($themePath . ltrim($file, '/\\')); 
} 

然后在应用程序的任何部分(模型,佣工,插件和视图)我可以访问此功能像这样:

//view/scripts/index/index.phtml 
$url_logo = My::app()->getSkinUrl('logo.jpg'); 
//this return http://example.com/themes/my-theme/logo.jpg 

在Zend 3中对我来说非常困难。有谁知道在Zend 3中有什么办法吗?或者如何从Zend 3的模型中获取baseUrl?

+0

你只迟到了5年:) – tasmaniski

+0

@ tasmaniski 3年前我使用ZF2,但它比ZF1慢。出于这个原因,我继续使用ZF1 :) –

回答

2

在Zend Framework 2/3中,您几乎可以将任何类注入到另一个类中。例如,如果您需要basePath插件(可在视图上下文中使用),则可以将此插件注入到您的模型/服务或控制器类中。这是推荐的方式:

这就是你需要这个插件或任何其他服务

use Zend\View\Helper\BasePath; 

class MyService 
{ 
    /** 
    * @var BasePath 
    */ 
    protected $plugin; 

    /** 
    * MyService constructor. 
    * 
    * @param BasePath $basePath 
    */ 
    public function __construct(BasePath $basePath) 
    { 
     $this->plugin = $basePath; 
    } 

    /** 
    * @return BasePath 
    */ 
    public function getPlugin() 
    { 
     return $this->plugin; 
    } 

    /** 
    * @param BasePath $plugin 
    */ 
    public function setPlugin($plugin) 
    { 
     $this->plugin = $plugin; 
    } 
} 

现在,你需要到工厂注入一个依赖到另一个

use Interop\Container\ContainerInterface; 
use Zend\ServiceManager\FactoryInterface; 
use Zend\ServiceManager\ServiceLocatorInterface; 
use MyNamespace\Service\MyService; 

class MyServiceFactory implements FactoryInterface 
{ 
    /** 
    * 
    * @param ContainerInterface $container 
    * @param string $requestedName 
    * @param null|array $options 
    * @return MyService 
    */ 
    public function __invoke(ContainerInterface $container, $requestedName, array $options = null) 
    { 
     $class = $requestedName ? $requestedName : MyService::class; 
     $plugin = $container->get('ViewHelperManager')->get('BasePath'); // inject this class 
     $myService = new $class($plugin); // into this class 

     return $myService; 

    } 
    /** 
    * Provided for backwards compatibility; proxies to __invoke(). 
    * 
    * @param ContainerInterface|ServiceLocatorInterface $container 
    * @return MyService 
    */ 
    public function createService(ServiceLocatorInterface $container) 
    { 
     return $this($container, MyService::class); 
    } 
} 

好类,现在MyServicebasePath插件,但要在控制器中使用它,您必须将您的服务注入控制器。所以......

的IndexController

use MyNamespace\Service\MyService; 
use Zend\Mvc\Controller\AbstractActionController; 

class IndexController extends AbstractActionController 
{ 
    /** 
    * @var MyService 
    */ 
    protected $service; 

    /** 
    * IndexController constructor. 
    * 
    * @param MyService $service 
    */ 
    public function __construct(MyService $service) 
    { 
     $this->service = $service; 
    } 

    public function indexAction() 
    { 
     $plugin = $this->service->getPlugin(); // Zend\View\Helper\BasePath object 
     //... 
    } 
} 

...和工厂为我们的控制器......

use Interop\Container\ContainerInterface; 
use Zend\ServiceManager\FactoryInterface; 
use Zend\ServiceManager\ServiceLocatorInterface; 
use MyNamespace\Controller\IndexController; 

class IndexControllerFactory implements FactoryInterface 
{ 
    /** 
    * 
    * @param ContainerInterface $container 
    * @param string $requestedName 
    * @param null|array $options 
    * @return IndexController 
    */ 
    public function __invoke(ContainerInterface $container, $requestedName, array $options = null) 
    { 
     $class = $requestedName ? $requestedName : IndexController::class; 
     $myService = $container->getServiceLocator()->get('MyNamespace\Service\MyService'); 
     $controller = new $class($myService); 

     return $controller; 

    } 
    /** 
    * Provided for backwards compatibility; proxies to __invoke(). 
    * 
    * @param ContainerInterface|ServiceLocatorInterface $container 
    * @return IndexController 
    */ 
    public function createService(ServiceLocatorInterface $container) 
    { 
     return $this($container, IndexController::class); 
    } 
} 

它几乎完成。最后一步是设置配置module.config.php文件

use MyNamespace\Controller; 
use MyNamespace\Factory; 

return [ 
    //... 
    'service_manager' => [ 
     'factories' => [ 
      Service\MyService::class => Factory\Service\MyServiceFactory::class 
     ] 
    ], 
    'controllers' => [ 
     'factories' => [ 
      Controller\IndexController::class => Factory\Controller\IndexControllerFactory::class 
     ], 
    ], 
] 

很简单,不是吗?
如果您需要在插件控制器,但不是在你的模型/服务类,你可以跳过这个“教程” MyService一部分,并直接注入到插件控制器类

相关问题