elasticsearch 实现查询忽略大小写

1 在项目中,产品已经上线一段时间,出现新的需求,需要解决查询的时候,忽略大小写的问题。本人用于测试的索引结构如下
PUT test_v1.000
{
  "settings": {
    "number_of_replicas": 1,
    "number_of_shards": 5
  },
  "mappings": {
    "product": {
      "properties": {
        "name":{
          "type": "keyword"
        },
        "sex":{
          "type": "keyword"
        },
        "content":{
          "type": "text",
          "fields": {
            "keyword":{
              "ignore_above": 32766,
              "type": "keyword"
            }
          }
        }
      }
    }
  },
  "aliases": {
    "test": {}
  }
}

2 在test索引里面新增几条数据,用于查询使用
​PUT test/product/_bulk
{"index":{"_id":5}}
{ "name": "New York5","sex":"男","content":"ES5.X版本以后,keyword支持的最大长度为32766个UTF-8字节数(至于多少个字符数需要根据业务场景定,建议参考最新版本的官方文档说明),text对字符长度没有限制。New York5"}
{"index":{"_id":6}}
{ "name": "new York6","sex":"男","content":"ES5.X版本以后,keyword支持的最大长度为32766个UTF-8字节数(至于多少个字符数需要根据业务场景定,建议参考最新版本的官方文档说明),text对字符长度没有限制。new York6"}
{"index":{"_id":7}}
{ "name": "New york7","sex":"男","content":"ES5.X版本以后,keyword支持的最大长度为32766个UTF-8字节数(至于多少个字符数需要根据业务场景定,建议参考最新版本的官方文档说明),text对字符长度没有限制。New york7"}
{"index":{"_id":8}}
{ "name": "NEW YORK8","sex":"男","content":"ES5.X版本以后,keyword支持的最大长度为32766个UTF-8字节数(至于多少个字符数需要根据业务场景定,建议参考最新版本的官方文档说明),text对字符长度没有限制。NEW YORK8"}

3 想查询name以及content.keyword里面的数据,但是需要忽略大小写的问题,测试如下,由于此时elasticsearch的mapping未做任何处理,是不会自动忽略大小写的,所以此时下面的查询语句,应该只能查询两条数据,id为2和6的数据。截图如下
POST test/_search
{
  "query": {
    "bool": {
      "must": [
        {
          "query_string": {
            "fields": ["content.keyword","name"],
            "query": "*new*"
          }
        }
      ]
    }
  }
}

4 对于elasticsearch查询忽略大小写的问题,官方给出了一个解决方案,使用normalizer来解决,normalizer是keyword的一个属性,可以对keyword生成的单一term,query_string做进一步的处理,比如lowercase,小写转换,使用方式和自定义分词器有相似之处,需要自定义,具体步骤如下。
5 此时由于elasticsearch的索引已经建好,由于es的规则,只能新增字段,不能删除或者修改已经存在的字段,可以动态更新原有索引的setting,动态更新setting,需要先关闭索引,执行玩更新操作以后,再开启索引,步骤如下
​POST test/_close

PUT test/_settings
{
  "index": {
    "analysis": {
      "normalizer": {
        "lowercase_normalizer": {
          "type": "custom",
          "char_filter": [],
          "filter": [
            "lowercase"
          ]
        }
      }
    }
  }
}

POST test/_open

6 查看原有test的索引setting,如下图,发现设置已经生效,这个时候,动态添加新的字段(keyword类型),既可使用lowercase_normalizer,实现忽略大小写的操作。
动态添加一个字段 author,如下,然后查看mapping,发现已经生效,并且author比其他keyword字段多一个属性normalizer
​PUT test/product/_mapping
{
  "properties": {
    "author": {
      "type": "keyword",
      "normalizer": "lowercase_normalizer"
    }
  }
}

