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

Mongo Atlas Search如何实现大小写不敏感的部分匹配查询?

解决Mongo Atlas Search同时支持大小写不敏感与部分匹配的方案

你的需求完全可以实现,之前的方向没有错误,只需调整索引配置和查询逻辑即可达成目标。

问题根源

当前使用的lucene.keyword分析器会将整个字段作为单个token,因此wildcard查询能实现部分匹配,但它不会做大小写转换,导致查询大小写敏感;而lucene.standard分析器虽支持大小写不敏感,但会将文本拆分为多个token,wildcard查询只能匹配单个token的部分内容,无法实现跨token或整个字段的任意位置部分匹配。

正确实现方案

1. 调整索引配置:使用自定义分析器

创建同时支持大小写转换和保留整字段为单个token的自定义分析器,兼顾大小写不敏感与部分匹配的需求。替换原search_organizations_name索引的配置:

{
  "name": {
    "type": "string",
    "analyzer": {
      "type": "custom",
      "tokenizer": "keyword",
      "filter": ["lowercase"]
    },
    "searchAnalyzer": {
      "type": "custom",
      "tokenizer": "keyword",
      "filter": ["lowercase"]
    }
  }
}

该分析器通过keyword分词器保留整字段为单个token,再通过lowercase过滤器统一转换为小写,索引时会将Organisation存储为organisation,查询时也会把输入的ORG转为org,实现大小写不敏感。

2. 调整查询代码

保留wildcard逻辑,新增allowAnalyzedField参数(允许在经过分析的字段上使用wildcard查询),同时可提前将查询文本转小写(增强兼容性):

func (r *Repo) Search(ctx context.Context, query string) ([]Organization, error) {
    querySplit := strings.Split(strings.ToLower(query), " ")

    // 为每个查询词添加通配符
    for i := range querySplit {
        querySplit[i] = fmt.Sprintf("*%s*", querySplit[i]) 
    }

    // 定义聚合搜索阶段
    searchStage := bson.D{
        {"$search", bson.D{
            {"index", "search_organizations_name"},
            {"wildcard", bson.D{
                {"path", "name"},
                {"query", querySplit},
                {"allowAnalyzedField", true} // 必须开启,支持在分析字段上执行wildcard查询
            }},
        }},
    }

    // 执行聚合查询
    cursor, err := r.organizationsCollection().Aggregate(ctx, mongo.Pipeline{searchStage})
    if err != nil {
        return nil, err // 按实际业务逻辑处理错误
    }

    var orgs []Organization
    if err = cursor.All(ctx, &orgs); err != nil {
        return nil, errors.Wrap(err, "parsing organizations to return")
    }

    return orgs, nil
}

效果验证

  • 输入org可匹配Organisation、ORGANIZATION、my-org等包含org(大小写无关)的内容
  • 输入Org或ORG会自动转为小写,匹配相同结果
  • 多词查询如big org可匹配同时包含big和org的组织名称

备选方案:autocomplete算子(适合前缀/中缀补全场景)

如果你的部分匹配需求以前缀/中缀补全为主,可使用autocomplete算子,性能比wildcard更优:
索引配置:

{
  "name": {
    "type": "autocomplete",
    "analyzer": "lucene.simple",
    "tokenizer": "keyword"
  }
}

查询代码:

searchStage := bson.D{
    {"$search", bson.D{
        {"index", "search_organizations_name"},
        {"autocomplete", bson.D{
            {"path", "name"},
            {"query", strings.ToLower(query)},
            {"fuzzy", bson.D{{"maxEdits", 1}}} // 可选,支持模糊匹配
        }},
    }},
}

内容的提问来源于stack exchange,提问作者Ido Van Orell

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.21 16:46:07