elasticsearch在tp6中搜中文需三步:用elasticsearch/elasticsearch v8.x官方包、手动定义含ik分词器的mapping、自行同步数据;跳过任一环节将导致中文搜索失败。

Elasticsearch 在 ThinkPHP(尤其是 TP6)里不是配个 host 就能搜中文的,核心卡点永远在三件事:客户端版本兼容、mapping 显式定义、ik 分词器落地。跳过任一环节,搜索返回空或只匹配英文。
TP6 用 elasticsearch/elasticsearch v8.x,别碰 think-elastic
think-elastic 是 TP5 时代产物,依赖 Elasticsearch\Client v5.x;TP6 默认要求 PHP 7.4+ 和 elasticsearch/elasticsearch v8.x——命名空间变了(Elasticsearch\ClientBuilder)、方法签名废了(index() 不再接受 type 参数)、返回结构也重构了。装了 think-elastic 会直接报 Class 'Elasticsearch\Client' not found 或 ArgumentCountError。必须用官方包:composer require elasticsearch/elasticsearch,然后自己封装驱动。
mapping 必须手动建,不能靠 auto_create_index
ES 默认开启动态映射,但生产环境普遍关掉:action.auto_create_index: false。哪怕你调 $client->index(),也不会自动建索引或推断字段类型。更关键的是:TP 模型字段改了,ES 不会感知,旧 mapping 仍生效,导致新增字段搜不到、类型不匹配报错。
- 删旧索引:
$client->indices()->delete(['index' => 'user']) - 用完整
mappings重建:$params['body']['mappings']['properties']必须和当前模型字段严格对齐,比如title要设为"type": "text", "analyzer": "ik_max_word" - 推荐把
mappings抽成 JSON 文件(如app/config/es_mapping_user.json),避免硬编码和手误
中文搜不到?90% 是 ik 没装或没生效
standard 分词器对中文是“切字”(“搜索引擎” → [“搜”, “索”, “引”, “擎”]),根本没法查词。Sphinx 的 charset_table 同理,不加中文范围就等于没开中文支持。
- ES 必须装
ik插件:bin/elasticsearch-plugin install https://github.com/medcl/elasticsearch-analysis-ik/releases/download/v8.12.2/elasticsearch-analysis-ik-8.12.2.zip - 装完重启 ES,用
GET /_cat/plugins?v确认插件已加载 - mapping 中每个中文字段必须显式指定
"analyzer": "ik_max_word"和"search_analyzer": "ik_smart",不能只写type: text
数据同步得自己管,TP 模型不监听变更
ES 不连 MySQL,也不 watch TP 模型事件。你在模型里加了个 status 字段,ES 里还是老 mapping,新字段不会进索引,bulk 导入时还会因类型冲突失败。
- 字段增删后,必须删索引 → 重定义 mapping → 全量 bulk 导入(别用循环
index()) - 日常更新建议走队列:TP 模型
saved事件触发 job,调$client->update()或bulk() - 首次全量导入务必用
bulk(),每批 100 条,index单条吞吐太低,万级数据可能跑几小时
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











