2009-11-05 3 views
22

У меня есть приложение Zend Framework на основе настройки quick-start.Как я могу получить доступ к конфигурации приложения Zend Framework с контроллера?

Я получил демоверсии, и теперь я собираюсь создать экземпляр нового класса модели для выполнения реальной работы. В моем контроллере я хочу передать параметр конфигурации (указанный в application.ini) к моей модели конструктора, что-то вроде этого:

class My_UserController extends Zend_Controller_Action 
{ 
    public function indexAction() 
    { 
     $options = $this->getFrontController()->getParam('bootstrap')->getApplication()->getOptions(); 
     $manager = new My_Model_Manager($options['my']); 
     $this->view->items = $manager->getItems(); 
    } 
} 

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

ответ

47

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

protected function _initConfig() 
{ 
    $config = new Zend_Config($this->getOptions(), true); 
    Zend_Registry::set('config', $config); 
    return $config; 
} 

Это позволит сократить ваш код немного:

class My_UserController extends Zend_Controller_Action 
{ 
    public function indexAction() 
    { 
     $manager = new My_Model_Manager(Zend_Registry::get('config')->my); 
     $this->view->items = $manager->getItems(); 
    } 
} 
+0

Это займет немного работы, чтобы повторно разбить массив на объект. Если вы предпочитаете иметь конфигурацию в виде массива, это просто «Zend_Registry :: set (« config », $ this-> getOptions()); хотя вам придется вывести его в переменную, прежде чем получить значение. –

+0

@Alister: Вы правы, тем быстрее будет хранить параметры-массивы в реестре, но хранение массива каждый раз, когда вы хотите получить одно значение, может быть громоздким. –

+2

Это не отличается от идеи $ GLOBALS ['application'] ниже, с дополнительным преимуществом, что $ GLOBALS ['application'] работает, вероятно, в 99% случаев. –

6

В качестве альтернативы, вместо использования Zend_Registry вы также можете создать одноэлементный класс приложений, который будет содержать всю информацию приложений с функциями общественных членов, которые позволяют вы получите доступ к соответствующим данным. Ниже вы можете найти фрагмент с соответствующим кодом (он не будет работать, как есть, просто чтобы дать вам представление о том, как она может быть реализована):

final class Application 
{ 
    /** 
    * @var Zend_Config 
    */  
    private $config = null; 

    /** 
    * @var Application 
    */  
    private static $application; 

    // snip 

    /** 
    * @return Zend_Config 
    */ 
    public function getConfig() 
    { 
     if (!$this->config instanceof Zend_Config) { 
      $this->initConfig(); 
     } 
     return $this->config; 
    } 

    /** 
    * @return Application 
    */ 
    public static function getInstance() 
    { 
     if (self::$application === null) { 
      self::$application = new Application(); 
     } 
     return self::$application; 
    } 

    /** 
    * Load Configuration 
    */ 
    private function initConfig() 
    { 
     $configFile = $this->appDir . '/config/application.xml'; 
     if (!is_readable($configFile)) { 
      throw new Application_Exception('Config file "' . $configFile . '" is not readable'); 
     } 
     $config = new Zend_Config_Xml($configFile, 'test'); 
     $this->config = $config; 
    } 

    // snip 

    /** 
    * @param string $appDir 
    */ 
    public function init($appDir) 
    { 
     $this->appDir = $appDir; 
     $this->initConfig(); 
     // snip 
    } 

    public function run ($appDir) 
    { 
     $this->init($appDir); 
     $front = $this->initController(); 
     $front->dispatch();    
    } 
} 

Ваш самозагрузки будет выглядеть следующим образом:

require 'Application.php'; 
try { 
    Application::getInstance()->run(dirname(dirname(__FILE__))); 
} catch (Exception $e) { 
    header("HTTP/1.x 500 Internal Server Error"); 
    trigger_error('Application Error : '.$e->getMessage(), E_USER_ERROR); 
} 

Если вы хотите получить доступ к конфигурации вы должны использовать следующее:

$var = Application::getInstance()->getConfig()->somevar; 
0

Я определить короткую руку в каком-то месте я require_once() в начале boostrap:

function reg($name, $value=null) { 
    (null===$value) || Zend_Registry::set($name, $value); 
    return Zend_Registry::get($name); 
} 

и в загрузчике у меня есть:

protected function _initFinal() 
{ 
    reg('::app', $this->getApplication()); 
} 

, то я могу получить экземпляр приложения в любом месте с помощью:

$app = reg('::app'); 
3

В большинстве приложений ZF, объект приложения объявлен в глобальный охват (см. public/index.php в приложениях, созданных с помощью ZFW_DISTRIBUTION/bin/zf.sh).

Это не совсем путь ZF, но вы можете получить доступ к объекту с помощью $GLOBALS['application']. Это похоже на обман, но если вы после исполнения, это, скорее всего, самый быстрый вариант.

$manager = new My_Model_Manager($GLOBALS['application']->getOption('my')); 
+1

Всегда можно обойти фреймворк и все его абстракции. Решение вроде этого должно быть взломом all-else-fail, а не готовым решением. В любом случае производительность вряд ли будет критической; переменная конфигурации не должна выбираться внутри критически важного цикла. –

+0

Что такое My_Model_Manager ?? – zardilior

+0

@zardilior my best guess (4 года) - это гипотетический пользовательский класс земли, который зависит от гипотетического пользовательского варианта «мой». Оба они вышли из вопроса SO ;-) –

21

Начиная с версией 1.8 вы можете использовать следующий код в контроллере:

$my = $this->getInvokeArg('bootstrap')->getOption('my'); 
1
$this->getInvokeArg('bootstrap')->getOptions(); 
// or 

$configDb = $this->getInvokeArg('bootstrap')->getOption('db'); 
0

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

class My_UserController extends Zend_Controller_Action { 
    public function indexAction() { 
     global $application; 
     $options = $application->getOptions(); 
    } 
} 
Смежные вопросы