ElasticSearch:使用 NEST 从动态条件列表中创建应该查询
ElasticSearch: Create should queries from a dynamic list of criterias with NEST
使用 ElasticSearch 7.6 我想找到区域列表内的所有点。
还有一些其他筛选条件已添加到 QueryContainerDescriptors 列表并应用于最终搜索。
var queries = new List<Func<QueryContainerDescriptor<MySearchableObject>, QueryContainer>>();
此示例适用于一个区域,其中 Coordinates 是一个字典
foreach (var area in areas)
{
var pointsList = area.Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude)).ToList();
queries.Add(sqs => sqs
.GeoPolygon(r => r
.Field(f => f.Position)
.ValidationMethod(GeoValidationMethod.Strict)
.Points(pointsList)));
}
还有这个:
queries.Add(sqs => sqs.Bool(b=>b.Should(bs => GeoPolygonShouldQuery(bs, area))));
private static QueryContainer GeoPolygonShouldQuery(QueryContainerDescriptor<MySearchableObject> bs, FilterArea area)
{
return bs
.GeoPolygon(r => r
.Field(f => f.Position)
.ValidationMethod(GeoValidationMethod.Strict)
.Points(area.Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude))));
}
我如何为列表中的每个区域附加一个 should 子句?
与此类似:
queries.Add(sqs => sqs.Bool(b => b.Should(
bs => bs.GeoPolygon(r => r.Field(f => f.Position)
.Points(areas.ElementAt(0).Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude)).ToList())),
bs => bs.GeoPolygon(r => r.Field(f => f.Position)
.Points(areas.ElementAt(1).Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude)).ToList()))
)));
经过更多的尝试和错误。这似乎解决了问题:
var areas = FindFilterAreas(query.Areas);
queries.Add(sqs => sqs.Bool(b => b.Should(MyQueries(b, areas))));
private static List<Func<QueryContainerDescriptor<SearchableSituation>, QueryContainer>> MyQueries(BoolQueryDescriptor<SearchableSituation> qd, IEnumerable<FilterArea> areas)
{
List<Func<QueryContainerDescriptor<SearchableSituation>, QueryContainer>> queries = new List<Func<QueryContainerDescriptor<SearchableSituation>, QueryContainer>> { };
foreach (var area in areas)
{
var pointsList = area.Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude)).ToList();
queries.Add(sqs => sqs
.GeoPolygon(r => r
.Field(f => f.Position)
.ValidationMethod(GeoValidationMethod.Strict)
.Points(pointsList)));
}
return queries;
}
使用 ElasticSearch 7.6 我想找到区域列表内的所有点。 还有一些其他筛选条件已添加到 QueryContainerDescriptors 列表并应用于最终搜索。
var queries = new List<Func<QueryContainerDescriptor<MySearchableObject>, QueryContainer>>();
此示例适用于一个区域,其中 Coordinates 是一个字典
foreach (var area in areas)
{
var pointsList = area.Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude)).ToList();
queries.Add(sqs => sqs
.GeoPolygon(r => r
.Field(f => f.Position)
.ValidationMethod(GeoValidationMethod.Strict)
.Points(pointsList)));
}
还有这个:
queries.Add(sqs => sqs.Bool(b=>b.Should(bs => GeoPolygonShouldQuery(bs, area))));
private static QueryContainer GeoPolygonShouldQuery(QueryContainerDescriptor<MySearchableObject> bs, FilterArea area)
{
return bs
.GeoPolygon(r => r
.Field(f => f.Position)
.ValidationMethod(GeoValidationMethod.Strict)
.Points(area.Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude))));
}
我如何为列表中的每个区域附加一个 should 子句?
与此类似:
queries.Add(sqs => sqs.Bool(b => b.Should(
bs => bs.GeoPolygon(r => r.Field(f => f.Position)
.Points(areas.ElementAt(0).Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude)).ToList())),
bs => bs.GeoPolygon(r => r.Field(f => f.Position)
.Points(areas.ElementAt(1).Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude)).ToList()))
)));
经过更多的尝试和错误。这似乎解决了问题:
var areas = FindFilterAreas(query.Areas);
queries.Add(sqs => sqs.Bool(b => b.Should(MyQueries(b, areas))));
private static List<Func<QueryContainerDescriptor<SearchableSituation>, QueryContainer>> MyQueries(BoolQueryDescriptor<SearchableSituation> qd, IEnumerable<FilterArea> areas)
{
List<Func<QueryContainerDescriptor<SearchableSituation>, QueryContainer>> queries = new List<Func<QueryContainerDescriptor<SearchableSituation>, QueryContainer>> { };
foreach (var area in areas)
{
var pointsList = area.Coordinates.Values.Select(p => new GeoLocation(p.Latitude, p.Longitude)).ToList();
queries.Add(sqs => sqs
.GeoPolygon(r => r
.Field(f => f.Position)
.ValidationMethod(GeoValidationMethod.Strict)
.Points(pointsList)));
}
return queries;
}