tp6.0中实现unicode模糊查询的关键在于mysql字段级utf8mb4_0900_ai_ci排序规则配置,而非框架层修改;该规则支持大小写与重音不敏感匹配,需结合连接字符集、字段显式声明及搜索器轻量预处理,避免手动转码或全文检索。

TP6.0 中实现支持模糊查询的 Unicode 排序规则配置,核心不在框架本身,而在 MySQL 层级的字符集与排序规则(collation)设计。国际化场景下,既要保证多语言(如中文、日文、阿拉伯语、西欧字符)正确显示和存储,又要让 LIKE 模糊查询行为符合用户预期——比如搜索“iPhone”能命中“iphone”“IPHONE”,搜索“café”能匹配“cafe”或带重音的变体。这需要数据库字段使用合适的 Unicode collation,而非简单依赖 PHP 层转义或替换。
选择适合模糊查询的 MySQL 8 排序规则
MySQL 8 推荐使用 utf8mb4_0900_ai_ci 作为国际化字段的默认排序规则:
- ai 表示 accent-insensitive(忽略重音),例如 café 和 cafe 被视为等价
- ci 表示 case-insensitive(大小写不敏感),适用于用户名、产品名、标题等自然语言字段
- 相比旧版
utf8mb4_unicode_ci,0900_ai_ci更符合 Unicode 9.0+ 标准,对东南亚、中东等语言的排序和比较更准确 - LIKE 查询时,
%苹果%可同时匹配“红苹果”“青蘋果”(繁体兼容)和“APPLE”(若开启 ci)
字段级 collation 配置(非全局修改)
不建议全库统一设为 utf8mb4_bin 或强行修改已有表 collation,易引发索引重建、锁表、唯一约束冲突等问题。应按字段语义差异化设置:
- 用户昵称、商品标题、文章摘要等搜索主字段:建表时显式指定
COLLATE utf8mb4_0900_ai_ci - 登录账号、API Token、UUID 等需精确匹配字段:保留
COLLATE utf8mb4_bin - 示例 SQL:
title VARCHAR(255) COLLATE utf8mb4_0900_ai_ci NOT NULL - TP6 模型中无需额外声明,只要数据库字段已设好 collation,原生
where('title', 'like', "%{$keyword}%")即自动生效
TP6 搜索器中适配 Unicode 模糊逻辑
在模型中定义搜索器方法时,可结合 collation 特性做轻量增强,避免过度依赖 PHP 字符串处理:
- 对关键词做基础清洗:去除首尾空格、合并连续空格(不影响
_0900_ai_ci的匹配能力) - 不手动转义 Unicode 字符(如 \uXXXX),因为 MySQL 的 LIKE 在 utf8mb4 + ai_ci 下天然支持 UTF-8 原始字符匹配
- 若需支持“连字符/空格互换”(如搜 “hello world” 匹配 “hello-world”),可在搜索器中预处理关键词:
str_replace([' ', '-'], '_', $keyword),再用like查"%{$pattern}%" - 示例搜索器:
public function searchTitleAttr($query, $value) { $pattern = str_replace([' ', '-'], '_', trim($value)); $query->where('title', 'like', "%{$pattern}%"); }
避免常见陷阱
Unicode 模糊查询失效往往源于底层配置失配,而非 TP6 写法问题:
- 确认连接层也使用 utf8mb4:
mysql.default_charset = utf8mb4(PHP 配置)、charset: utf8mb4(TP6 database.php) - 检查字段实际 collation:执行
SHOW FULL COLUMNS FROM your_table LIKE 'title';,确保 Collation 列显示为utf8mb4_0900_ai_ci - 不要在 TP6 查询中对关键词做
mb_strtoupper()或iconv()转换——MySQL 的 ai_ci 已内置语言感知,手动转换反而破坏匹配 - 全文检索(FULLTEXT)不推荐用于多语言模糊查,因分词器对中文/日文支持弱;优先用 LIKE + 合理索引 + 正确 collation











