Home > Software design >  Checking if in migration
Checking if in migration

Time:10-23

I had in one migration

$table->unsignedBigInteger('blog_category_id')->nullable();
$table->foreign('blog_category_id')
->references('id')->on('blog_categories')->onDelete('set null');

I am removing these fields with another migration

$table->dropForeign(['blog_category_id']);
$table->dropColumn('blog_category_id');

The first time everything goes well, but when the data is deleted from the database and I do a second migration, I get an error

SQLSTATE[42S01]: Base table or view already exists: 1050 Table 'articles' alre ady exists (SQL: create table 'articles' ('id' bigint unsigned not null auto_inc rement primary key) default character set utf8 collate 'utf8_general_ci' engine = InnoDB)

Can I do a check in the migration file, like if the field $table->foreign('blog_category_id') ->references('id')->on('blog_categories')->onDelete('set null'); empty then we do nothing. Can you do this in a laravel?

CodePudding user response:

I think instead of trying to search if such setup exists, you could rather add change() the to the end of the new migration as such if you know the table exists and the column exists.

$table->unsignedBigInteger('blog_category_id')->nullable()->change();

$table->foreign('blog_category_id')
->references('id')->on('blog_categories')->onDelete('set null');

See below if you don't know if table or column exists.

From your question, I see the table you were trying to create already exists. In other to prevent such error, you can check if table exists or not and create your migrations based on what is suitable. Example code below:

Example 1:

if(Schema::hasTable('articles')) {
  // Do something here is articles exists. (Mostly used for updating migration)
} else {
  // Do something if table doesn't exist (Mostly for creating migration)
}

Example 2. Check if column exists (you know table exists)

if(Schema::hasColumn('articles', 'blog_category_id')) {
  $table->unsignedBigInteger('blog_category_id')->nullable()->change();
$table->foreign('blog_category_id')
->references('id')->on('blog_categories')->onDelete('set null');
} else {
  $table->unsignedBigInteger('blog_category_id')->nullable();
  $table->foreign('blog_category_id')
->references('id')->on('blog_categories')->onDelete('set null');
}

Example 3. Check if column exists (multiple columns)

if(Schema::hasColumns('articles', ['blog_category_id', 'another_column'])) {
  $table->unsignedBigInteger('blog_category_id')->nullable()->change();
$table->foreign('blog_category_id')
->references('id')->on('blog_categories')->onDelete('set null');

 // More code
} else {
  $table->unsignedBigInteger('blog_category_id')->nullable();
  $table->foreign('blog_category_id')
->references('id')->on('blog_categories')->onDelete('set null');

 // More code
}

Check this for more information from Laravel docs if needed https://laravel.com/docs/8.x/migrations#checking-for-table-column-existence

Also though not necessary part of your question, Laravel has a function nullOnDelete() which you can chain to your foreign key part $table->foreign('blog_category_id') ->references('id')->on('blog_categories')->nullOnDelete(); to reduce the possibility of typos or just have some nice addition.

CodePudding user response:

I think you use $table->foreign('blog_category_id')->references('id')->on('blog_categories')->onDelete('cascade');

  • Related