ASP.NET Core用NEST调用Elasticsearch Search After API未返回错误日志
错误1:Match查询语法错误
你写的Match查询参数完全不符合NEST规范:
// 错误写法 q.Match(m => m.Field(f => f.Level == "error"))
Field()方法仅用于指定要匹配的字段,查询值需要通过Query()方法传递,正确写法如下:
q.Match(m => m.Field(f => f.Level).Query("error"))
错误2:ES字段与模型属性未正确映射
Serilog写入ES的时间字段名为@timestamp,你的ESFields类中的TimeStamp属性没有配置映射,NEST默认无法自动匹配带特殊符号的字段,需要给属性加PropertyName特性:
public class ESFields { public string Level { get; set; } [PropertyName("@timestamp")] public DateTime TimeStamp { get; set; } }
错误3:search_after参数使用错误
你直接传了固定值3000作为search_after参数,但你的排序规则是按@timestamp升序,search_after需要传入上一页最后一条数据的排序字段值(也就是上一页最后一条的@timestamp值),首次查询不需要加search_after,加了这个错误的固定值会导致ES过滤掉所有时间戳小于3000的记录,自然查不到数据。如果不需要分页首次查询直接删掉.SearchAfter(3000)即可。
错误4:接口返回逻辑问题
你查询了最多3000条数据,但仅返回了第一条FirstOrDefault(),如果要返回所有符合条件的日志应该返回response?.Documents。
可选优化:ConnectionSettings配置补充
初始化ConnectionSettings时建议添加默认映射,避免后续字段匹配问题:
var settings = new ConnectionSettings(node) .DefaultMappingFor<ESFields>(m => m.IndexName("elastic-search-app-logs*"));
修正后的完整查询代码
[HttpGet] public async Task<List<ESFields>> Get() { var response = await _elasticClient.SearchAsync<ESFields>(s => s .Index("elastic-search-app-logs*") .Size(3000) .Query(q => q.Match(m => m.Field(f => f.Level).Query("error"))) .Sort(srt => srt.Ascending(p => p.TimeStamp))); // 可加调试日志排查查询失败原因 if (!response.IsValid) { Console.WriteLine(response.ServerError?.Error?.Reason); } return response?.Documents?.ToList() ?? new List<ESFields>(); }
内容的提问来源于stack exchange,提问作者NoviceCoder
相关产品推荐
相关产品推荐

