How to create foreign keys in Laravel without errors - laravel

I'm trying to create foreign keys in Laravel. However, when I migrate my table using Artisan, I am thrown the following error.
Schema::create('billing_transactions', function (Blueprint $table) {
$table->id();
$table->integer('payment_amount')->default(0);
$table->tinyInteger('status')->default(0);
$table->foreignIdFor(PatientVisit::class)->nullable()->constrained()->onDelete('cascade')->onUpdate('cascade');
$table->foreignIdFor(BillingInvoice::class)->nullable()->constrained()->onDelete('cascade')->onUpdate('cascade');
$table->foreignId('created_by_id')->nullable()->constrained('users')->onDelete('cascade')->onUpdate('cascade');
$table->foreignId('updated_by_id')->nullable()->constrained('users')->onDelete('cascade')->onUpdate('cascade');
$table->timestamps();
});
SQLSTATE[HY000]: General error: 1215 Cannot add foreign key constraint
(SQL: alter table billing_transactions add constraint
billing_transactions_billing_invoice_id_foreign foreign key
(billing_invoice_id) references billing_invoices (id) on delete
cascade on update cascade)

/**
* Run the migrations.
*
* #return void
*/
public function up()
{
Schema::create('users', function (Blueprint $table) {
$table->id();
$table->BigInteger('role_id')->unsigned();
$table->BigInteger('lang_id')->unsigned()->nullable();
$table->BigInteger('reference_id')->unsigned()->nullable()->default(null);
$table->string('name');
$table->string('surname');
$table->boolean('blocked')->default(0);
$table->string('email')->unique();
$table->timestamp('email_verified_at')->nullable();
$table->string('password');
$table->rememberToken();
$table->timestamps();
});
Schema::table('users', function($table) {
$table->foreign('role_id')->references('id')->on('roles')->onDelete('cascade');
$table->foreign('lang_id')->references('id')->on('languages')->onDelete('cascade');
$table->foreign('reference_id')->references('id')->on('users')->onDelete('cascade');
});
}
/**
* Reverse the migrations.
*
* #return void
*/
public function down()
{
Schema::table('users', function($table) {
$table->dropForeign(['role_id']);
$table->dropColumn('role_id');
$table->dropForeign(['lang_id']);
$table->dropColumn('lang_id');
$table->dropForeign(['reference_id']);
$table->dropColumn('reference_id');
$table->dropUnique(['email']);
$table->dropColumn('email');
});
Schema::dropIfExists('users');
}
I use like that. For foreigns and uniques.

Related

Laravel Database Migration foreign key error while using "php artisan migrate" command

