如何修改Elasticsearch查询,筛选含agent1及其他代理且多城市的用户?
解决方案
原查询的问题在于提前用match过滤掉了非agent1的文档,导致无法统计该user_id下的其他代理信息和完整城市数量。下面是修改后的查询,能实现你的需求:
query = { "size": 0, # 不需要返回具体文档,只需要聚合结果 "aggs": { "user_ids": { "terms": {"field": "user_id", "size": 60000}, "aggs": { # 统计该user_id下的代理种类数量 "agent_count": {"cardinality": {"field": "agent_name"}}, # 检查该user_id下是否存在agent1 "has_agent1": { "filter": {"match": {"agent_name": "agent1"}}, "aggs": {"doc_count": {"value_count": {"field": "agent_name"}}} }, # 统计该user_id下所有代理的城市去重数量 "total_city_count": {"cardinality": {"field": "city"}}, # 筛选满足所有条件的user_id "qualified_users": { "bucket_selector": { "buckets_path": { "agentNum": "agent_count", "hasAgent1": "has_agent1.doc_count", "cityNum": "total_city_count" }, "script": "params.hasAgent1 > 0 && params.agentNum >= 2 && params.cityNum > 2" } } } } } }
关键修改说明:
- 移除了原查询的
query部分:不再提前过滤文档,保留所有记录才能统计每个user_id的完整代理信息 - 新增三个子聚合:
agent_count:计算该user_id下有多少种不同的代理,确保数量≥2(说明存在agent1之外的其他代理)has_agent1:筛选出该user_id下属于agent1的记录,通过统计文档数确认agent1存在total_city_count:统计该user_id下所有代理覆盖的城市总数
bucket_selector聚合:用脚本同时校验三个条件,只保留符合要求的user_id聚合结果
内容的提问来源于stack exchange,提问作者alsa
相关产品推荐
相关产品推荐

