Миграции похожи на контроль версий для вашей базы данных, позволяют вашей команде определять схемы базы данных приложения и совместно использовать их определение. Если вам когда-либо приходилось указывать товарищу по команде вручную добавить столбец в его схему локальной базы данных после применения изменений в системе управления версиями, то вы столкнулись с проблемой, которую решает миграция базы данных.
Фасад Schema
обеспечивает независимую от базы данных поддержку для создания и управления таблицами во всех поддерживаемых Laravel системах баз данных. В обычной ситуации, этот фасад используется для создания и изменения таблиц / столбцов базы данных во время миграции.
Чтобы сгенерировать новую миграцию базы данных, используйте команду make:migration
Artisan. Эта команда поместит новый класс миграции в каталог database/migrations
вашего приложения. Каждое имя файла миграции содержит временную метку, которая позволяет Laravel определять порядок применения миграций:
php artisan make:migration create_flights_table
Laravel будет использовать имя миграции, чтобы попытаться угадать имя таблицы и будет ли миграция создавать новую таблицу. Если Laravel может определить имя таблицы по имени миграции, то сгенерированный файл миграции будет предварительно заполнен указанной таблицей. В противном случае вы можете просто вручную указать таблицу в файле миграции.
Если вы хотите указать собственный путь для сгенерированной миграции, вы можете использовать параметр --path
при выполнении команды make:migration
. Указанный путь должен быть относительно базового пути вашего приложения.
Примечание
Заготовки миграции можно настроить с помощью публикации заготовок.
По мере создания приложения вы можете со временем накапливать все больше и больше миграций. Это может привести к тому, что ваш каталог database/migrations
станет раздутым из-за потенциально сотен миграций. Если хотите, то можете «сжать» свои миграции в один файл SQL. Для начала выполните команду schema:dump
:
php artisan schema:dump
// Выгрузить текущую схему БД и удалить все существующие миграции ...
php artisan schema:dump --prune
Когда вы выполните эту команду, Laravel запишет файл «схемы» в каталог database/schema
вашего приложения. Имя файла схемы будет соответствовать подключению к базе данных. Теперь, когда вы попытаетесь перенести свою базу данных, Laravel сначала выполнит SQL-операторы файла схемы, при условии, что никакие другие миграции не выполнялись. После выполнения команд файла схемы, Laravel выполнит все оставшиеся миграции, которые не были включены в дамп схемы БД.
Если тесты вашего приложения используют соединение с базой данных, отличное от того, которое вы обычно используете во время локальной разработки, то вы должны убедиться, что вы создали дамп файла схемы, используя это соединение с базой данных, чтобы ваши тесты могли построить вашу базу данных. Вы можете сделать это после сброса подключения к базе данных, которое вы обычно используете во время локальной разработки:
php artisan schema:dump
php artisan schema:dump --database=testing --prune
Вы должны зафиксировать файл схемы базы данных в системе контроля версиями, чтобы другие / новые разработчики в вашей команде могли быстро воссоздать исходную структуру базы данных вашего приложения.
Предупреждение
Сжатие миграции доступно только для баз данных MySQL, PostgreSQL и SQLite и использует клиент командной строки базы данных. Дампы схемы не могут быть восстановлены в базах данных SQLite, хранимых в памяти.
Класс миграции содержит два метода: up
и down
. Метод up
используется для добавления новых таблиц, столбцов или индексов в вашу базу данных, тогда как метод down
должен отменять операции, выполняемые методом up
.
В обоих этих методах вы можете использовать построитель схем Laravel для выразительного создания и изменения таблиц. Чтобы узнать обо всех методах, доступных построителю Schema
, просмотрите его документацию. Например, следующая миграция создает таблицу flights
:
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
/**
* Запустить миграцию.
*
* @return void
*/
public function up()
{
Schema::create('flights', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->string('airline');
$table->timestamps();
});
}
/**
* Обратить миграции.
*
* @return void
*/
public function down()
{
Schema::drop('flights');
}
};
Если ваша миграция будет использовать соединение с базой данных, отличное от соединения с базой данных по умолчанию для вашего приложения, то необходимо установить свойство $connection
миграции:
/**
* Соединение с БД, которое должно использоваться миграцией.
*
* @var string
*/
protected $connection = 'pgsql';
/**
* Запустить миграцию.
*
* @return void
*/
public function up()
{
//
}
Чтобы запустить все незавершенные миграции, выполните команду migrate
Artisan:
php artisan migrate
Если вы хотите узнать, какие миграции уже выполнены, то вы можете использовать команду migrate:status
Artisan:
php artisan migrate:status
Если вы хотите увидеть операции SQL, выполняемые при миграции, без их фактического запуска, то вы можете указать флаг --pretend
для команды migrate
:
php artisan migrate --pretend
Если вы развертываете свое приложение на нескольких серверах и выполняете миграцию как часть процесса развертывания, то вы, вероятно, не хотите, чтобы два сервера пытались одновременно выполнить миграцию базу данных. Чтобы избежать этого, вы можете использовать флаг isolated
при вызове команды migrate
.
При передачи флага isolated
, Laravel получит атомарную блокировку, используя драйвер кеша вашего приложения, перед попыткой запуска миграций. Все другие попытки запустить команду migrate
, пока эта блокировка удерживается, не будут выполнены; эта команда всегда завершается с кодом успешного выхода:
php artisan migrate --isolated
Предупреждение
Чтобы использовать эту функцию, ваше приложение должно использовать драйвер кешаmemcached
,redis
,dynamodb
,database
,file
илиarray
в качестве драйвера кеша вашего приложения по умолчанию. Кроме того, все серверы должны обмениваться данными с одним и тем же сервером центрального кэша.
Некоторые операции миграции являются деструктивными, что означает, что они могут привести к потере данных. Чтобы защитить вас от запуска этих команд для вашей производственной базы данных, от вас потребуется подтверждение перед выполнением команд. Чтобы команды запускались без подтверждения, используйте флаг --force
:
php artisan migrate --force
Чтобы откатить последнюю операцию миграции, вы можете использовать команду rollback
Artisan. Эта команда откатывает последний «пакет» миграций, который может включать несколько файлов миграции:
php artisan migrate:rollback
Вы можете откатить ограниченное количество миграций, указав параметр step
для команды rollback
. Например, следующая команда откатит последние пять миграций:
php artisan migrate:rollback --step=5
Команда migrate:reset
откатит все миграции вашего приложения:
php artisan migrate:reset
Команда migrate:refresh
откатит все ваши миграции, а затем выполнит команду migrate
. Эта команда эффективно воссоздает всю вашу базу данных:
php artisan migrate:refresh
// Обновляем базу данных и запускаем все наполнители базы данных ...
php artisan migrate:refresh --seed
Вы можете откатить и повторно запустить ограниченное количество миграций, указав параметр step
для команды refresh
. Например, следующая команда откатит и повторно запустит последние пять миграций:
php artisan migrate:refresh --step=5
Команда migrate:fresh
удалит все таблицы из базы данных, а затем выполнит команду migrate
:
php artisan migrate:fresh
php artisan migrate:fresh --seed
Предупреждение
Командаmigrate:fresh
удалит все таблицы базы данных независимо от их префикса. Эту команду следует использовать с осторожностью при разработке в базе данных, которая используется совместно с другими приложениями.
Чтобы создать новую таблицу базы данных, используйте метод create
фасада Schema
. Метод create
принимает два аргумента: первый – это имя таблицы, а второй – замыкание, которое получает объект Blueprint
, используемый для определения новой таблицы:
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
Schema::create('users', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->string('email');
$table->timestamps();
});
При создании таблицы вы можете использовать любой из методов столбцов построителя схемы для определения столбцов таблицы.
Вы можете проверить наличие таблицы или столбца с помощью методов hasTable
и hasColumn
, соответственно:
if (Schema::hasTable('users')) {
// Таблица `users` существует ...
}
if (Schema::hasColumn('users', 'email')) {
// Таблица `users` существует и содержит столбец `email` ...
}
Если вы хотите выполнить операцию схемы с подключением, которое не является подключением к базе данных по умолчанию для вашего приложения, используйте метод connection
:
Schema::connection('sqlite')->create('users', function (Blueprint $table) {
$table->id();
});
Кроме того, некоторые другие свойства и методы могут использоваться для определения других аспектов создания таблицы. Свойство engine
используется для указания механизма хранения таблицы при использовании MySQL:
Schema::create('users', function (Blueprint $table) {
$table->engine = 'InnoDB';
// ...
});
Свойства charset
и collation
могут использоваться для указания набора символов и сопоставления для создаваемой таблицы при использовании MySQL:
Schema::create('users', function (Blueprint $table) {
$table->charset = 'utf8mb4';
$table->collation = 'utf8mb4_unicode_ci';
// ...
});
Метод temporary
используется, чтобы указать, что таблица должна быть «временной». Временные таблицы видны только текущему сеансу соединения базы данных и автоматически удаляются при закрытии соединения:
Schema::create('calculations', function (Blueprint $table) {
$table->temporary();
// ...
});
Если вы хотите добавить «комментарий» к таблице базы данных, то вы можете вызвать метод comment
для экземпляра table
. Комментарии к таблицам в настоящее время поддерживаются только в MySQL и Postgres:
Schema::create('calculations', function (Blueprint $table) {
$table->comment('Business calculations');
// ...
});
Метод table
фасада Schema
используется для обновления существующих таблиц. Подобно методу create
, метод table
принимает два аргумента: имя таблицы и замыкание, которое получает экземпляр Blueprint
, используемый для добавления столбцов или индексов в таблицу:
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
Schema::table('users', function (Blueprint $table) {
$table->integer('votes');
});
Чтобы переименовать существующую таблицу базы данных, используйте метод rename
:
use Illuminate\Support\Facades\Schema;
Schema::rename($from, $to);
Чтобы удалить существующую таблицу, вы можете использовать методы drop
или dropIfExists
:
Schema::drop('users');
Schema::dropIfExists('users');
Перед переименованием таблицы вы должны убедиться, что любые ограничения внешнего ключа в таблице имеют явное имя в ваших файлах миграции, вместо того, чтобы позволять Laravel назначать имя на основе соглашения. В противном случае, имя ограничения внешнего ключа будет ссылаться на имя старой таблицы.
Метод table
фасада Schema
используется для обновления существующих таблиц. Как и метод create
, метод table
принимает два аргумента: имя таблицы и замыкание, которое получает экземпляр Illuminate\Database\Schema\Blueprint
, используемый для добавления столбцов в таблицу:
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
Schema::table('users', function (Blueprint $table) {
$table->integer('votes');
});
Построитель схем Blueprint предлагает множество методов, соответствующих различным типам столбцов, которые вы можете добавить в таблицы базы данных. Все доступные методы перечислены в таблице ниже:
- bigIncrements
- bigInteger
- binary
- boolean
- char
- dateTimeTz
- dateTime
- date
- decimal
- double
- enum
- float
- foreignId
- foreignIdFor
- foreignUlid
- foreignUuid
- geometryCollection
- geometry
- id
- increments
- integer
- ipAddress
- json
- jsonb
- lineString
- longText
- macAddress
- mediumIncrements
- mediumInteger
- mediumText
- morphs
- multiLineString
- multiPoint
- multiPolygon
- nullableMorphs
- nullableTimestamps
- nullableUlidMorphs
- nullableUuidMorphs
- point
- polygon
- rememberToken
- set
- smallIncrements
- smallInteger
- softDeletesTz
- softDeletes
- string
- text
- timeTz
- time
- timestampTz
- timestamp
- timestampsTz
- timestamps
- tinyIncrements
- tinyInteger
- tinyText
- unsignedBigInteger
- unsignedDecimal
- unsignedInteger
- unsignedMediumInteger
- unsignedSmallInteger
- unsignedTinyInteger
- ulidMorphs
- uuidMorphs
- ulid
- uuid
- year
Метод bigIncrements
создает эквивалент автоинкрементного столбца UNSIGNED BIGINT
(первичный ключ):
$table->bigIncrements('id');
Метод bigInteger
создает эквивалент столбца BIGINT
:
$table->bigInteger('votes');
Метод binary
создает эквивалент столбца BLOB
:
$table->binary('photo');
Метод boolean
создает эквивалент столбца BOOLEAN
:
$table->boolean('confirmed');
Метод char
создает эквивалент столбца CHAR
указанной длины:
$table->char('name', 100);
Метод dateTimeTz
создает эквивалент столбца DATETIME
(с часовым поясом) с необязательной точностью (общее количество цифр):
$table->dateTimeTz('created_at', $precision = 0);
Метод dateTime
создает эквивалент столбца DATETIME
с необязательной точностью (общее количество цифр):
$table->dateTime('created_at', $precision = 0);
Метод date
создает эквивалент столбца DATE
:
$table->date('created_at');
Метод decimal
создает эквивалент столбца DECIMAL
с точностью (общее количество цифр) и масштабом (десятичные цифры):
$table->decimal('amount', $precision = 8, $scale = 2);
Метод double
создает эквивалент столбца DOUBLE
с точностью (общее количество цифр) и масштабом (десятичные цифры):
$table->double('amount', 8, 2);
Метод enum
создает эквивалент столбца ENUM
с указанием допустимых значений:
$table->enum('difficulty', ['easy', 'hard']);
Метод float
создает эквивалент столбца FLOAT
с точностью (общее количество цифр) и масштабом (десятичные цифры):
$table->float('amount', 8, 2);
Метод foreignId
создает эквивалент столбца UNSIGNED BIGINT
:
$table->foreignId('user_id');
Метод foreignIdFor
добавляет для переданного класса модели эквивалент столбца {column}_id UNSIGNED BIGINT
:
$table->foreignIdFor(User::class);
Метод foreignUlid
создает эквивалент столбца ULID
:
$table->foreignUlid('user_id');
Метод foreignUuid
создает эквивалент столбца UUID
:
$table->foreignUuid('user_id');
Метод geometryCollection
создает эквивалент столбца GEOMETRYCOLLECTION
:
$table->geometryCollection('positions');
Метод geometry
создает эквивалент столбца GEOMETRY
:
$table->geometry('positions');
Метод id
является псевдонимом метода bigIncrements
. По умолчанию метод создает столбец id
; однако, вы можете передать имя столбца, если хотите присвоить столбцу другое имя:
$table->id();
Метод increments
создает эквивалент автоинкрементного столбца UNSIGNED INTEGER
в качестве первичного ключа:
$table->increments('id');
Метод integer
создает эквивалент столбца INTEGER
:
$table->integer('votes');
Метод ipAddress
создает эквивалент столбца VARCHAR
:
$table->ipAddress('visitor');
Метод json
создает эквивалент столбца JSON
:
$table->json('options');
Метод jsonb
создает эквивалент столбца JSONB
:
$table->jsonb('options');
Метод lineString
создает эквивалент столбца LINESTRING
:
$table->lineString('positions');
Метод longText
создает эквивалент столбца LONGTEXT
:
$table->longText('description');
Метод macAddress
создает столбец, предназначенный для хранения MAC-адреса. Некоторые системы баз данных, такие как PostgreSQL, имеют специальный тип столбца для этого типа данных. Другие системы баз данных будут использовать столбец строкового эквивалента:
$table->macAddress('device');
Метод mediumIncrements
создает эквивалент автоинкрементного столбца UNSIGNED MEDIUMINT
в качестве первичного ключа:
$table->mediumIncrements('id');
Метод mediumInteger
создает эквивалент столбца MEDIUMINT
:
$table->mediumInteger('votes');
Метод mediumText
создает эквивалент столбца MEDIUMTEXT
:
$table->mediumText('description');
Метод morphs
– это удобный метод, который добавляет эквивалент столбца UNSIGNED BIGINT
({column}_id
) и эквивалент столбца VARCHAR
({column}_type
).
Этот метод предназначен для использования при определении столбцов, необходимых для полиморфного отношения Eloquent. В следующем примере будут созданы столбцы taggable_id
и taggable_type
:
$table->morphs('taggable');
Метод multiLineString
создает эквивалент столбца MULTILINESTRING
:
$table->multiLineString('positions');
Метод multiPoint
создает эквивалент столбца MULTIPOINT
:
$table->multiPoint('positions');
Метод multiPolygon
создает эквивалент столбца MULTIPOLYGON
:
$table->multiPolygon('positions');
Метод nullableTimestamps
является псевдонимом для timestamps:
$table->nullableTimestamps(0);
Метод аналогичен методу morphs
; тем не менее, создаваемый столбец будет иметь значение NULL:
$table->nullableMorphs('taggable');
Метод аналогичен методу ulidMorphs
; тем не менее, создаваемый столбец будет иметь значение NULL:
$table->nullableUlidMorphs('taggable');
Метод аналогичен методу uuidMorphs
; тем не менее, создаваемый столбец будет иметь значение NULL:
$table->nullableUuidMorphs('taggable');
Метод point
создает эквивалент столбца POINT
:
$table->point('position');
Метод polygon
создает эквивалент столбца POLYGON
:
$table->polygon('position');
Метод rememberToken
создает NULL-эквивалент столбца VARCHAR(100)
, предназначенный для хранения текущего токена аутентификации:
$table->rememberToken();
Метод set
создает эквивалент столбца SET
с заданным списком допустимых значений:
$table->set('flavors', ['strawberry', 'vanilla']);
Метод smallIncrements
создает эквивалент автоинкрементного столбца UNSIGNED SMALLINT
в качестве первичного ключа:
$table->smallIncrements('id');
Метод smallInteger
создает эквивалент столбца SMALLINT
:
$table->smallInteger('votes');
Метод softDeletesTz
добавляет NULL-эквивалент столбца TIMESTAMP
(с часовым поясом) с необязательной точностью (общее количество цифр). Этот столбец предназначен для хранения временной метки deleted_at
, необходимой для функции «программного удаления» Eloquent:
$table->softDeletesTz($column = 'deleted_at', $precision = 0);
Метод softDeletes
добавляет NULL-эквивалент столбца TIMESTAMP
с необязательной точностью (общее количество цифр). Этот столбец предназначен для хранения временной метки deleted_at
, необходимой для функции «программного удаления» Eloquent:
$table->softDeletes($column = 'deleted_at', $precision = 0);
Метод string
создает эквивалент столбца VARCHAR
указанной длины:
$table->string('name', 100);
Метод text
создает эквивалент столбца TEXT
:
$table->text('description');
Метод timeTz
создает эквивалент столбца TIME
(с часовым поясом) с необязательной точностью (общее количество цифр):
$table->timeTz('sunrise', $precision = 0);
Метод time
создает эквивалент столбца TIME
с необязательной точностью (общее количество цифр):
$table->time('sunrise', $precision = 0);
Метод timestampTz
создает эквивалент столбца TIMESTAMP
(с часовым поясом) с необязательной точностью (общее количество цифр):
$table->timestampTz('added_at', $precision = 0);
Метод timestamp
создает эквивалент столбца TIMESTAMP
с необязательной точностью (общее количество цифр):
$table->timestamp('added_at', $precision = 0);
Метод timestampsTz
создает столбцы created_at
и updated_at
, эквивалентные TIMESTAMP
(с часовым поясом) с необязательной точностью (общее количество цифр):
$table->timestampsTz($precision = 0);
Метод timestamps
создает столбцы created_at
и updated_at
, эквивалентные TIMESTAMP
с необязательной точностью (общее количество цифр):
$table->timestamps($precision = 0);
Метод tinyIncrements
создает эквивалент автоинкрементного столбца UNSIGNED TINYINT
в качестве первичного ключа:
$table->tinyIncrements('id');
Метод tinyInteger
создает эквивалент столбца TINYINT
:
$table->tinyInteger('votes');
Метод tinyText
создает эквивалент столбца TINYTEXT
:
$table->tinyText('notes');
Метод unsignedBigInteger
создает эквивалент столбца UNSIGNED BIGINT
:
$table->unsignedBigInteger('votes');
Метод unsignedDecimal
создает эквивалент столбца UNSIGNED DECIMAL
с необязательной точностью (общее количество цифр) и масштабом (десятичные цифры):
$table->unsignedDecimal('amount', $precision = 8, $scale = 2);
Метод unsignedInteger
создает эквивалент столбца UNSIGNED INTEGER
:
$table->unsignedInteger('votes');
Метод unsignedMediumInteger
создает эквивалент столбца UNSIGNED MEDIUMINT
:
$table->unsignedMediumInteger('votes');
Метод unsignedSmallInteger
создает эквивалент столбца UNSIGNED SMALLINT
:
$table->unsignedSmallInteger('votes');
Метод unsignedTinyInteger
создает эквивалент столбца UNSIGNED TINYINT
:
$table->unsignedTinyInteger('votes');
Метод ulidMorphs
– это удобный метод, который добавляет эквивалент столбца CHAR(26)
({column}_id
) и эквивалент столбца VARCHAR
({column}_type
).
Этот метод предназначен для использования при определении столбцов, необходимых для полиморфного отношения Eloquent, использующего идентификаторы ULID. В следующем примере будут созданы столбцы taggable_id
и taggable_type
:
$table->ulidMorphs('taggable');
Метод uuidMorphs
– это удобный метод, который добавляет эквивалент столбца CHAR(36)
({column}_id
) и эквивалент столбца VARCHAR
({column}_type
).
Этот метод предназначен для использования при определении столбцов, необходимых для полиморфного отношения Eloquent, использующего идентификаторы UUID. В следующем примере будут созданы столбцы taggable_id
и taggable_type
:
$table->uuidMorphs('taggable');
Метод ulid
создает эквивалент столбца ULID
:
$table->ulid('id');
Метод uuid
создает эквивалент столбца UUID
:
$table->uuid('id');
Метод year
создает эквивалент столбца YEAR
:
$table->year('birth_year');
В дополнение к типам столбцов, перечисленным выше, есть несколько «модификаторов» столбцов, которые вы можете использовать при добавлении столбца в таблицу базы данных. Например, чтобы сделать столбец «допускающим значение NULL», вы можете использовать метод nullable
:
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
Schema::table('users', function (Blueprint $table) {
$table->string('email')->nullable();
});
В следующей таблице представлены все доступные модификаторы столбцов. В этот список не входят модификаторы индексов:
Модификатор | Описание |
---|---|
->after('column') |
Поместить столбец «после» другого столбца (MySQL). |
->autoIncrement() |
Установить столбцы INTEGER как автоинкрементные (первичный ключ). |
->charset('utf8mb4') |
Указать набор символов для столбца (MySQL). |
->collation('utf8mb4_unicode_ci') |
Указать параметры сравнения для столбца (MySQL/PostgreSQL/SQL Server). |
->comment('my comment') |
Добавить комментарий к столбцу (MySQL/PostgreSQL). |
->default($value) |
Указать значение «по умолчанию» для столбца. |
->first() |
Поместить столбец «первым» в таблице (MySQL). |
->from($integer) |
Установить начальное значение автоинкрементного поля (MySQL / PostgreSQL). |
->invisible() |
Сделать столбец «невидимым» для SELECT * -запросов (MySQL). |
->nullable($value = true) |
Позволить (по умолчанию) значения NULL для вставки в столбец. |
->storedAs($expression) |
Создать сохраненный генерируемый столбец (MySQL / PostgreSQL). |
->unsigned() |
Установить столбцы INTEGER как UNSIGNED (MySQL). |
->useCurrent() |
Установить столбцы TIMESTAMP для использования CURRENT_TIMESTAMP в качестве значения по умолчанию. |
->useCurrentOnUpdate() |
Установить столбцы TIMESTAMP для использования CURRENT_TIMESTAMP при обновлении записи. |
->virtualAs($expression) |
Создать виртуальный генерируемый столбец (MySQL). |
->generatedAs($expression) |
Создать столбец идентификаторов с указанными параметрами последовательности (PostgreSQL). |
->always() |
Определить приоритет значений последовательности над вводом для столбца идентификаторов (PostgreSQL). |
->isGeometry() |
Установить тип пространственного столбца как geometry , т.е. тип по умолчанию для geography (PostgreSQL). |
Модификатор default
принимает значение или экземпляр Illuminate\Database\Query\Expression
. Использование экземпляра Expression
не позволит Laravel заключить значение в кавычки и позволит вам использовать функции, специфичные для базы данных. Одна из ситуаций, когда это особенно полезно, когда вам нужно назначить значения по умолчанию для столбцов JSON:
<?php
use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Query\Expression;
use Illuminate\Database\Migrations\Migration;
return new class extends Migration
{
/**
* Запустить миграцию.
*
* @return void
*/
public function up()
{
Schema::create('flights', function (Blueprint $table) {
$table->id();
$table->json('movies')->default(new Expression('(JSON_ARRAY())'));
$table->timestamps();
});
}
};
Предупреждение
Поддержка выражений по умолчанию зависит от вашего драйвера базы данных, версии базы данных и типа поля. См. документацию к вашей базе данных. Кроме того, невозможно комбинировать необработанные выраженияdefault
(используяDB::raw
) и изменения столбцов через методchange
.
Метод after
добавляет набор столбцов после указанного существующего столбца в схеме базы данных MySQL:
$table->after('password', function ($table) {
$table->string('address_line1');
$table->string('address_line2');
$table->string('city');
});
Перед изменением столбца вы должны установить пакет doctrine/dbal
с помощью менеджера пакетов Composer. Библиотека Doctrine DBAL используется для определения текущего состояния столбца и для создания запросов SQL, необходимых для внесения запрошенных изменений в столбец:
composer require doctrine/dbal
Если вы планируете изменять столбцы, созданные с помощью метода timestamp
, вы также должны добавить следующую конфигурацию в файл config/database.php
вашего приложения:
use Illuminate\Database\DBAL\TimestampType;
'dbal' => [
'types' => [
'timestamp' => TimestampType::class,
],
],
Предупреждение
Если ваше приложение использует Microsoft SQL Server, то убедитесь, что вы установилиdoctrine/dbal:^3.0
.
Метод change
позволяет вам изменять тип и атрибуты существующих столбцов. Например, вы можете увеличить размер string
столбца. Чтобы увидеть метод change
в действии, давайте увеличим размер столбца name
до 50. Для этого мы просто определяем новое состояние столбца и затем вызываем метод change
:
Schema::table('users', function (Blueprint $table) {
$table->string('name', 50)->change();
});
Мы также можем изменить столбец, чтобы он допускал значение NULL:
Schema::table('users', function (Blueprint $table) {
$table->string('name', 50)->nullable()->change();
});
Предупреждение
Только следующие типы столбцов могут быть изменены:bigInteger
,binary
,boolean
,char
,date
,dateTime
,dateTimeTz
,decimal
,double
,integer
,json
,longText
,mediumText
,smallInteger
,string
,text
,time
,tinyText
,unsignedBigInteger
,unsignedInteger
,unsignedSmallInteger
иuuid
. Чтобы изменить столбец типаtimestamp
, должен быть зарегистрирован Doctrine Type.
Чтобы переименовать столбец, вы можете использовать метод renameColumn
построителя схемы:
Schema::table('users', function (Blueprint $table) {
$table->renameColumn('from', 'to');
});
Если вы используете установку базы данных более ранней, чем один из нижеуказанных выпусков, то вы должны убедиться, что вы установили библиотеку doctrine/dbal
через менеджер пакетов Composer, прежде чем переименовывать столбец:
- MySQL <
8.0.3
- MariaDB <
10.5.2
- SQLite <
3.25.0
Чтобы удалить столбец, вы можете использовать метод dropColumn
построителя схемы:
Schema::table('users', function (Blueprint $table) {
$table->dropColumn('votes');
});
Вы можете удалить несколько столбцов из таблицы, передав массив имен столбцов методу dropColumn
:
Schema::table('users', function (Blueprint $table) {
$table->dropColumn(['votes', 'avatar', 'location']);
});
Если вы используете версию SQLite до 3.35.0
, то вы должны установить пакет doctrine/dbal
через менеджер пакетов Composer, прежде чем можно будет использовать метод dropColumn
. Удаление или изменение нескольких столбцов в рамках одной миграции при использовании этого пакета не поддерживается.
Laravel содержит несколько удобных методов, связанных с удалением общих типов столбцов. Каждый из этих методов описан в таблице ниже:
Команда | Описание |
---|---|
$table->dropMorphs('morphable'); |
Удалить столбцы morphable_id и morphable_type . |
$table->dropRememberToken(); |
Удалить столбец remember_token . |
$table->dropSoftDeletes(); |
Удалить столбец deleted_at . |
$table->dropSoftDeletesTz(); |
Псевдоним dropSoftDeletes() . |
$table->dropTimestamps(); |
Удалить столбцы created_at и updated_at . |
$table->dropTimestampsTz(); |
Псевдоним dropTimestamps() . |
Построитель схем Laravel поддерживает несколько типов индексов. В следующем примере создается новый столбец email
и указывается, что его значения должны быть уникальными. Чтобы создать индекс, мы можем связать метод unique
с определением столбца:
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
Schema::table('users', function (Blueprint $table) {
$table->string('email')->unique();
});
В качестве альтернативы вы можете создать индекс после определения столбца. Для этого вы должны вызвать метод unique
построителя схемы Blueprint. Этот метод принимает имя столбца, который должен получить уникальный индекс:
$table->unique('email');
Вы даже можете передать массив столбцов методу индекса для создания составного индекса:
$table->index(['account_id', 'created_at']);
При создании индекса Laravel автоматически сгенерирует имя индекса на основе таблицы, имен столбцов и типа индекса, но вы можете передать второй аргумент методу, чтобы указать имя индекса самостоятельно:
$table->unique('email', 'unique_email');
Построитель схем Laravel содержит методы для создания каждого типа индекса, поддерживаемого Laravel. Каждый метод индекса принимает необязательный второй аргумент для указания имени индекса. Если не указано, то имя будет производным от имен таблицы и столбцов, используемых для индекса, а также типа индекса. Все доступные методы индекса описаны в таблице ниже:
Команда | Описание |
---|---|
$table->primary('id'); |
Добавить первичный ключ. |
$table->primary(['id', 'parent_id']); |
Добавить составной ключ. |
$table->unique('email'); |
Добавить уникальный индекс. |
$table->index('state'); |
Добавить простой индекс. |
$table->fullText('body'); |
Добавить полнотекстовый индекс (MySQL/PostgreSQL). |
$table->fullText('body')->language('english'); |
Добавить полнотекстовый индекс для указанного языка (PostgreSQL). |
$table->spatialIndex('location'); |
Добавить пространственный индекс (кроме SQLite). |
По умолчанию Laravel использует набор символов utf8mb4
. Если вы используете версию MySQL древнее 5.7.7 или MariaDB древнее 10.2.2, то вам может потребоваться вручную настроить длину строки по умолчанию, сгенерированную миграциями, чтобы MySQL мог создавать для них индексы. Вы можете настроить длину строки по умолчанию, вызвав метод Schema::defaultStringLength
в методе boot
поставщика App\Providers\AppServiceProvider
:
use Illuminate\Support\Facades\Schema;
/**
* Загрузка любых служб приложения.
*
* @return void
*/
public function boot()
{
Schema::defaultStringLength(191);
}
Кроме того, вы можете включить опцию innodb_large_prefix
для своей базы данных. Обратитесь к документации вашей базы данных для получения инструкций о том, как правильно включить эту опцию.
Чтобы переименовать индекс, вы можете использовать метод renameIndex
построителя схемы Blueprint. Этот метод принимает текущее имя индекса в качестве первого аргумента и желаемое имя в качестве второго аргумента:
$table->renameIndex('from', 'to')
Предупреждение
Если ваше приложение использует базу данных SQLite, то вы должны установить пакетdoctrine/dbal
через менеджер пакетов Composer, прежде чем можно будет использовать методrenameIndex
.
Чтобы удалить индекс, вы должны указать имя индекса. По умолчанию Laravel автоматически назначает имя индекса на основе имени таблицы, имени индексированного столбца и типа индекса. Вот некоторые примеры:
Команда | Описание |
---|---|
$table->dropPrimary('users_id_primary'); |
Удалить первичный ключ из таблицы users . |
$table->dropUnique('users_email_unique'); |
Удалить уникальный индекс из таблицы users . |
$table->dropIndex('geo_state_index'); |
Удалить простой индекс из таблицы geo . |
$table->dropFullText('posts_body_fulltext'); |
Удалить полнотекстовый индекс из таблицы posts . |
$table->dropSpatialIndex('geo_location_spatialindex'); |
Удалить пространственный индекс из таблицы geo (кроме SQLite). |
Если вы передадите массив столбцов в метод, удаляющий индексы, то обычное имя индекса будет сгенерировано на основе имени таблицы, столбцов и типа индекса:
Schema::table('geo', function (Blueprint $table) {
$table->dropIndex(['state']); // Удалить простой индекс `geo_state_index`.
});
Laravel также поддерживает создание ограничений внешнего ключа, которые используются для обеспечения ссылочной целостности на уровне базы данных. Например, давайте определим столбец user_id
в таблице posts
, который ссылается на столбец id
в таблице users
:
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
Schema::table('posts', function (Blueprint $table) {
$table->unsignedBigInteger('user_id');
$table->foreign('user_id')->references('id')->on('users');
});
Поскольку этот синтаксис довольно подробный, Laravel предлагает дополнительные, более сжатые методы, использующие соглашения, для повышения продуктивности разработки. При использовании метода foreignId
для создания столбца, пример выше можно переписать так:
Schema::table('posts', function (Blueprint $table) {
$table->foreignId('user_id')->constrained();
});
Метод foreignId
создает эквивалент столбца UNSIGNED BIGINT
, в то время как метод constrained
будет использовать соглашения для определения имени таблицы и столбца, на которые ссылаются. Если имя вашей таблицы не соответствует соглашениям Laravel, вы можете указать имя таблицы, передав его в качестве аргумента методу constrained
:
Schema::table('posts', function (Blueprint $table) {
$table->foreignId('user_id')->constrained('users');
});
Вы также можете указать желаемое действие для свойств ограничения «при удалении» и «при обновлении»:
$table->foreignId('user_id')
->constrained()
->onUpdate('cascade')
->onDelete('cascade');
Для этих действий также предусмотрен альтернативный синтаксис:
Метод | Описание |
---|---|
$table->cascadeOnUpdate(); |
Обновления должны выполняться каскадом. |
$table->restrictOnUpdate(); |
Обновления должны быть ограничены. |
$table->cascadeOnDelete(); |
Удаление должно происходить каскадом. |
$table->restrictOnDelete(); |
Удаление должно быть ограничено. |
$table->nullOnDelete(); |
При удалении значение внешнего ключа должно быть установлено как null . |
Любые дополнительные модификаторы столбца должны быть вызваны перед методом constrained
:
$table->foreignId('user_id')
->nullable()
->constrained();
Чтобы удалить внешний ключ, вы можете использовать метод dropForeign
, передав в качестве аргумента имя ограничения внешнего ключа, которое нужно удалить. Ограничения внешнего ключа используют то же соглашение об именах, что и индексы. Другими словами, имя ограничения внешнего ключа основано на имени таблицы и столбцов в ограничении, за которым следует суффикс _foreign
:
$table->dropForeign('posts_user_id_foreign');
В качестве альтернативы вы можете передать массив, содержащий имя столбца, который содержит внешний ключ, методу dropForeign
. Массив будет преобразован в имя ограничения внешнего ключа с использованием соглашений об именах ограничений Laravel:
$table->dropForeign(['user_id']);
Вы можете включить или отключить ограничения внешнего ключа в своих миграциях, используя следующие методы:
Schema::enableForeignKeyConstraints();
Schema::disableForeignKeyConstraints();
Schema::withoutForeignKeyConstraints(function () {
// Ограничения отключены в этом замыкании ...
});
Предупреждение
SQLite по умолчанию отключает ограничения внешнего ключа. При использовании SQLite убедитесь, что включили поддержку внешнего ключа в вашей конфигурации базы данных, прежде чем пытаться создать их в ваших миграциях. Кроме того, SQLite поддерживает внешние ключи только при создании, а не при изменении таблиц.
Для удобства каждая операция миграции инициирует событие. Все указанные ниже события расширяют базовый класс Illuminate\Database\Events\MigrationEvent
:
Класс | Описание |
---|---|
Illuminate\Database\Events\MigrationsStarted |
Сейчас будет выполнен пакет миграций. |
Illuminate\Database\Events\MigrationsEnded |
Выполнение пакета миграций завершено. |
Illuminate\Database\Events\MigrationStarted |
Сейчас будет выполнена одна миграция. |
Illuminate\Database\Events\MigrationEnded |
Выполнение одиночной миграции завершено. |
Illuminate\Database\Events\SchemaDumped |
Дамп схемы базы данных завершен. |
Illuminate\Database\Events\SchemaLoaded |
Загружен существующий дамп схемы базы данных. |