yii2 change database dynamically

Viewed 3723

I'm trying to move to another database dynamically. I've seen several questions that showed change db files from one to another and they just getting some information from next database. But what I need is completely moving to second database. How should I do this? I've seen that in order to achieve this dsn (in db.php file) should be altered. But I changed it and it's still not changed?? I should have full access to second database closing first one. Give me advice please

3 Answers

Set up multiple database connections in your main.php or main-local.php configuration

Yii::$app->db1;
Yii::$app->db2;
Yii::$app->db3;

when making inquiries

$usersDB1=User::find()->all(Yii::$app->db1);
$usersDB2=User::find()->all(Yii::$app->db2);
$usersDB3=User::find()->all(Yii::$app->db3);

Globally switch to a different database dynamically

I have combined Yerke's answer above and Write & use a custom Component in Yii2.0 here.

First, create a component class to do the DB switching. Here, I call it DbSelector and put it in app\components\DbSelector.php.

namespace app\components;

use Yii;
use yii\base\Component;
use yii\base\InvalidConfigException;

class DbSelector extends Component {

    const DB_MAIN = 'db';
    const DB_SUB1 = 'db1';
    const DB_SUB2 = 'db2';

    private static $db = self::DB_MAIN;

    public static function setDb($db)
    {
        self::$db = $db;
    }

    public static function getDb()
    {
        return \Yii::$app->get(self::$db);
    }
}

Second, modify the config/web.php file or whichever your config file is to have multiple databases and add DbSelector as a Yii::$app component.

$config = [
    'components' => [
        //...

        'db' => $db,
        'db1' => $db1,
        'db2' => $db2,

        'dbSelector' => [
            'class' => 'app\components\DbSelector',
        ],

        //...
    ],

    //...
];

Third, in each model class, add the following static function getDb() to call the DbSelector getDb():

public static function getDb()
{
    return \Yii::$app->dbSelector->getDb();
}

For example,

class DiningTable extends \yii\db\ActiveRecord
{
    public static function tableName()
    {
        return '{{%dining_table}}';
    }

    public static function getDb()
    {
        return \Yii::$app->dbSelector->getDb();
    }

    //...
}
    
class Customer extends \yii\db\ActiveRecord
{
    public static function tableName()
    {
        return '{{%customer}}';
    }

    public static function getDb()
    {
        return \Yii::$app->dbSelector->getDb();
    }

    //...
}

Lastly, to globally switch to a different database, use \Yii::$app->dbSelector->setDb(YOUR_PREFERRED_DB),

use app\components\DbSelector;

//...

\Yii::$app->dbSelector->setDb(DbSelector::DB_SUB1);
$tables_1 = DiningTable::findAll();
$customers_1 = Customer::find()->where(['<', 'dob', '2000-01-01'])->all();

\Yii::$app->dbSelector->setDb(DbSelector::DB_MAIN);
$tables_main = DiningTable::findAll();
$customers_main = Customer::find()->where(['<', 'dob', '2000-01-01'])->all();
Related