如何使用架构构建器添加虚拟列?
How to add a virtual column with the schema builder?
我正在创建一个这样的 table,
Schema::create('booking_segments', function (Blueprint $table) {
$table->increments('id');
$table->datetime('start')->index();
$table->integer('duration')->unsigned();
$table->string('comments');
$table->integer('booking_id')->unsigned();
$table->foreign('booking_id')->references('id')->on('bookings')->onDelete('cascade');
});
但我想多加一栏。在原始 SQL 中看起来像这样:
ALTER TABLE booking_segments ADD COLUMN `end` DATETIME AS (DATE_ADD(`start`, INTERVAL duration MINUTE)) PERSISTENT AFTER `start`
如何将它添加到我的迁移中?我还需要在其上创建索引。
我不认为你可以用模式构建器来做(如果我错了请有人纠正我)但你总是可以 "fall back" 原始 SQL:
DB::statement('ALTER TABLE booking_segments ADD COLUMN `end` DATETIME AS (DATE_ADD(`start`, INTERVAL duration MINUTE)) PERSISTENT AFTER `start`');
我知道这是一个老问题,但是从 Laravel 5.3 开始就有一种使用架构构建器来解决这个问题的方法,所以我想我会把它放在这里是为了完整性。
您可以使用 laravel 5.3 column modifiers virtualAs 或 storedAs。
因此,要创建一个虚拟生成列以在每次查询时计算,您可以像这样创建列:
$table->dateTime('created_at')->virtualAs( 'DATE_ADD(`start`, INTERVAL duration MINUTE)' );
要创建存储的生成列,您可以像这样创建列:
$table->dateTime('created_at')->storedAs( 'DATE_ADD(`start`, INTERVAL duration MINUTE)' );
您也可以使用 Laravel 事件来获得相同的结果,而无需使用
存储为或虚拟为。
供参考:Laravel: performing some task on every insert/update when using Query Builder or Eloquent ORM
我是这样做的:
class MyModel extends Model
{
/** .... **/
/**
* The "booted" method of the model.
*
* @return void
*/
protected static function booted()
{
static::creating(function ($option) {
$option->column1 = $option->column2 + 2;
});
static::updating(function ($option) {
$option->column1 = $option->column2 + 2;
});
}
}
我正在创建一个这样的 table,
Schema::create('booking_segments', function (Blueprint $table) {
$table->increments('id');
$table->datetime('start')->index();
$table->integer('duration')->unsigned();
$table->string('comments');
$table->integer('booking_id')->unsigned();
$table->foreign('booking_id')->references('id')->on('bookings')->onDelete('cascade');
});
但我想多加一栏。在原始 SQL 中看起来像这样:
ALTER TABLE booking_segments ADD COLUMN `end` DATETIME AS (DATE_ADD(`start`, INTERVAL duration MINUTE)) PERSISTENT AFTER `start`
如何将它添加到我的迁移中?我还需要在其上创建索引。
我不认为你可以用模式构建器来做(如果我错了请有人纠正我)但你总是可以 "fall back" 原始 SQL:
DB::statement('ALTER TABLE booking_segments ADD COLUMN `end` DATETIME AS (DATE_ADD(`start`, INTERVAL duration MINUTE)) PERSISTENT AFTER `start`');
我知道这是一个老问题,但是从 Laravel 5.3 开始就有一种使用架构构建器来解决这个问题的方法,所以我想我会把它放在这里是为了完整性。
您可以使用 laravel 5.3 column modifiers virtualAs 或 storedAs。
因此,要创建一个虚拟生成列以在每次查询时计算,您可以像这样创建列:
$table->dateTime('created_at')->virtualAs( 'DATE_ADD(`start`, INTERVAL duration MINUTE)' );
要创建存储的生成列,您可以像这样创建列:
$table->dateTime('created_at')->storedAs( 'DATE_ADD(`start`, INTERVAL duration MINUTE)' );
您也可以使用 Laravel 事件来获得相同的结果,而无需使用 存储为或虚拟为。 供参考:Laravel: performing some task on every insert/update when using Query Builder or Eloquent ORM
我是这样做的:
class MyModel extends Model
{
/** .... **/
/**
* The "booted" method of the model.
*
* @return void
*/
protected static function booted()
{
static::creating(function ($option) {
$option->column1 = $option->column2 + 2;
});
static::updating(function ($option) {
$option->column1 = $option->column2 + 2;
});
}
}