在zf2中配置多个数据库

时间:2012-12-22 13:22:56

标签: php zend-framework2

如何在Zend Framework 2中配置(和使用)多个数据库?目前我在global.php中有这个:

return array(
    'db' => array(
        'driver'         => 'Pdo',
        'dsn'            => 'mysql:dbname=my_db;host=localhost',
        'driver_options' => array(
            PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES \'UTF8\''
        ),
        'username' => 'user',
        'password' => '******',
    ),
    'service_manager' => array(
        'factories' => array(
            'Zend\Db\Adapter\Adapter' => 'Zend\Db\Adapter\AdapterServiceFactory',
        ),
    ),
);

但是我没有办法增加第二个。

2 个答案:

答案 0 :(得分:51)

如果查看Zend \ Db \ Adapter \ AdapterServiceFactory,您将看到适配器配置仅指向一个键'db'。这意味着它构建的适配器将始终使用此(唯一)配置密钥。

我建议您创建一个如下所示的工厂:

namespace Your\Namespace;

use Zend\ServiceManager\FactoryInterface;
use Zend\ServiceManager\ServiceLocatorInterface;
use Zend\Db\Adapter\Adapter;

class MyAdapterFactory implements FactoryInterface
{

  protected $configKey;

  public function __construct($key)
  {
      $this->configKey = $key;
  }

  public function createService(ServiceLocatorInterface $serviceLocator)
  {
      $config = $serviceLocator->get('Config');
      return new Adapter($config[$this->configKey]);
  }
}

在主模块(或任何其他模块)中,将以下内容添加到Module.php文件中,以将适配器工厂声明为Zend Service Manager:

use Your\Namespace\MyAdapterFactory;
use Zend\ModuleManager\Feature\ServiceProviderInterface;

class Module implements ServiceProviderInterface{

//Previous code

public function getServiceConfig()
{
    return array(
        'factories' => array(
            'myadapter1'        => new MyAdapterFactory('dbconfigkey1'),
            'myadapter2'        => new MyAdapterFactory('dbconfigkey2'),
            ),
       );

}

//...

全局配置现在应该如下所示:

return array(
'dbconfigkey1' => array(
    'driver'         => 'Pdo',
    'dsn'            => 'mysql:dbname=my_db;host=localhost',
    'driver_options' => array(
        PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES \'UTF8\''
    ),
    'username' => 'user',
    'password' => '******',
),

'dbconfigkey2' => array(
    'driver'         => 'Pdo',
    'dsn'            => 'mysql:dbname=my_db2;host=localhost',
    'driver_options' => array(
        PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES \'UTF8\''
    ),
    'username' => 'user',
    'password' => '******',
),

);

使用您需要使用服务管理器调用它们的适配器:

$adapter1=$serviceManager->get('myadapter1');
$adapter2=$serviceManager->get('myadapter2');

从版本2.2开始

抽象服务工厂现在是zf2 Zend \ Db模块的一部分。可以在“适配器”子键下添加多个配置键:

'db'=> array(
    'adapters'=>array(
        'adapter' => array(
            'driver'         => 'Pdo',
            'dsn'            => 'mysql:dbname=test;host=localhost',
            'username' => 'readCredential',
            'password' => '****'
        ),
        'adapter2' => array(
            'driver'         => 'Pdo',
            'dsn'            => 'mysql:dbname=test;host=localhost',
            'username' => 'rwCredential',
            'password' => '****'
        ),
    )
),

但是,AbstractServiceFactory需要“手动”添加,因为默认情况下不是这样:

'service_manager' => array(
    'abstract_factories' => array(
            'Zend\Db\Adapter\AdapterAbstractServiceFactory',
    )
),

可以像以前一样访问适配器:

$adapter1=$serviceManager->get('adapter');
$adapter2=$serviceManager->get('adapter2');

从性能角度来看,第二种方法更好:一个对象将被实例化(抽象工厂)以(可能)创建不同的适配器。而在之前的方法中,每个配置创建了一个对象。

答案 1 :(得分:3)

我在https://samsonasik.wordpress.com/2013/07/27/zend-framework-2-multiple-named-db-adapter-instances-using-adapters-subkey/

上找到了更好的解释

Zend Framework 2.2附带了abstract_factories Zend\Db\Adapter\AdapterAbstractServiceFactory,它允许我们配置多个命名的数据库适配器实例。这是一步一步做到的:

  1. 在'service_manager'键下的'abstract_factories'类型中注册Zend\Db\Adapter\AdapterAbstractServiceFactory

    //配置/自动加载/ global.php // .... config / autoload / global.php的一部分     'service_manager'=>阵列(         'abstract_factories'=>阵列(             '的Zend \ DB \适配器\ AdapterAbstractServiceFactory',         )     ),

  2. config/autoload/global.php

  3. 下的“db”键下配置“适配器”子项

    //配置/自动加载/ global.php // .... config / autoload / global.php的一部分

    'db' => array(
        'adapters' => array(
    
            'db1' => array(
               'driver'         => 'Pdo',
               'dsn'             => 'mysql:dbname=zf2_staging;host=localhost',
               'driver_options'  => array(
                    PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES \'UTF8\''
                ),
            ),
    
            'db2' => array(
               'driver'         => 'Pdo',
               'dsn'             => 'mysql:dbname=zf2_test;host=localhost',
               'driver_options'  => array(
                    PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES \'UTF8\''
                ),
            ),
        ),
    ),
    
    1. config/autoload/local.php
    2. 的“db”键下配置“adapters”子项

      //配置/自动加载/ local.php

      return array(
          'db' => array(
              'adapters' => array(
                  'db1' => array(
                      'username' => 'root',
                      'password' => '',
                  ),
                  'db2' => array(
                      'username' => 'other_user',
                      'password' => 'other_user_passwd',
                  ),
              ),
          ),
      );
      
      1. 使用'db1'或'db2'作为ServiceManager的数据库适配器调用适配器

        $ SM->获得( 'DB1');

        $ SM->获得( 'DB2');

      2. 如果您需要将$sm->get(‘Zend\Db\Adapter\Adapter’)作为主适配器,'db1'和'db2'作为特定用途的其他适配器,那么您需要直接在db下定义主适配器,因此{{1}的配置将如下所示:

        //配置/自动加载/ global.php

        config/autoload/global.php

        return array( 'db' => array( //this is for primary adapter.... 'driver' => 'Pdo', 'dsn' => 'mysql:dbname=zf21_learn;host=localhost', 'driver_options' => array( PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES \'UTF8\'' ), //other adapter when it needed... 'adapters' => array( 'db1' => array( 'driver' => 'Pdo', 'dsn' => 'mysql:dbname=zf2_staging;host=localhost', 'driver_options' => array( PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES \'UTF8\'' ), ), 'db2' => array( 'driver' => 'Pdo', 'dsn' => 'mysql:dbname=zf2_test;host=localhost', 'driver_options' => array( PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES \'UTF8\'' ), ), ), ), 'service_manager' => array( // for primary db adapter that called // by $sm->get('Zend\Db\Adapter\Adapter') 'factories' => array( 'Zend\Db\Adapter\Adapter' => 'Zend\Db\Adapter\AdapterServiceFactory', ), // to allow other adapter to be called by // $sm->get('db1') or $sm->get('db2') based on the adapters config. 'abstract_factories' => array( 'Zend\Db\Adapter\AdapterAbstractServiceFactory', ), ), ); 的配置也应如下所示:

        //配置/自动加载/ local.php

        config/autoload/global.local.php
相关问题