国产av日韩一区二区三区精品,成人性爱视频在线观看,国产,欧美,日韩,一区,www.成色av久久成人,2222eeee成人天堂

Laravel 遷移中外鍵定義與“重復(fù)列名”錯(cuò)誤的解決策略

心靈之曲
發(fā)布: 2025-07-11 22:42:19
原創(chuàng)
226人瀏覽過(guò)

Laravel 遷移中外鍵定義與“重復(fù)列名”錯(cuò)誤的解決策略

本文探討了在Laravel 8中定義外鍵時(shí)常見(jiàn)的“重復(fù)列名”錯(cuò)誤。該錯(cuò)誤通常因同時(shí)使用unsignedBigInteger和foreignId創(chuàng)建同一列引起。教程將詳細(xì)解釋foreignId輔助函數(shù)的正確用法,展示如何簡(jiǎn)潔高效地定義外鍵,避免重復(fù)列創(chuàng)建,確保數(shù)據(jù)庫(kù)遷移的順利執(zhí)行。

理解Laravel中的外鍵定義

在laravel中,數(shù)據(jù)庫(kù)遷移是管理數(shù)據(jù)庫(kù)結(jié)構(gòu)變更的強(qiáng)大工具。定義表之間的關(guān)系,特別是外鍵,是數(shù)據(jù)庫(kù)設(shè)計(jì)中的關(guān)鍵一環(huán)。laravel提供了多種方式來(lái)定義外鍵,其中foreignid()輔助函數(shù)是推薦且最簡(jiǎn)潔的方式。然而,不恰當(dāng)?shù)氖褂每赡軙?huì)導(dǎo)致“duplicate column name”(重復(fù)列名)錯(cuò)誤,尤其是在執(zhí)行php artisan migrate:fresh等命令時(shí)。

常見(jiàn)錯(cuò)誤:重復(fù)列名

當(dāng)開(kāi)發(fā)者嘗試在遷移文件中定義一個(gè)外鍵時(shí),如果同時(shí)手動(dòng)創(chuàng)建了用于外鍵的列類型(如unsignedBigInteger)又使用了foreignId()輔助函數(shù),就會(huì)出現(xiàn)重復(fù)列名錯(cuò)誤。

錯(cuò)誤示例代碼:

public function up()
{   
    Schema::enableForeignKeyConstraints(); // 通常不需要在up()方法內(nèi)手動(dòng)啟用
    Schema::create('dso', function (Blueprint $table) {
        $table->string('id_dso',30);
        $table->unsignedBigInteger('id_rso'); // 第一次創(chuàng)建 'id_rso' 列
        $table->foreignId('id_rso')->constrained('rso'); // foreignId() 再次嘗試創(chuàng)建 'id_rso' 列
        $table->smallInteger('id_focus');
        $table->smallInteger('id_wilayah');
        $table->smallInteger('id_grup_wilayah');
        $table->string('nama_dso',50);
        $table->string('created_by',50)->nullable();
        $table->timestamp('created_date',$precision = 0);
        $table->string('modified_by',50)->nullable();
        $table->timestamp('modified_date',$precision = 0)->nullable()->default(null);
        $table->boolean('status')->default(true);
        $table->timestamps();
        $table->primary('id_dso');
    });
}
登錄后復(fù)制

在上述代碼中,$table->unsignedBigInteger('id_rso'); 已經(jīng)創(chuàng)建了一個(gè)名為 id_rso 的 UNSIGNED BIGINT 類型的列。緊接著,$table->foreignId('id_rso')->constrained('rso'); 會(huì)再次嘗試創(chuàng)建一個(gè)名為 id_rso 的列,并將其定義為外鍵。由于該列已存在,數(shù)據(jù)庫(kù)會(huì)拋出 SQLSTATE[42S21]: Column already exists: 1060 Duplicate column name 'id_rso' 錯(cuò)誤。

foreignId() 輔助函數(shù)的正確用法

Laravel 的 foreignId() 輔助函數(shù)是一個(gè)非常方便的宏,它不僅會(huì)創(chuàng)建符合外鍵要求的列(默認(rèn)為 UNSIGNED BIGINT 類型),還會(huì)自動(dòng)將其定義為外鍵。因此,無(wú)需再手動(dòng)定義列類型。

正確用法示例:

public function up()
{   
    // Schema::enableForeignKeyConstraints(); // 通常不需要,Laravel默認(rèn)開(kāi)啟
    Schema::create('dso', function (Blueprint $table) {
        $table->string('id_dso',30);
        // 直接使用 foreignId() 創(chuàng)建并定義外鍵
        $table->foreignId('id_rso')->constrained('rso'); 
        $table->smallInteger('id_focus');
        $table->smallInteger('id_wilayah');
        $table->smallInteger('id_grup_wilayah');
        $table->string('nama_dso',50);
        $table->string('created_by',50)->nullable();
        $table->timestamp('created_date',$precision = 0);
        $table->string('modified_by',50)->nullable();
        $table->timestamp('modified_date',$precision = 0)->nullable()->default(null);
        $table->boolean('status')->default(true);
        $table->timestamps();
        $table->primary('id_dso');
    });
}
登錄后復(fù)制

在這個(gè)修正后的代碼中,$table->foreignId('id_rso')->constrained('rso'); 這一行代碼完成了兩項(xiàng)任務(wù):

  1. 創(chuàng)建了一個(gè)名為 id_rso 的 UNSIGNED BIGINT 類型的列。
  2. 將該列定義為外鍵,引用 rso 表的主鍵(默認(rèn)是 id 列)。

constrained() 方法詳解

