C# 如何使用NEST进行筛选聚合?
我需要使用NEST筛选聚合。但由于我对这方面了解不多,我提出以下建议:C# 如何使用NEST进行筛选聚合?,c#,elasticsearch,nest,dsl,C#,elasticsearch,Nest,Dsl,我需要使用NEST筛选聚合。但由于我对这方面了解不多,我提出以下建议: class Program { static void Main(string[] args) { ISearchResponse<TestReportModel> searchResponse = ConnectionToES.EsClient()
class Program
{
static void Main(string[] args)
{
ISearchResponse<TestReportModel> searchResponse =
ConnectionToES.EsClient()
.Search<TestReportModel>
(s => s
.Index("feedbackdata")
.From(0)
.Size(50000)
.Query(q =>q.MatchAll())
);
var testRecords = searchResponse.Documents.ToList<TestReportModel>();
result = ComputeTrailGap(testRecords);
}
private static List<TestModel> ComputeTrailGap(List<TestReportModel> testRecords)
{
var objTestModel = new List<TestModel>();
var ptpDispositionCodes = new string[] { "PTP" };
var bptpDispositionCodes = new string[] { "BPTP","SBPTP" };
int gapResult = testRecords.Where(w => w.trailstatus == "Gap").Count();
var ptpResult = testRecords.Where(w => ptpDispositionCodes.Contains(w.lastdispositioncode)).ToList().Count();
var bptpResult = testRecords.Where(w => bptpDispositionCodes.Contains(w.lastdispositioncode)).ToList().Count();
objTestModel.Add(new TestModel { TrailStatus = "Gap", NoOfAccounts = gapResult });
objTestModel.Add(new TestModel { TrailStatus = "PTP", NoOfAccounts = ptpResult });
objTestModel.Add(new TestModel { TrailStatus = "BPTP", NoOfAccounts = bptpResult });
return objTestModel;
}
}
类程序
{
静态void Main(字符串[]参数)
{
ISearchResponse搜索响应=
ConnectionToES.EsClient()
.搜索
(s=>s
.索引(“反馈数据”)
.从(0)
.尺寸(50000)
.Query(q=>q.MatchAll())
);
var testRecords=searchResponse.Documents.ToList();
结果=ComputeTrailGap(测试记录);
}
私有静态列表ComputeTrailGap(列表测试记录)
{
var objTestModel=新列表();
var ptpDispositionCodes=新字符串[]{“PTP”};
var bptpDispositionCodes=新字符串[]{“BPTP”,“SBPTP”};
int gapResult=testRecords.Where(w=>w.trailstatus==“Gap”).Count();
var ptpResult=testRecords.Where(w=>ptpDispositionCodes.Contains(w.lastdispositioncode)).ToList().Count();
var bptpResult=testRecords.Where(w=>bptpDispositionCodes.Contains(w.lastdispositioncode)).ToList().Count();
Add(新的TestModel{TrailStatus=“Gap”,NoOfAccounts=gapResult});
Add(新的TestModel{TrailStatus=“PTP”,NoOfAccounts=ptpResult});
Add(新的TestModel{TrailStatus=“BPTP”,NoOfAccounts=bptpResult});
返回对象测试模型;
}
}
DTO
public class TestReportModel
{
public string trailstatus { get; set; }
public string lastdispositioncode { get; set; }
}
public class TestOutputAPIModel
{
public List<TestModel> TestModelDetail { get; set; }
}
public class TestModel
{
public string TrailStatus { get; set; }
public int NoOfAccounts { get; set; }
}
公共类TestReportModel
{
公共字符串trailstatus{get;set;}
公共字符串lastdispositioncode{get;set;}
}
公共类TestOutputAPIModel
{
公共列表TestModelDetail{get;set;}
}
公共类测试模型
{
公共字符串TrailStatus{get;set;}
公共整数{get;set;}
}
这个程序可以工作,但可以看出,我们只通过NEST访问弹性搜索,其余的聚合/过滤器使用Lambda完成
我希望使用NEST框架执行整个操作(聚合/过滤等),并使用过滤聚合将其放入TestModel中
如何在嵌套内构造DSL查询
更新
到目前为止,我已经能够进行以下操作,但计数为零。我的查询构造出了什么问题
var ptpDispositionCodes = new TermsQuery
{
IsVerbatim = true,
Field = "lastdispositioncode",
Terms = new string[] { "PTP" },
};
var bptpDispositionCodes = new TermsQuery
{
IsVerbatim = true,
Field = "lastdispositioncode",
Terms = new string[] { "BPTP" },
};
ISearchResponse<TestReportModel> searchResponse =
ConnectionToES.EsClient()
.Search<TestReportModel>
(s => s
.Index("feedbackdata")
.From(0)
.Size(50000)
.Query(q =>q.MatchAll())
.Aggregations(fa => fa
.Filter("ptp_aggs", f => f.Filter(fd => ptpDispositionCodes))
.Filter("bptp_aggs", f => f.Filter(fd => bptpDispositionCodes))
)
);
var ptpDispositionCodes=新术语查询
{
IsVerbatim=true,
Field=“lastdispositioncode”,
Terms=新字符串[]{“PTP”},
};
var bptpDispositionCodes=新术语
{
IsVerbatim=true,
Field=“lastdispositioncode”,
Terms=新字符串[]{“BPTP”},
};
ISearchResponse搜索响应=
ConnectionToES.EsClient()
.搜索
(s=>s
.索引(“反馈数据”)
.从(0)
.尺寸(50000)
.Query(q=>q.MatchAll())
.聚合(fa=>fa
.Filter(“ptp_aggs”,f=>f.Filter(fd=>ptpdispositioncode))
.Filter(“bptp_aggs”,f=>f.Filter(fd=>bptpDispositionCodes))
)
);
结果
我看到您正在尝试对
TestReportModel
类型执行搜索。您的方法的总体结构似乎已经足够好了。但是,附加到筛选容器的查询存在问题
您的TestReportModel
包含两个属性trialStatus
和lastdispositioncode
。您正在将字段
属性设置为术语
查询中的描述。这就是您将计数视为零的原因。在其上执行搜索的模型(反过来,在其上执行搜索的索引)没有属性description
,因此存在差异<代码>嵌套或Elasticsearch,在这种情况下不会引发任何异常。相反,它返回count zero<代码>字段值应修改为lastdispositioncode
// Type on which the search is being performed.
// Response is of the type ISearchResponse<TestReportModel>
public class TestReportModel
{
public string trailstatus { get; set; }
public string lastdispositioncode { get; set; }
}
由于lastdispositioncode
的值似乎只包含一个单词值(示例中的PTP或BPTP),因此我认为,是否分析文档中的字段并不重要。您可以从下面显示的ISearchResponse
类型中进一步获取计数
var ptpDocCount = ((Nest.SingleBucketAggregate)response.Aggregations["ptp_aggs"]).DocCount;
var bptpDocCount = ((Nest.SingleBucketAggregate)response.Aggregations["bptp_aggs"]).DocCount;
.Aggregations(aggs => aggs
.Filter("f1", f => f.Filter(f => qc1))
.Filter("f2", f => f.Filter(f => qc2)))
编辑:添加关键字搜索方法
在本例中,NEST
客户端生成的聚合查询如下所示
“f1”:{
“过滤器”:{
“布尔”:{
“必须”:[
{
“条款”:{
“lastdispositioncode.keyword”:[
“bptp”
]
}
}
]
}
}
}
另外,回到搜索不区分大小写的情况,Elasticsearch以不区分大小写的方式处理搜索。但是,它因分析字段与未分析字段的不同而不同。分析的字段被标记化,而文本字段默认被标记化。理想情况下,我们在分析字段上使用
NEST
的suffix
扩展方法,并在分析字段上获得精确匹配。关于它们的更多信息您是否可以添加由json格式的代码生成的原始查询。我现在已将术语值设置为小写,以获得类似“ptp”或“bptp”的结果。是否有任何方法可以使此不区分大小写。我尝试了以下方法,但幸运的是var ptpDispositionCo
QueryContainer qc1 = new QueryContainerDescriptor<TestReportModel>()
.Bool(b => b.Must(m => m.Terms(t => t.Field(f => f.lastdispositioncode.Suffix("keyword"))
.Terms(new string[]{"ptp"}))));
QueryContainer qc2 = new QueryContainerDescriptor<TestReportModel>()
.Bool(b => b.Must(m => m.Terms(t => t.Field(f => f.lastdispositioncode.Suffix("keyword"))
.Terms(new string[]{"bptp", "sbptp"}))));
.Aggregations(aggs => aggs
.Filter("f1", f => f.Filter(f => qc1))
.Filter("f2", f => f.Filter(f => qc2)))