Как создать новую базу данных с помощью миграции Yii2, когда я должен использовать ее по умолчанию? - PullRequest
0 голосов
/ 26 марта 2019

У меня есть задача, которая описана как «Создание новой базы данных с миграцией Yii2 и использование по умолчанию».Но у меня есть некоторый сговор: мне нужно настроить хотя бы одну базу данных по умолчанию в моем файле main-local.php, чтобы начать миграцию.Но я также должен создать эту базу данных с начальной миграцией.

return [
    'db' => [
        'class' => 'yii\db\Connection',
        'dsn' => 'mysql:host=localhost;dbname=default_base',
        'username' => 'root',
        'password' => '',
        'charset' => 'utf8',
    ],
];

Как я могу справиться с этим?Чтобы создать базу данных с миграцией и настроить ее по умолчанию.

Когда я выполняю свою миграцию (в моем файле миграции есть код):

public function safeUp()
{
    $this->execute("CREATE DATABASE default_base");
}

У меня есть исключение:

General error: 1007 Can't create database 'default_base'; database exists

Я понимаю, что это потому, что я уже создал default_base в phpmyadmin (нажмите кнопку «создана база данных») и связал его с приложением в моем файле main-local.php.Но мне нужно, чтобы эта база создавалась только когда я выполняю yii migrate.

UPD

Я попробовал способ, рекомендованный rob006, но получаю ошибку соединения

Exception 'yii\db\Exception' with message 'SQLSTATE[HY000] [1049] Unknown database 'default_base''

Мой main-local.php выглядит так, как рекомендует именно rob006, но я все еще не могу мигрировать.Это работает, только если я установил:

'preinstallDb' => [
                  'class'    => 'yii\db\Connection',
                  'dsn'      => 'mysql:host=localhost',
                  'username' => 'root',
                  'password' => '',
                  'charset'  => 'utf8',
            ],
            'db'           => [
                  'class'    => 'yii\db\Connection',
                  'dsn'      => 'mysql:host=localhost;dbname=already_exists_db',
                  'username' => 'root',
                  'password' => '',
                  'charset'  => 'utf8',
            ],

С уже существующей базой данных.Что я опять делаю не так?

Ответы [ 2 ]

4 голосов
/ 26 марта 2019

Вы можете определить DSN без имени базы данных:

'dsn' => 'mysql:host=localhost',

И использовать это соединение для создания базы данных.

Yii::$app->preinstallDb->createCommand('CREATE DATABASE default_base')->execute();

Однако вы не можете создать базу данных при миграции - MigrateController нужна база данных для таблицы migration, чтобы сохранить историю миграций.Вам нужно создать базу данных, прежде чем MigrateController попытается получить доступ к таблице migration.Вы можете сделать это, переопределив MigrateController::getMigrationHistory():

class MigrateController extends \yii\console\controllers\MigrateController {

    protected function getMigrationHistory($limit) {
        Yii::$app->preinstallDb->createCommand('CREATE DATABASE IF NOT EXISTS default_base')->execute();

        return parent::getMigrationHistory($limit);
    }
}

И использовать свой контроллер в конфигурации консольного приложения:

'controllerMap' => [
    'migrate' => [
        'class' => MigrateController::class,
    ],
],

Но, честно говоря, это уродливое решение с большим количеством жесткого кодирования,может быть лучше создать некоторую утилиту настройки, которая будет выполнять создание базы данных вне основного приложения.Также обычно по соображениям безопасности пользователь БД, используемый приложением, даже не должен иметь прав для создания базы данных, поэтому вы можете пересмотреть свой вариант использования - вам действительно нужно создавать базу данных приложением?

0 голосов
/ 30 марта 2019

Я нахожу единственный способ заставить его работать на меня. Просто переопределяя init () в MigrateController. Сначала я добавил controllerMap в файл main-local.php:

'controllerMap' => [
            'migrate' => [
                  'class' => 'console\controllers\MigrateController',]]

Затем поместите новый контроллер в консоль \ контроллеры:

 namespace console\controllers;
use yii\console\controllers\MigrateController as BasicMigrateController;
use Yii;
class MigrateController extends BasicMigrateController
{
   public function init()
    {
       Yii::$app->preinstallDb->createCommand('CREATE DATABASE IF NOT EXISTS default_base')->execute();
       parent::init();
    }
}
...