constrained() 方法是 foreignId() 的鏈?zhǔn)秸{(diào)用,用于指定外鍵引用的表。

  • 默認(rèn)行為: 如果不傳入任何參數(shù),constrained() 會(huì)根據(jù)列名推斷引用的表名。例如,id_rso 會(huì)默認(rèn)引用 rso 表的 id 列。
  • 指定表名: 如果引用的表名與列名不符,可以顯式傳入表名,如 ->constrained('another_rso_table')。
  • 指定引用列: 如果引用的不是主表默認(rèn)的 id 列,可以使用 ->references('custom_id')->on('rso') 的形式,但這通常與 foreignId() 的簡(jiǎn)潔性相悖,更常見(jiàn)于手動(dòng)定義外鍵。

進(jìn)階用法與注意事項(xiàng)

  1. 刪除行為: 可以通過(guò) onDelete() 和 onUpdate() 方法來(lái)定義外鍵的級(jí)聯(lián)操作。

    $table->foreignId('user_id')->constrained()->onDelete('cascade'); // 當(dāng)關(guān)聯(lián)用戶被刪除時(shí),級(jí)聯(lián)刪除此記錄
    $table->foreignId('product_id')->constrained()->onUpdate('restrict'); // 當(dāng)關(guān)聯(lián)產(chǎn)品ID更新時(shí),限制操作
    登錄后復(fù)制
  2. 遷移順序: 定義外鍵時(shí),被引用的表(父表)必須在引用表(子表)之前創(chuàng)建。如果 rso 表的遷移文件在 dso 表之后執(zhí)行,那么在創(chuàng)建 dso 表時(shí)就會(huì)因?yàn)檎也坏?rso 表而報(bào)錯(cuò)。通常,Laravel 會(huì)根據(jù)遷移文件名的時(shí)間戳自動(dòng)排序,確保依賴關(guān)系正確。

  3. Schema::enableForeignKeyConstraints() 與 Schema::disableForeignKeyConstraints(): 這兩個(gè)方法用于臨時(shí)啟用或禁用外鍵約束。在進(jìn)行大量數(shù)據(jù)導(dǎo)入或刪除操作時(shí),禁用外鍵可以提高性能。在 up() 方法中,通常不需要手動(dòng)調(diào)用 Schema::enableForeignKeyConstraints(),因?yàn)長(zhǎng)aravel默認(rèn)在遷移運(yùn)行時(shí)會(huì)處理好外鍵約束的啟用。只有在 down() 方法中,如果需要?jiǎng)h除帶有外鍵的表,可能需要先禁用外鍵,再刪除表,最后重新啟用。

  4. php artisan migrate:fresh: 這個(gè)命令會(huì)刪除所有表,然后重新運(yùn)行所有遷移。這也是最容易暴露出上述重復(fù)列名錯(cuò)誤的環(huán)境,因?yàn)樗鼤?huì)從頭開(kāi)始構(gòu)建數(shù)據(jù)庫(kù)結(jié)構(gòu)。

總結(jié)

在Laravel中定義外鍵時(shí),使用 foreignId() 輔助函數(shù)結(jié)合 constrained() 方法是最佳實(shí)踐。它不僅代碼簡(jiǎn)潔,而且能自動(dòng)處理列的創(chuàng)建和外鍵的定義,有效避免了因重復(fù)創(chuàng)建列而導(dǎo)致的“Duplicate column name”錯(cuò)誤。遵循這些最佳實(shí)踐,可以確保數(shù)據(jù)庫(kù)遷移的順暢執(zhí)行和數(shù)據(jù)庫(kù)結(jié)構(gòu)的清晰維護(hù)。

以上就是Laravel 遷移中外鍵定義與“重復(fù)列名”錯(cuò)誤的解決策略的詳細(xì)內(nèi)容,更多請(qǐng)關(guān)注php中文網(wǎng)其它相關(guān)文章!

最佳 Windows 性能的頂級(jí)免費(fèi)優(yōu)化軟件
最佳 Windows 性能的頂級(jí)免費(fèi)優(yōu)化軟件

每個(gè)人都需要一臺(tái)速度更快、更穩(wěn)定的 PC。隨著時(shí)間的推移,垃圾文件、舊注冊(cè)表數(shù)據(jù)和不必要的后臺(tái)進(jìn)程會(huì)占用資源并降低性能。幸運(yùn)的是,許多工具可以讓 Windows 保持平穩(wěn)運(yùn)行。

下載
來(lái)源:php中文網(wǎng)
本文內(nèi)容由網(wǎng)友自發(fā)貢獻(xiàn),版權(quán)歸原作者所有,本站不承擔(dān)相應(yīng)法律責(zé)任。如您發(fā)現(xiàn)有涉嫌抄襲侵權(quán)的內(nèi)容,請(qǐng)聯(lián)系admin@php.cn
最新問(wèn)題
開(kāi)源免費(fèi)商場(chǎng)系統(tǒng)廣告
最新下載
更多>
網(wǎng)站特效
網(wǎng)站源碼
網(wǎng)站素材
前端模板
關(guān)于我們 免責(zé)申明 意見(jiàn)反饋 講師合作 廣告合作 最新更新
php中文網(wǎng):公益在線php培訓(xùn),幫助PHP學(xué)習(xí)者快速成長(zhǎng)!
關(guān)注服務(wù)號(hào) 技術(shù)交流群
PHP中文網(wǎng)訂閱號(hào)
每天精選資源文章推送
PHP中文網(wǎng)APP
隨時(shí)隨地碎片化學(xué)習(xí)
PHP中文網(wǎng)抖音號(hào)
發(fā)現(xiàn)有趣的

Copyright 2014-2025 http://m.miracleart.cn/ All Rights Reserved | php.cn | 湘ICP備2023035733號(hào)