Транслятор Zend framework 2 в модели

Как получить переводчик в модели?

Вид изнутри, мы можем получить переводчик, используя этот код

$this->translate('Text')

Внутри контроллера мы можем получить транслятор, используя этот код

$translator=$this->getServiceLocator()->get('translator');

$translator->translate("Text") ;

Но как получить переводчик в модели?

Я перепробовал так много способов найти сервисный локатор в моделях 2 из этих

1) Использование событий MVC

    $e=new MvcEvent();
    $sm=$e->getApplication()->getServiceManager();
    $this->translator = $sm->get('translator');

если я pring $sm, он показывает ноль. но он отлично работает в Model.php onBootstrap

2) Создана одна модель, которая реализует ServiceLocatorAwareInterface SomeModel.php

    <?php

namespace Web\Model;

use Zend\ServiceManager\ServiceLocatorAwareInterface;
use Zend\ServiceManager\ServiceLocatorInterface;

class SomeModel implements ServiceLocatorAwareInterface
{
    protected $services;

    public function setServiceLocator(ServiceLocatorInterface $locator)
    {
        $this->services = $locator;
    }

    public function getServiceLocator()
    {
        return $this->services;
    }
}

и использовал это внутри моей модели

        $sl = new SomeModel();
        $sm=$sl->getServiceManager();
        var_dump($sm); exit;
        $this->translator = $sm->get('translator');

это также печатает ноль.


person Saidulu Buchhala    schedule 04.06.2013    source источник


Ответы (2)


Если вам не нужен экземпляр servicemanager в вашей модели, просто добавьте в него экземпляр переводчика.

Например:

// Your model's constructor

class MyModel {
  // Use the trait if your php version >= 5.4.0
  use \Zend\I18n\Translator\TranslatorAwareTrait;

  public function __construct( $translator )
  {
     $this->setTranslator( $translator ); 
  }

  public function modelMethodWhichNeedsToUseTranslator()
  {
    // ...
    $text = $this->getTranslator()->translate('lorem ipsum');
    // ...
  }
}

Когда вы впервые создаете свою модель на уровне сервиса или контроллера

class someClass implements ServiceLocatorAwareInterface {
    public function theMethodWhichCreatesYourModelInstance()
    {
    // ...
    $sm = $this->getServiceLocator();
    $model = new \Namespace\MyModel( $sm->get('translator') )
    // ...
    }
}

Если вам нужно создать экземпляр вашей модели (new MyModel();) для нескольких методов/классов, рассмотрите возможность написания для нее фабрики.

Вот хорошая статья о внедрении зависимостей и PHP от Ralph Schindler для получения более подробных комментариев об этом подходе.

person edigu    schedule 06.06.2013

Чтобы ваш класс Model был ServiceLocatorAware, вам нужно не только реализовать интерфейс, вам также нужно сделать вашу модель службой диспетчера служб и получить модель оттуда.

Добавьте свою модель в диспетчер служб, поскольку ей не нужны параметры конструктора, ее можно вызывать, поэтому вы можете добавить ее в массив invokables в конфигурации диспетчера служб. Вы можете сделать это, используя метод getServiceConfig() в вашем классе Module...

class Module
{
    public function getServiceConfig()
    {
        return array(
            'invokables' => array(
                'SomeModel' => 'Fully\Qualified\ClassName\To\SomeModel',
            ),
        );
    }
}

Затем вместо вызова ключевого слова new для создания экземпляра модели вы получаете его, например, от диспетчера служб, вызывая метод getServiceLocator() в действии контроллера...

public function fooAction()
{
     $sm = $this->getServiceLocator();
     $model = $sm->get('SomeModel');
}

Когда ваша модель получена от диспетчера служб, служба initializer проверит, реализует ли она ServiceLocatorAwareInterface, и автоматически вызовет setServiceLocator(), если да, передав ей экземпляр диспетчера служб.

person Crisp    schedule 05.06.2013
comment
спасибо за ответ, но вы не правильно поняли мой вопрос - person Saidulu Buchhala; 05.06.2013
comment
Действительно? Что я пропустил? - person Crisp; 05.06.2013
comment
не могли бы вы написать код, который должен точно соответствовать моему вопросу - person Saidulu Buchhala; 05.06.2013
comment
Я написал код, объясняющий, как сделать локатор сервисов доступным в классе вашей модели. Как только вы это сделаете, в SomeModel вы сможете получить переводчик, позвонив в $this->getServiceLocator()->get('translator');. Итак, еще раз, если это не отвечает на ваш вопрос, что я упускаю? - person Crisp; 05.06.2013