关于建立索引的 767 bytes 长度限制
生产环境执行
php artisan migrate
Laravel 抛出错误:
Index column size too large. The maximum column size is 767 bytes.
然而在本地开发的时候是正常的。
搜索了一番。 原因定位在字段的长度设置。
- Laravel 建表使用的是 utf8mb4 字符集。 这个一个4字节字符集
- 如果说最大限制是 767 bytes。 那么一个 varchar 字段:767/4=191.75。
- 所以我字段设置使用默认的(255),远远超出了限制。
为什么在本地开发时又正常呢?
- 本地开发使用的 MySQL5.7 而线上环境是 MySQL5.6。
- MySQL5.7 有默认参数
innodb_default_row_format=dynamic和innodb_large_prefix=on。这样的参数下是允许建立长字节索引的。 - MySQL5.6 的参数
innodb_large_prefix默认为off,并且没有一个默认参数可以在新建表时选择自己想要的 row_format,只能在create table或alert table时 加上ROW_FORMAT=DYNAMIC。
目前我试过可行的三种方法
- 将建立索引的
varchar字段长度调低,使所有字段字节之和不超过 767 bytes。 - 建表时将 MySQL 的
charset改为 utf8 ,collation改为 utf8_general_ci。可在 config/database.php 中设置默认值。 - 将 MySQL 升级到 5.7 版本
未尝试的方法
- 设置 MySQL 的参数:
set GLOBAL innodb_large_prefix=ON; - 建表时添加
ROW_FORMAT=DYNAMIC
参考
MySQL 5.6 Reference Manual : DYNAMIC and COMPRESSED Row Formats
MySQL 5.7 Reference Manual : Limits on InnoDB Tables
本作品采用《CC 协议》,转载必须注明作者和本文链接
本帖由系统于 7年前 自动加精
关于 LearnKu
使用
WordPress搭建博客遇到类似问题,直接升级数据库版本解决MySQL数据库的编码应为utf8mb4,且要求MySQL版本在5.7.7以上或MariaDB版本在10.2.2以上。
laravel文档有说过这个问题
https://learnku.com/docs/laravel/5.6/migrations#cr...
@leililei
文档并没强制要求。 MySQL 5.7以下也可以使用。只是需要注意字段长度。
而且文档也没细说索引长度限制是怎么回事
@ealiwood 这是文档给的解决办法:
@轻色年华 不推荐这种解决方法,如果不是 MySQL5.7,就算是 utf8mb4 的情况下创建联合索引照样会超长。 最好就是直接升级到 MySQL 5.7
用前缀索引