本文目录导读:

在Laravel中为数据库添加索引,有几种方法,我来详细说明:
使用数据库迁移(推荐)
在迁移文件中创建索引
<?php
// database/migrations/2024_01_01_000000_add_indexes_to_users_table.php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
public function up()
{
Schema::table('users', function (Blueprint $table) {
// 普通索引
$table->index('email');
// 复合索引(多个字段)
$table->index(['country', 'city']);
// 唯一索引
$table->unique('phone');
// 指定索引名称
$table->index('status', 'idx_user_status');
});
}
public function down()
{
Schema::table('users', function (Blueprint $table) {
// 删除索引
$table->dropIndex(['email']);
$table->dropIndex(['country', 'city']);
$table->dropUnique(['phone']);
$table->dropIndex('idx_user_status');
});
}
};
在创建表时添加索引
Schema::create('products', function (Blueprint $table) {
$table->id();
$table->string('name');
$table->string('sku')->unique();
$table->decimal('price', 10, 2);
$table->unsignedBigInteger('category_id');
// 在创建表时添加索引
$table->index('name');
$table->index(['category_id', 'price']);
$table->foreign('category_id')->references('id')->on('categories');
});
使用索引类型
Laravel支持多种索引类型:
Schema::table('posts', function (Blueprint $table) {
// 全文索引(MySQL/PostgreSQL)
$table->fullText('content');
// 空间索引(MySQL)
$table->spatialIndex('coordinates');
// 复合唯一索引
$table->unique(['user_id', 'post_id']);
// 索引长度限制(SQLite)
$table->index(DB::raw('LEFT(title, 100)'));
});
通过Artisan命令生成迁移
# 生成新的迁移文件 php artisan make:migration add_indexes_to_products_table --table=products # 运行迁移 php artisan migrate # 回滚最后一个迁移 php artisan migrate:rollback --step=1
常见索引建议场景
常用查询字段
// 用户表经常按邮箱、手机号查询
Schema::table('users', function (Blueprint $table) {
$table->index('email');
$table->index('phone');
});
外键字段
Schema::table('orders', function (Blueprint $table) {
$table->foreignId('user_id')->index();
$table->foreignId('product_id')->index();
});
组合查询条件
Schema::table('products', function (Blueprint $table) {
// 当经常按 category_id 和 status 查询时
$table->index(['category_id', 'status']);
});
检查现有索引
// 在代码中检查表是否已有索引
if (!Schema::hasIndex('users', 'email')) {
Schema::table('users', function (Blueprint $table) {
$table->index('email')->name('idx_user_email');
});
}
性能优化建议
// 为查询频率高的字段添加索引
$table->index('order_number'); // 订单号查询频繁
// 为排序字段添加索引
$table->index('created_at'); // 经常按时间排序
// 避免过度索引,只对WHERE、JOIN、ORDER BY中的字段添加
完整的迁移示例
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
return new class extends Migration
{
public function up()
{
Schema::table('products', function (Blueprint $table) {
// 添加多个索引
$table->index('category_id');
$table->index('brand_id');
$table->unique('barcode');
$table->index(['store_id', 'status']);
$table->index('updated_at');
});
}
public function down()
{
Schema::table('products', function (Blueprint $table) {
$table->dropIndex(['category_id']);
$table->dropIndex(['brand_id']);
$table->dropUnique(['barcode']);
$table->dropIndex(['store_id', 'status']);
$table->dropIndex(['updated_at']);
});
}
};
注意事项
- 不要过度添加索引:每个索引都会增加写入和存储成本
- 命名规范:通常使用
idx_前缀(普通索引)和uq_前缀(唯一索引) - 小表不需要索引:当表行数很少时,全表扫描可能比索引查找更快
- 测试影响:在添加索引前,使用
EXPLAIN命令分析查询
-- 在数据库客户端中测试查询性能 EXPLAIN SELECT * FROM products WHERE category_id = 1 AND status = 'active';
使用迁移管理索引是Laravel的最佳实践,它让索引管理版本化、可重复,并支持在团队中协作。
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播