7 新增一条数据,并且测试,看查询author字段的时候,忽略大小写的操作是否已经实现,具体插入数据不再展示,自行插入数据,查询语句以及结果如下。发现查询da也能将包含DA的数据查询出来,说明已经实现了新增字段忽略大小写的操作。但是对老数据老字段,这种方式并不能解决问题,所以只能新增索引,将老数据同步过去,让我们继续往下操作
8 新建一个新索引,设置normalizer属性,命令如下
PUT xsj_test_v1.000
{
  "settings": {
    "number_of_replicas": 1,
    "number_of_shards": 5,
    "analysis": {
      "normalizer": {
        "lowercase_normalizer": {
          "type": "custom",
          "char_filter": [],
          "filter": [
            "lowercase"
          ]
        }
      }
    }
  },
  "mappings": {
    "product": {
      "properties": {
        "name":{
          "type": "keyword",
           "normalizer": "lowercase_normalizer"
        },
        "sex":{
          "type": "keyword",
           "normalizer": "lowercase_normalizer"
        },
         "author":{
          "type": "keyword",
           "normalizer": "lowercase_normalizer"
        },
        "content":{
          "type": "text",
          "fields": {
            "keyword":{
              "ignore_above": 32766,
              "type": "keyword",
               "normalizer": "lowercase_normalizer"
            }
          }
        }
      }
    }
  },
  "aliases": {
    "xsj_test": {}
  }
}

9 新建完xsj_test索引以后,同步test的数据过来,命令如下
​POST /_reindex
{
  "source": {
    "index": "test"
  },
  "dest": {
    "index": "xsj_test"
  }
}

10 测试name以及content.keyword字段,看是否忽略大小写操作已经生效。查询命令以及结果如下,发现query_string查询的时候,忽略大小写的操作已经生效,并且老数据也可以忽略大小写查询。
​POST xsj_test/product/_search
{
  "query": {
    "bool": {
      "must": [
        {
          "query_string": {
            "fields": ["name","author","content.keyword"],
            "query": "*new*"
          }
        }
      ]
    }
  }
}

  • 10
    点赞
  • 32
    收藏
    觉得还不错? 一键收藏
  • 10
    评论
在使用Spring集成Elasticsearch7时,可以通过设置索引的映射和查询时使用的分析器来实现忽略大小写的功能。 首先,在创建索引时,可以使用字段的映射设置来指定对应字段的分析器。通过设置分析器为"keyword_lowercase",可以将字段设置为忽略大小写。例如,以下代码片段演示了如何创建一个忽略大小写的索引: ```java CreateIndexRequest createIndexRequest = new CreateIndexRequest("my_index"); createIndexRequest.settings(Settings.builder() .put("index.analysis.analyzer.default.type", "custom") .put("index.analysis.analyzer.default.tokenizer", "keyword") .put("index.analysis.analyzer.default.filter", "lowercase") .build()); Mapping mapping = new Mapping.Builder() .field(new StringField("my_field") .analyzer("keyword_lowercase")) .build(); createIndexRequest.mapping(mapping); CreateIndexResponse response = restHighLevelClient.indices().create(createIndexRequest, RequestOptions.DEFAULT); ``` 在查询时,我们可以使用Spring Data Elasticsearch来构造查询请求。通过使用`QueryBuilders`类提供的`matchQuery`方法,并指定字段为忽略大小写的分析器,可以实现忽略大小写查询。例如,以下代码片段演示了如何使用忽略大小写的方式进行查询: ```java QueryBuilder queryBuilder = QueryBuilders.matchQuery("my_field", "value") .analyzer("keyword_lowercase"); SearchSourceBuilder searchSourceBuilder = new SearchSourceBuilder(); searchSourceBuilder.query(queryBuilder); SearchRequest searchRequest = new SearchRequest("my_index"); searchRequest.source(searchSourceBuilder); SearchResponse response = restHighLevelClient.search(searchRequest, RequestOptions.DEFAULT); ``` 通过以上的设置和方法,我们可以在Spring集成Elasticsearch7中实现忽略大小写的功能。这样,无论字段的大小写如何,都可以正确地进行索引和查询操作。
评论 10
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值