ZF2: позвонить в службу из внешнего класса?

В моем проекте Zend Framework 2 у меня есть внешняя библиотека, и я хочу сохранить информацию в базе вместе с моделью.

............

РЕДАКЦИОННОЕ СООБЩЕНИЕ:

Я снова объясняю свою потребность: в своих контроллерах я делаю вставки и удаления в базе данных и хочу записывать все действия в таблицу "t_log". Для этого я подумал создать внешний класс.

У меня вопрос: как я могу вызвать метод моделей из моего внешнего класса?

namespace Mynamespace;

use Firewall\Model\Logs;
use Firewall\Model\LogsTable;

class StockLog
{
    public function addLog()
    {
       $log = $this->getServiceLocator()->get('Firewall\Model\LogTable');
       $log->save('user added'); 
       die('OK');
    }
}

Моя модель:

namespace Firewall\Model;

use Zend\Db\TableGateway\TableGateway;
use Zend\Db\Sql\Select;

class UserGroupTable
{

    protected $tableGateway;

    public function __construct(TableGateway $tableGateway)
    {
        $this->tableGateway = $tableGateway;
    }

    public function save()
    {
        // How I Can call this method from the StockLog method ?
    }
}

Спасибо вам!

1 ответ

Решение

getServiceLocator является функцией \Zend\Mvc\Controller\AbstractActionController поэтому он должен использоваться в ваших контроллерах.

Я не знаю, что ты StockLog класс есть, но он не расширяет какой-либо другой класс, поэтому я думаю, что он не имеет этой функции, и ваша ошибка на шаг раньше, в вызове getSErviceLocator это не определено, поэтому его не возвращают объект.

Вероятно, вы можете ввести сервисный локатор с чем-то вроде

class StockLog 
{

  private $serviceLocator= null;

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


    public function add()
    {
       # Do you know how I can call the service ??
       $User = $this->serviceLocator->get('Firewall\Model\UserTable');
    }


}

и затем, когда вы создаете свой объект StockLog, в вашем контроллере вы вводите service locator

public class yourController extends AbstractActionController {

   public function yourAction(){
      $mStockLog = new StockLog ();
       $mStockLog->setServiceLocator($this->getServiceLocator()); 
    /...

   }
}

Кроме того, если вам нужно только 'Firewall\Model\UserTable' сервис, вы должны внедрить именно это, вместо serviceLocator.

В любом случае, вы должны минимизировать знания классов вашей модели об остальной части системы, всегда помня о принципе инверсии зависимостей, чтобы добиться лучшего разделения.

ОБНОВИТЬ

добавить таблицу журналов

namespace Mynamespace;

use Firewall\Model\Logs; use Firewall\Model\LogsTable;

class StockLog {


 private $logTable= null;

  public function setLogTable($logTable)
  {
    $this->logTable= $logTable;
  }

public function addLog()
{

   $this->logTable->save('user added'); 
   die('OK');
}

}

и затем, когда вы создаете свой StockLog (в вашем контроллере, или где бы вы ни делали его, прежде чем его использовать), вы вводите объект logtable

  $mStockLog = new StockLog ();
  $mStockLog->setLogTable($this->getServiceLocator()->get('Firewall\Model\LogTable')); 

Конечно, я полагаю, что вы правильно настроили свой Firewall\Model\LogTable класс, который нужно получить с помощью менеджера сервисов, в getServiceConfig() в вашем Module.php

  public function getServiceConfig() {
       return array (
            'factories' => array (
                    'Firewall\Model\LogTable' => function ($sm) {
                         $logTable = //create it as you use to  
                  return $logTable;
            }  

        )

  }
Другие вопросы по тегам