您好我是弹性嵌套API的新手,我使用的是嵌套5.x.我目前正在开发某种高级搜索页面,因此当用户没有检查条件时,我不必在我的查询中包含该过滤器。我试图在使用nest的对象初始化方法下将must运算符下的2个查询组合起来。怎么实现呢?我跟随[https://www.elastic.co/guide/en/elasticsearch/client/net-api/current/bool-queries.html]
上的示例var secondSearchResponse = client.Search(new SearchRequest { Query = new TermQuery {Field = Field(p => p.Name),Value =" x" }&& 新的TermQuery {Field = Field(p => p.Name),Value =" y" }});
但它不起作用,因为Field类不接受类型参数。
我也试图从这个主题中采用这种方法 [Nest Elastic - Building Dynamic Nested Query
这是我的代码
public HttpResponseMessage GetSearchResult([FromUri] SearchModels queries) { try { /// string result = string.Empty; result += "queryfields + " + queries.queryfields == null ? string.Empty : queries.queryfields; result += "datefrom + " + queries.datefrom == null ? string.Empty : queries.datefrom; result += "dateto + " + queries.dateto == null ? string.Empty : queries.dateto; result += "emitentype + " + queries.emitentype == null ? string.Empty : queries.emitentype; QueryContainer andQuery = null; //List<QueryContainer> QueryContainers = new List<QueryContainer>(); IDXNetAnnouncement record = new IDXNetAnnouncement { kode_emiten = queries.kodeemiten }; #region keyword if (!string.IsNullOrEmpty(queries.queryfields)) { var val = queries.queryfields; TermQuery tq = new TermQuery { Field = queries.queryfields, Value = val }; if (andQuery == null) andQuery = tq; else andQuery &= tq; //QueryContainers.Add(tq); } #endregion keyword #region kodeemiten if (!string.IsNullOrEmpty(queries.kodeemiten)) { var val = queries.kodeemiten; TermQuery tq = new TermQuery { Name = "kode_emiten", Field = record.kode_emiten, Value = val }; if (andQuery == null) andQuery = tq; else andQuery &= tq; //QueryContainers.Add(tq); } #endregion #region date if (!string.IsNullOrEmpty(queries.datefrom) && !string.IsNullOrEmpty(queries.dateto)) { DateRangeQuery dq = new DateRangeQuery(); dq.Name = "tglpengumuman"; dq.LessThanOrEqualTo = DateMath.Anchored(queries.dateto); dq.GreaterThanOrEqualTo = DateMath.Anchored(queries.datefrom); dq.Format = "dd/mm/yyyy"; if (andQuery == null) andQuery = dq; else andQuery &= dq; //QueryContainers.Add(dq); } #endregion keyword var reqs = (ISearchResponse<IDXNetAnnouncement>)null; if (andQuery != null) { reqs = conn.client.Search<IDXNetAnnouncement>(s => s .AllIndices() .AllTypes() .From(queries.indexfrom) .Size(queries.pagesize) .Query(q => q.Bool(qb => qb.Must(m => m.MatchAll() && andQuery)))); //var json = conn.client.Serializer.SerializeToString(reqs.ApiCall.ResponseBodyInBytes); } else { reqs = conn.client.Search<IDXNetAnnouncement>(s => s .AllIndices() .AllTypes() .From(queries.indexfrom) .Size(queries.pagesize) .Query(m => m.MatchAll())); } //var reqstring = Encoding.UTF8.GetString(conn.client.); var reslts = this.conn.client.Serializer.SerializeToString(reqs,SerializationFormatting.Indented); var resp = new HttpResponseMessage() { Content = new StringContent(reslts) }; resp.Content.Headers.ContentType = new MediaTypeHeaderValue("application/json"); return resp; } catch (Exception e) { var resp = new HttpResponseMessage() { Content = new StringContent(e.ToString()) }; resp.Content.Headers.ContentType = new MediaTypeHeaderValue("application/json"); return resp; } }
但是返回零结果。怎么做到这一点?无论如何,谢谢。
编辑:
这是params变量定义。它的搜索关键字的apoco模型
public class SearchModels { public string queryfields { get; set; } public string datefrom { get; set; } public string dateto { get; set; } public string emitentype { get; set; } public string kodeemiten { get; set; } public string issuercode { get; set; } public int indexfrom { get; set; } public int pagesize { get; set; } }
IDXNetAnnouncement是搜索结果的poco模型。它实际上是一个存储在弹性服务器上的文档类型
public class IDXNetAnnouncement { public string perihalpengumuman { get; set; } public string attachments { get; set; } public string createddate { get; set; } public bool efekemiten_spei { get; set; } public string jmsxgroupid { get; set; } public string tglpengumuman { get; set; } public object errordescription { get; set; } public string ESversion { get; set; } public int oldfinalid { get; set; } public bool efekemiten_etf { get; set; } public object errorcode { get; set; } public string jenisemiten { get; set; } public int pkid { get; set; } public string judulpengumuman { get; set; } public string form_id { get; set; } public bool efekemiten_eba { get; set; } public string jenispengumuman { get; set; } public string nopengumuman { get; set; } public string kode_emiten { get; set; } public string divisi { get; set; } public string EStimestamp { get; set; } public bool efekemiten_obligasi { get; set; } public long finalid { get; set; } public bool efekemiten_saham { get; set; } public string kodedivisi { get; set; } public string SearchTerms { get { return string.Format("{0} {1} {2}", judulpengumuman, kode_emiten, nopengumuman); } } }
答案 0 :(得分:2)
但它不起作用,因为Field类不接受类型参数。
您需要确保为Nest.Infer
包括using static directive,即
using static Nest.Infer;
使用其余的using指令。
.Query(q =&gt; q.Bool(qb =&gt; qb.Must(m =&gt; m.MatchAll()&amp;&amp; andQuery))));
无需包裹Must()
,只需执行
.Query(q => q.MatchAll() && andQuery)
将在bool
查询must
子句中包装两个查询。您也不需要null
检查andQuery
,因为如果其中一个或两个都是null
,NEST足够聪明,不能合并这两个查询。
if (!string.IsNullOrEmpty(queries.queryfields)) { var val = queries.queryfields; TermQuery tq = new TermQuery { Field = queries.queryfields, Value = val }; if (andQuery == null) andQuery = tq; else andQuery &= tq; //QueryContainers.Add(tq); }
NEST具有conditionless queries的概念,因此您无需检查它queries.queryfields
是空还是空,只需构建查询并将其添加到andQuery
即可。所以它会成为
var val = queries.queryfields;
andQuery &= new TermQuery
{
Field = queries.queryfields,
Value = val
};
所有NEST文档都是从源代码生成的;您可以通过单击文档中的任何编辑链接追溯回原始源文件。这将带您进入github页面such as this one for bool queries。从这里开始,该文档包含一个重要的注释,链接回original source。