Error: SQLSTATE[HY000]: General error: 1005 Can't create table epicit_cms.ep_users (errno: 150 "Foreign key constraint is incorrectly formed") (SQL: alter table ep_users add constraint ep_users_client_id_foreign foreign key (client_id) references ep_clients (id) on delete cascade)
can someone explain what should do?
what i want to achieve is. if i want to delete a client it should delete users with the same client id too but i can't make it happen because i cant migrate my foreign key
Migration:
users table
public function up()
{
Schema::create('users', function (Blueprint $table) {
$table->uuid('id')->primary();
$table->string('name');
$table->string('insertion')->nullable();
$table->string('secondname');
$table->string('email')->unique();
$table->string('password');
$table->integer('client_id');
$table->foreign('client_id')->references('id')->on('clients')->onDelete('cascade');
$table->boolean('admin')->default(0);
$table->rememberToken();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* #return void
*/
public function down()
{
Schema::dropIfExists('users');
}
Clients table
public function up()
{
Schema::create('clients', function (Blueprint $table) {
$table->uuid('id')->primary();
$table->string('company_name');
$table->string('postal_code');
$table->string('street');
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* #return void
*/
public function down()
{
Schema::dropIfExists('clients');
}
Models:
User relation
public function Client()
{
return $this->belongsTo(Client::class );
}
Client relation
public function user()
{
return $this->hasMany(User::class);
}
change your migration like this
public function up()
{
Schema::create('users', function (Blueprint $table) {
$table->uuid('id')->primary();
$table->string('name');
$table->string('insertion')->nullable();
$table->string('secondname');
$table->string('email')->unique();
$table->string('password');
$table->foreignId('client_id')
->constrained()
->onDelete('cascade');
$table->boolean('admin')->default(0);
$table->rememberToken();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* #return void
*/
public function down()
{
Schema::dropIfExists('users');
}
You should make sure, your Clients table migration is running before users table migration.
And also your foreign_key field and your id should be of the same type, for example, if clients.id is bigIncrements, your foreign_key inside your user table also should be bigInteger.
Okay thank you guys for showing more then one way to do it. I fixed my code using this $table->foreignId('client_id')->constrained()->onDelete('cascade'); the way #sherifcoder did it and i changed client tabel from this $table->uuid('id')->primary(); to $table->id('id'); .I did more research into UUID and what it appears to be that UUID it doesn't always work with FKS. Again thank you for time

Laravel foreign key constraint is incorrectly formed (errno 150)

can someone tell me why do I get a foreign key is incorrectly formed?
Here is part of the code:
public function up()
{
Schema::create('posts', function (Blueprint $table) {
$table->id();
$table->foreignId('user_id')->constrained()->onDelete('cascade');
$table->string('title');
$table->text('content');
$table->string('featured');
$table->string('slug');
$table->foreignId('category_id')->constrained()->onDelete('cascade');
$table->softDeletes();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* #return void
*/
public function down()
{
Schema::dropIfExists('posts');
}
Here is the categories table:
public function up()
{
Schema::create('categories', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->string('slug');
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* #return void
*/
public function down()
{
Schema::dropIfExists('categories');
}
Note
It does not drop this error for 'user_id' foreign key just for categories.
FIX FOR THIS ISSUE
just change date on your database/migrations - migration for example if you want your categories to be created before posts table do this change:
2020_08_06_172006_create_posts_table.php
2020_08_09_172006_create_categories_table.php
change date on categories migration from
2020_08_09 to for example 2020_07_09
I'm guessing your table posts is created before categories
Therefore, you cannot constraint posts.category_id to the categories.id table.
In order to fix the issue you should create the table categories before creating the table posts

I cant migrate, what shoud I do( laravel-5.8 ) ? SQLSTATE[HY000]: General error: 1215 Cannot add foreign key constraint

1.why cant I migrate ?
I wanted to crate role permission table, but i cant add foreign key, i got this error : SQLSTATE[HY000]: General error: 1215 Cannot add foreign key constraint
i tried to migrate, but got some errors
i dont know what should i do in laravel 5.8
use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;
class CreateRoleAndPermissionTable extends Migration
{
/**
* Run the migrations.
*
* #return void
*/
public function up()
{
Schema::create('roles', function (Blueprint $table) {
$table->increments('id');
$table->string('name');
$table->string('title')->nullable();
$table->timestamps();
});
Schema::create('permissions', function (Blueprint $table) {
$table->increments('id');
$table->string('name');
$table->string('title')->nullable();
$table->timestamps();
});
**Schema::create('role_user', function (Blueprint $table) {
$table->integer('role_id')->unsigned();
$table->integer('user_id')->unsigned();
$table->foreign('role_id')->references('id')->on('roles')->onDelete('cascade')->onUpdate('cascade');
$table->foreign('user_id')->references('id')->on('users')->onDelete('cascade')->onUpdate('cascade');
$table->primary(['role_id','user_id']);
});
2.it just migrate upper tables,It wont migrate this table ?
Schema::create('permission_role', function (Blueprint $table) {
$table->integer('permission_id')->unsigned();
$table->integer('role_id')->unsigned();
$table->foreign('permission_id')->references('id')->on('permissions')->onDelete('cascade')->onUpdate('cascade');
$table->foreign('role_id')->references('id')->on('roles')->onDelete('cascade')->onUpdate('cascade');
$table->primary(['permission_id','role_id']);
});
}
/**
* Reverse the migrations.
*
* #return void
*/
public function down()
{
Schema::dropIfExists('role_and_permission');
}
}
Comment or remove all $table->foreign('') from all migration. It will work.
The best solution is to use $table->bigIncrements('') on primary key rather than $table->increments('') and $table->unsignedBigInteger(''); for foreign keys rather than $table->integer('');.
Because Laravel 5.8 uses $table->bigIncrements('') on primary key and $table->unsignedBigInteger(''); for foreign keys.

laravel migration "SQL: alter table `posts` add constraint `posts_category_id_foreign` foreign key (`category_id`) references `categories` (`id`) "

am trying to do laravel migration but am getting this error
[Illuminate\Database\QueryException]
SQLSTATE[HY000]: General error: 1005 Can't create table `urbancruise`.`#sql-18f8_112` (errno: 150 "Foreign key cons
traint is incorrectly formed") (SQL: alter table `posts` add constraint `posts_category_id_foreign` foreign key (`c
ategory_id`) references `categories` (`id`))
here is my code
Schema::create('categories', function (Blueprint $table) {
$table->increments('id');
$table->string('name');
$table->timestamps();
});
}
public function down(){
Schema::drop('categories');
}
public function up(){
Schema::create('posts', function (Blueprint $table) {
$table->increments('id');
$table->bigInteger('category_id')->unsigned();
$table->foreign('category_id')->references('id')->on('categories');
$table->timestamps();
});
}
public function down(){
Schema::drop('posts');
}
When you are creating a foreign key, the categories.id and posts.category_id must have the same type.
Swap the ->bigInteger() with ->integer()should solve your problem:
Your categories migration:
public function up(){
Schema::create('categories', function (Blueprint $table) {
$table->increments('id');
$table->string('name');
$table->timestamps();
});
}
public function down(){
Schema::drop('categories');
}
In your posts migration:
public function up(){
Schema::create('posts', function (Blueprint $table) {
$table->increments('id');
$table->integer('category_id', false, true);
//Or $table->unsignedInteger('category_id');
$table->foreign('category_id')
->references('id')
->on('categories');
$table->timestamps();
});
}
public function down(){
Schema::drop('posts');
}
Hope it helps.
Foreign key should always be of same type in both child and parent table.
In your case, categories.id is of type ٰINTEGER while posts.category_id is defined as BIGINT. Replacing your posts migration with below should work.
public function up() {
Schema::create('posts', function (Blueprint $table) {
$table->increments('id');
$table->integer('category_id')->unsigned();
$table->foreign('category_id')->references('id')->on('categories');
$table->timestamps();
});
}

Foreign Key issue with migrations

Im using the package https://github.com/musonza/groups to added group system on my laravel app, but when I want to migrate I get the error:
Migration table created successfully.
Migrating: 2019_05_26_125854_create_groups_tables
Illuminate\Database\QueryException : SQLSTATE[HY000]: General error: 1005 Can't create table `groupsystem`.`#sql-2678_26` (errno: 150 "Foreign key constraint is incorrectly formed") (SQL: alter table `groups` add constraint `groups_user_id_foreign` foreign key (`user_id`) references `users` (`id`) on delete cascade)
This is my 2 migrations table code:
<?php
use Illuminate\Support\Facades\Schema;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Database\Migrations\Migration;
class CreateUsersTable extends Migration
{
/**
* Run the migrations.
*
* #return void
*/
public function up()
{
Schema::create('users', function (Blueprint $table) {
$table->bigIncrements('id');
$table->string('name');
$table->string('email')->unique();
$table->timestamp('email_verified_at')->nullable();
$table->string('password');
$table->rememberToken();
$table->timestamps();
});
}
/**
* Reverse the migrations.
*
* #return void
*/
public function down()
{
Schema::dropIfExists('users');
}
}
And also this is the migration table I get from installing the package:
That I mentioned in the link in the top of this post
This is the first time I try to use this package
And im trying tocreate a group system on my laravel application
Any other suggetions will be welcomed
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreateGroupsTables extends Migration
{
/**
* Run the migrations.
*
* #return void
*/
public function up()
{
Schema::create('groups', function (Blueprint $table) {
$table->increments('id');
$table->string('name');
$table->string('description')->nullable();
$table->string('short_description')->nullable();
$table->string('image')->nullable();
$table->string('url')->nullable();
$table->integer('user_id')->unsigned();
$table->boolean('private')->unsigned()->default(false);
$table->integer('conversation_id')->unsigned()->nullable();
$table->text('extra_info')->nullable();
$table->text('settings')->nullable();
$table->timestamps();
$table->foreign('user_id')
->references('id')
->on('users')
->onDelete('cascade');
});
Schema::create('group_user', function (Blueprint $table) {
$table->increments('id');
$table->integer('user_id')->unsigned();
$table->integer('group_id')->unsigned();
$table->timestamps();
$table->foreign('user_id')
->references('id')
->on('users')
->onDelete('cascade');
$table->foreign('group_id')
->references('id')
->on('groups')
->onDelete('cascade');
});
Schema::create('posts', function (Blueprint $table) {
$table->increments('id');
$table->string('title');
$table->text('body');
$table->string('type');
$table->integer('user_id')->unsigned();
$table->text('extra_info')->nullable();
$table->timestamps();
$table->foreign('user_id')
->references('id')
->on('users')
->onDelete('cascade');
});
Schema::create('comments', function (Blueprint $table) {
$table->increments('id');
$table->string('body');
$table->integer('user_id')->unsigned();
$table->integer('post_id')->unsigned();
$table->string('type')->nullable();
$table->timestamps();
$table->foreign('user_id')
->references('id')
->on('users');
$table->foreign('post_id')
->references('id')
->on('posts');
});
Schema::create('group_post', function (Blueprint $table) {
$table->integer('group_id')->unsigned();
$table->integer('post_id')->unsigned();
$table->timestamps();
$table->foreign('group_id')
->references('id')
->on('groups')
->onDelete('cascade');
$table->foreign('post_id')
->references('id')
->on('posts')
->onDelete('cascade');
});
Schema::create('likes', function (Blueprint $table) {
$table->integer('user_id')->index();
$table->integer('likeable_id')->unsigned();
$table->string('likeable_type');
$table->primary(['user_id', 'likeable_id', 'likeable_type']);
$table->timestamps();
});
Schema::create('reports', function (Blueprint $table) {
$table->integer('user_id')->index();
$table->integer('reportable_id')->unsigned();
$table->string('reportable_type');
$table->primary(['user_id', 'reportable_id', 'reportable_type']);
$table->timestamps();
});
Schema::create('group_request', function (Blueprint $table) {
$table->increments('id');
$table->integer('user_id')->unsigned()->index();
$table->integer('group_id')->unsigned()->index();
$table->timestamps();
$table->foreign('group_id')
->references('id')
->on('groups')
->onDelete('cascade');
$table->foreign('user_id')
->references('id')
->on('users')
->onDelete('cascade');
});
}
/**
* Reverse the migrations.
*
* #return void
*/
public function down()
{
Schema::drop('groups');
Schema::drop('group_user');
Schema::drop('posts');
Schema::drop('comments');
Schema::drop('group_post');
Schema::drop('likes');
Schema::drop('reports');
Schema::drop('group_request');
}
}
If you have used laravel 5.8 then
$table->unsignedBigInteger('user_id');
$table->foreign('user_id')->references('id')->on('users');
If you have used laravel < 5.8 then
$table->unsignedInteger('user_id');
$table->foreign('user_id')->references('id')->on('users');
I did found the solution it's because of the new Laravel 5.8.3 it comes with unsignedBigInteger(id) instead of increments(id)

Resources