昨天下班前弄了一下 wildcard 模糊查询发现没有效果,今天早上来马上就解决了,记录下。
说明:查询的字段必须有keyword类型
需求背景
先说下我的背景,我需要对一个文件表(es存了一份),查询某个文件的下级。
实现方法是根据filePath和level一起查询,如果是mysql可以用 file_path like '父文件路径%' 这种方式实现。
但是我需要用 ES实现,查了一下有 wildcard 能实现同样的功能。
先看下我的索引数据
我的问题,很简单,如 搜索 /测试项目12 开头的所有数据
实现方法
1、先创建索引
这里贴出完整的内容
{
"settings": {
"index": {
"number_of_shards": "1",
"number_of_replicas": "1"
},
"index.max_ngram_diff": 5,
"analysis": {
"analyzer": {
"ngram_analyzer": {
"tokenizer": "ngram_tokenizer"
}
},
"tokenizer": {
"ngram_tokenizer": {
"type": "ngram",
"min_gram": 1,
"max_gram": 5,
"token_chars": [
"letter",
"digit"
]
}
}
}
},
"mappings": {
"properties": {
"repoPrefix": {
"type": "keyword"
},
"fileName": {
"type": "text",
"analyzer": "ngram_analyzer"
},
"level": {
"type": "long"
},
"leafFlag": {
"type": "boolean"
},
"filePath": {
"type": "text",
"fields": {
"keyword": {
"type": "keyword"
},
"text": {
"type": "text",
"analyzer": "ngram_analyzer"
}
}
},
"creatorName": {
"type": "text"
},
"description": {
"type": "text"
},
"updateTime": {
"type": "date"
},
"revision": {
"type": "long"
},
"createTime": {
"type": "date"
},
"fileSize": {
"type": "long"
},
"updaterName": {
"type": "text"
},
"_class": {
"type": "keyword"
},
"id": {
"type": "long"
},
"projectId": {
"type": "long"
},
"fileType": {
"type": "long"
}
}
}
}
主要看 filePath那段
2、wildcard模糊查询语句
指定使用 keyword 类型
GET http://10.1.5.190:9200/common_file/_search
{
"query": {
"wildcard": {
"filePath.keyword": "/测试项目12*"
}
}
}
运行结果如下
成功查出来了,不容易啊!!!
3. 使用分词查询
因为我还需要用这个字段分词查询,比如查询任意一段内容,比如 查询 12/历史库/v1 ,一般的分词器是满足不了,所以用到了ngram_tokenizer分词器
使用 text 类型
GET http://10.1.5.190:9200/common_file/_search
{
"query": {
"match": {
"filePath.text": "12/历史库/v1"
}
}
}
运行结果如下
三、完整的代码实现
这里贴出我的需求,根据文件名称/路径搜索,且能满足搜索指定文件夹下面的文件(根据仓库路径,文件路径右匹配和level一起查询)
//查询对象
BoolQueryBuilder queryBuilder = new BoolQueryBuilder();
// level查询
if (CommonUtil.isNotEmpty(fileSearchDTO.getLevel()))
{
queryBuilder.must(QueryBuilders.matchQuery("level", fileSearchDTO.getLevel()+1));
}
// repoPrefix查询
if (CommonUtil.isNotEmpty(fileSearchDTO.getRepoPrefix()))
{
queryBuilder.must(QueryBuilders.matchQuery("repoPrefix", fileSearchDTO.getRepoPrefix()));
}
// filePath查询
if (CommonUtil.isNotEmpty(fileSearchDTO.getFilePath()))
{
queryBuilder.must(QueryBuilders.wildcardQuery("filePath.keyword", fileSearchDTO.getFilePath()+"*"));
}
// 关键字查询
// 搜文件路径
if ("filePath".equals(fileSearchDTO.getSearchType()))
{
queryBuilder.must(QueryBuilders.matchQuery("filePath.text", fileSearchDTO.getSearchKeywords()));
}
// 搜文件名称
else
{
queryBuilder.must(QueryBuilders.matchQuery("fileName", fileSearchDTO.getSearchKeywords()));
}
PageRequest pageRequest = PageRequest.of(fileSearchDTO.getPage() - 1, fileSearchDTO.getLimit());
org.springframework.data.domain.Page<EsCommonFile> esCommonFilePage = esCommonFileRepository.search(queryBuilder, pageRequest);
您可以选择一种方式赞助本站
支付宝扫一扫赞助
微信钱包扫描赞助
赏