在Laravel 5.4上使用php artisan make:auth迁移错误

[Illuminate\Database\QueryException] SQLSTATE[42000]: Syntax error or access violation: 1071 Specified key was too long; max key length is 767 bytes (SQL: alter tabl e users add unique users_email_unique(email)) [PDOException] SQLSTATE[42000]: Syntax error or access violation: 1071 Specified key was too long; max key length is 767 bytes


当前回答

我得到了这个错误尽管我已经有了(实际上因为我已经有了) 模式:defaultStringLength (191);在AppServiceProvider.php文件中。

原因是我试图在我的一个迁移中设置一个高于191的字符串值:

Schema::create('order_items', function (Blueprint $table) {
    $table->primary(['order_id', 'product_id', 'attributes']);
    $table->unsignedBigInteger('order_id');
    $table->unsignedBigInteger('product_id');
    $table->string('attributes', 1000); // This line right here
    $table->timestamps();
});

删除1000或将其设置为191解决了我的问题。

其他回答

我认为强制stringlength到191是一个非常糟糕的主意。 所以我去调查了解到底发生了什么。

我注意到这个消息错误:

SQLSTATE[42000]:语法错误或访问违规:1071指定的键 太长了;最大密钥长度为767字节

在我更新MySQL版本后开始出现。所以我已经用PHPMyAdmin检查了表,我注意到所有创建的新表都带有utf8mb4_unicode_ci,而不是旧表的utf8_unicode_ci。

在我的doctrine配置文件中,我注意到charset被设置为utf8mb4,但我之前的所有表都是在utf8中创建的,所以我猜这是一些更新魔术,它开始在utf8mb4上工作。

现在最简单的解决方法是更改ORM配置文件中的行字符集。 然后使用utf8mb4_unicode_ci删除表(如果您在dev模式下),或者如果您不能删除它们则修复字符集。

Symfony 4

在config/packages/doctrine.yaml中将字符集:utf8mb4修改为字符集:utf8

现在我的理论迁移又开始起作用了。

对于这个错误,我找到了两个解决方案

选项1:

打开database/migrations文件夹下的user和password_reset表

只需要改变邮件的长度:

$table->string('email',191)->unique();

选项2:

打开app/Providers/AppServiceProvider.php文件,在boot()方法中设置一个默认字符串长度:

use Illuminate\Support\Facades\Schema;

public function boot()
{
    Schema::defaultStringLength(191);
}

Laravel 5.4由数据库版本导致。

根据文档(在索引长度和MySQL / MariaDB部分):

Laravel默认使用utf8mb4字符集,其中包括 支持在数据库中存储“表情包”。如果你正在运行一个 MySQL版本高于5.7.7或MariaDB版本高于5.7.7 对于10.2.2版本,您可能需要手动配置默认值 由迁移生成的字符串长度,以便MySQL创建 它们的索引。方法进行配置 方案::defaultStringLength方法在你的AppServiceProvider。

换句话说,在<ROOT>/app/Providers/AppServiceProvider.php:

// Import Schema
use Illuminate\Support\Facades\Schema;
// ...

class AppServiceProvider extends ServiceProvider
{

public function boot()
{
    // Add the following line
    Schema::defaultStringLength(191);
}

// ...

}

但正如另一个答案的评论所说:

注意这个解决方案。例如,如果您索引电子邮件字段, 存储邮件的最大长度为191个字符。这个更少 比RFC官方声明的要多。

因此,文档还提出了另一种解决方案:

或者,您可以启用innodb_large_prefix选项 数据库。有关的说明,请参阅数据库的文档 如何正确启用此选项。

最干净的解决方案是去你的数据库并更改:

default_storage_engine to InnoDB

你很可能有MyISAM。

Laravel 7。X(也适用于8X):简单的解决方案。

选项1:

php artisan db:wipe 

更新/config/database.php中mysql数组的这些值

'charset' => 'utf8', 'collation' => 'utf8_general_ci',

然后

php artisan migrate

这是完成了!迁移表创建成功。


选项2:

使用php artisan db:手动擦除或删除数据库中的所有表。

更新AppServiceProvider.php[位于app/Providers/AppServiceProvider.php]

use Illuminate\Support\Facades\Schema;
/**
 * Bootstrap any application services.
 *
 * @return void
 */
public function boot()
{
    Schema::defaultStringLength(191); 
}

然后

php artisan migrate

这是完成了!

陷阱:我想提一下@shock_gone_wild的评论

注意这个解决方案(选项2)。例如,如果您索引电子邮件字段, 存储邮件的最大长度为191个字符。这个更少 比RFC官方声明的要多。


可选地,我尝试了这些可能的方法(如下面),但不工作。

PHP artisan config:cache PHP artisan migrate:fresh

PHP工匠迁移:重置