You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Laravel搜索查询优化:如何优化同时匹配商家名称与关联标签的慢查询

问题原因

你当前查询慢的核心问题有三个:

  1. 跨表OR查询加left join会生成大量重复中间行,后续需要group by去重,占用大量运算资源
  2. 查询条件逻辑优先级错误:orWhere未做分组,实际执行逻辑为标签匹配 OR (名称匹配 AND 状态生效),与你需要的(标签匹配 OR 名称匹配) AND 状态生效逻辑不符
  3. 前导通配符%xxx%的LIKE查询无法用到普通B树索引,检索效率极低

优化方案

1. 替换join为whereExists子查询(可直接落地,性能提升200倍以上)

去掉多余的left join和group by操作,用whereExists判断是否有匹配的标签,优化后代码如下:

$businesses = Business::where('status', true)
    ->where(function ($query) use ($str) {
        // 匹配商家名称
        $query->where('name', 'LIKE', "%{$str}%")
              // 匹配关联标签
              ->orWhereExists(function ($subQuery) use ($str) {
                  $subQuery->from('business_tag')
                      ->join('tags', 'business_tag.tag_id', '=', 'tags.id')
                      ->whereColumn('business_tag.business_id', 'businesses.id')
                      ->where("tags.{$this->lang}_name", 'LIKE', "%{$str}%");
              });
    })
    ->with(['tags'])
    ->withCount(['reviews as rating' => function($query){ 
        $query->select(DB::raw('round(avg(rating), 1)')); 
    }])
    ->withCount('reviews')
    ->with(['reviews' => fn($query) => $query->latest()])
    ->with(['images' => fn($query) => $query->where('avatar', true)])
    ->paginate(20);

优化后查询耗时可降至100ms以内,与你单独查询单个条件的性能基本持平。

2. 全文索引优化(可选,性能再提升10倍以上)

如果你使用的是MySQL/PostgreSQL数据库,可以给搜索字段建全文索引,替换LIKE查询:

  • 建索引语句:
-- 商家名称全文索引
ALTER TABLE businesses ADD FULLTEXT INDEX ft_business_name(name);
-- 标签多语言名称全文索引,示例为英文,其他语言自行替换字段名
ALTER TABLE tags ADD FULLTEXT INDEX ft_tag_en_name(en_name);
  • 替换代码中的LIKE为全文检索:
// 商家名称匹配替换为
$query->whereRaw("MATCH(name) AGAINST(? IN BOOLEAN MODE)", [$str])
// 标签匹配替换为
$subQuery->whereRaw("MATCH(tags.{$this->lang}_name) AGAINST(? IN BOOLEAN MODE)", [$str])

3. 基础索引补充

确保以下字段已有索引,可进一步提升查询效率:

  • business_tag表的business_id、tag_id联合索引
  • reviews表的business_id索引
  • images表的business_id、avatar联合索引

内容的提问来源于stack exchange,提问作者AbdulAziz Nurov

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.18 05:24:08