简体   繁体   English

Laravel 数据库架构,可为空的外国

[英]Laravel Database Schema, Nullable Foreign

I've these two database tables:我有这两个数据库表:

  1. User Tables用户表
  2. Partner Tables伙伴表

User Tables will handle this kind of informations用户表将处理此类信息

Schema::create('users', function (Blueprint $table) {
      $table->increments('id')->unique();
      $table->string('email')->unique();
      $table->string('username')->unique();
      $table->string('password', 60);
      $table->string('photo')->nullable();
      $table->integer('partner_id')->unsigned();
      $table->foreign('partner_id')->references('id')->on('partners');
      $table->rememberToken();
      $table->timestamps();
});

While Partner Tables will contains all the user meta information such as first name and last name, etc.合作伙伴表将包含所有用户元信息,例如名字和姓氏等。

Schema::create('partners', function (Blueprint $table) {

    /**
     * Identity Columns
     */
    $table->increments('id')->unique();
    $table->string('first_name');
    $table->string('middle_name')->nullable();
    $table->string('last_name')->nullable();
    $table->string('display_name')->nullable();
    $table->string('email')->unique()->nullable();
    $table->string('website')->nullable();
    $table->string('phone')->nullable();
    $table->string('mobile')->nullable();
    $table->string('fax')->nullable();
    $table->date('birthdate')->nullable();
    $table->longText('bio')->nullable();
    $table->string('lang')->nullable(); //Language

    /**
     * Address Columns
     */
    $table->text('street')->nullable();
    $table->text('street2')->nullable();
    $table->integer('country_id')->unsigned(); // foreign
    $table->foreign('country_id')->references('id')->on('countries');
    $table->integer('state_id')->unsigned();   // foreign
    $table->foreign('state_id')->references('id')->on('country_states');
    $table->string('city')->nullable();
    $table->string('district')->nullable();
    $table->string('area')->nullable();
    $table->string('zip')->nullable();
});

When a user is register to the site I only want few fields which are, username , email address , password , first name and last name .当用户注册到该站点时,我只需要几个字段,即usernameemail addresspasswordfirst namelast name These are only the required fields.这些只是必填字段。

So information in partner tables can be filled later after the user have finish registering to the site.因此,合作伙伴表中的信息可以在用户完成网站注册后填写。

But due to the structure of foreign key, I cannot proceed any further because of this error:但是由于外键的结构,由于这个错误我无法继续进行:

SQLSTATE[23000]: Integrity constraint violation: 1452 Cannot add or update a child row: a foreign key constraint fails (`mytable`.`tbl_partners`, CONSTRAINT `partners_country_id_foreign` FOREIGN KEY (`country_id`) REFERENCES `tbl_countries` (`id`)) (SQL: insert into `tbl_partners` (`first_name`, `last_name`, `display_name`, `email`, `updated_at`, `created_at`) values (Jack, Wilson, admin, admin@example.com, 2016-06-09 19:41:18, 2016-06-09 19:41:18))

I know this is cause by the countries table which is required by the partner table.我知道这是由合作伙伴表所需的国家/地区表引起的。
My question is: is there a work around so I can fill the country or any other non required data on partner table but keep the foreign table schema for countries, states, etc.我的问题是:是否有解决方法,以便我可以在合作伙伴表上填写国家或任何其他不需要的数据,但保留国家、州等的外部表模式。

For laravel 7.x to create a nullable foreign key use simply:为了让 laravel 7.x 创建一个可为空的外键,只需简单地使用:

$table->foreignId('country_id')->nullable()->constrained();

$table->foreignId('state_id')->nullable()->constrained();

REMEMBER: nullable should be before constrained otherwise the nullable will not be affected.记住: nullable应该约束之前,否则 nullable 不会受到影响。

Set the country_id and the state_id nullable, like so.像这样设置country_idstate_id空。

$table->integer('country_id')->nullable()->unsigned();

$table->integer('state_id')->nullable()->unsigned();

With the latest version of Laravel, you can use the nullable method in conjunction of foreignKey :使用最新版本的 Laravel,您可以结合使用nullable方法来使用foreignKey

$table
      ->foreignId('other_table_id')
      ->nullable() // here
      ->references('id')
      ->on('other_table');

For Laravel 7.x I use this way:对于 Laravel 7.x,我使用这种方式:

$table->bigInteger('word_type_id')->nullable()->unsigned();
$table->index('word_type_id')->nullable();
$table->foreign('word_type_id')->nullable()->references('id')->on('word_types')->onDelete('cascade');

拉拉维尔 8

$table->foreignId('foreign_key_id')->nullable()->constrained()->onDelete('cascade');

Note that if you have references('{column}')->on('{table}') you need to put the nullable()->constrained() before this ie:请注意,如果您有 references('{column}')->on('{table}') ,则需要将 nullable()->constrained() 放在此之前,即:

$table->foreignId('author')->nullable()->constrained()->references('id')->on('users');

This is on Laravel 9 but probably earlier too.这是在 Laravel 9 上,但也可能更早。

Best way is最好的办法是

$table->unsignedBigInteger('country_id')->nullable();
$table->foreign('country_id')->references('id')->on('stock_indices')->onDelete('cascade');

$table->foreignId('profile_id')->nullable()->constrained('profiles')->onDelete('cascade');

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM