##当需求查询es数据库中大量数据时,用_search就不符合应用场景了,建议使用helpers.scan,helpers.scan返回的数据对象时迭代器,很大节省内存空间,而且查询速度要远远大于search;search在利用from、size参数控制返回数据的条数,使用 from and size 的深度分页,size=10&from=10000 是非常低效的,因为 100,000 排序的结果必须从每个分片上取出并重新排序最后返回 10 条。这个过程需要对每个请求页重复,scroll进行数据分页,也可以返回大数据,但是search返回的数据是以list的形式,如果一次需要返回的数据量比较大的话,则会十分耗费内存,而且数据传输速度也会比较慢
from elasticsearch6.helpers import bulk, scan
search_query = {
"query": {
"match_phrase": {
"domain": {
"query": "xxxxxxxxxxxx.onion"
}
}
}
}
#scroll='5m'查询一次数据在ES中缓存5分钟再销毁
res = scan(client=es, query=search_query, scroll='5m', index='page', doc_type='_doc', timeout='1m')
cnt = 0
for record in res:
print(cnt, record["_source"]["url"])
cnt += 1
还有一种需求场景,想指定某些字段譬如时间倒序查询,并且查询的数据量还比较大那么可以用如下
search_query = {
"query": {
"match": {
"domain": "xxxxxxxxxxxx.onion"
}
},
"sort": {
"crawl_time": {
"order": "desc"
}
},
"size": 20000
}
res = es.search(index='page', doc_type='_doc',scroll='5m',body=search_query, timeout='10m')
cnt = 0
res_lst = res["hits"]["hits"]
for record in res_lst:
print(cnt,record["_source"]["url"])
cnt += 1