在 ASP.NET Core 中使用 Serilog 使用 Fluentd 将日志写入 Elasticsearch

在 ASP.NET Core 中使用 Serilog 使用 Fluentd 将日志写入 Elasticsearch

原文来自:https://andrewlock.net/writing-logs-to-elasticsearch-with-fluentd-using-serilog-in-asp-net-core/

对于在 Kubernetes 中运行的应用程序,将日志消息存储在一个中心位置尤为重要。我认为这对所有应用程序都很重要,无论您使用的是 Kubernetes 还是 docker,但 pod 和容器的短暂性质使得后一种情况特别重要。

如果您没有集中存储容器中的日志,那么如果容器崩溃并重新启动,日志可能会永远丢失。

有很多方法可以实现这一目标。您可以直接从您的应用程序登录Elasticsearch或Seq,或者登录到Elmah.io等外部服务。一种常见的方法是使用 Fluentd 从容器的控制台输出中收集日志,并将这些日志通过管道传输到 Elasticsearch 集群。

默认情况下,ASP.NET Core 中的控制台日志输出格式为人类可读格式。如果您采用 Fluentd/Elasticsearch 方法,您需要确保您的控制台输出采用 Elasticsearch 可以理解的结构化格式,即 JSON。

在这篇文章中,我描述了如何将 Serilog 添加到 ASP.NET Core 应用程序,以及如何自定义 Serilog 控制台接收器的输出格式,以便您可以使用 Fluentd 将控制台输出通过管道传输到 Elasticsearch。

请注意,也可以将 Serilog 配置为使用Elasticsearch sink直接写入Elasticsearch。如果您没有使用 Fluentd,或者没有将您的应用程序容器化,那么这是一个不错的选择。

将日志写入控制台输出

当您从模板创建新的 ASP.NET Core 应用程序时,您的程序文件将如下所示(至少在 .NET Core 2.1 中):

public class Program
{public static void Main(string[] args){CreateWebHostBuilder(args).Build().Run();}public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>WebHost.CreateDefaultBuilder(args).UseStartup<Startup>();
}

静态辅助方法WebHost.CreateDefaultBuilder(args)创建一个WebHostBuilder并连接许多标准配置选项[1]。默认情况下,它配置控制台和调试记录器提供程序:

.ConfigureLogging((hostingContext, logging) =>
{logging.AddConfiguration(hostingContext.Configuration.GetSection("Logging"));logging.AddConsole();logging.AddDebug();
})

如果您从命令行使用 运行您的应用程序dotnet run,您将在控制台中看到每个请求的日志。下面显示了来自浏览器的两个请求生成的日志 - 一个用于主页,另一个用于 favicon.ico。

使用默认控制台记录器的控制台输出

不幸的是,控制台记录器在如何写入日志方面没有提供很大的灵活性。您可以选择包含 scopes或禁用颜色,但仅此而已。

ASP.NET Core 中默认Microsoft.Extensions.Logging基础结构的替代方法是使用 Serilog进行日志记录,并将其作为标准 ASP.NET Core 记录器进行连接。

将 Serilog 添加到 ASP.NET Core 应用程序

Serilog是一个成熟的开源项目,早于 ASP.NET Core 中的所有日志记录基础结构。在许多方面,ASP.NET Core 日志记录基础结构似乎以 Serilog 为模型:Serilog 具有类似的配置选项和可插拔的“接收器”来控制写入日志的位置。

开始使用 Serilog 的最简单方法是使用Serilog.AspNetCore NuGet 包。使用以下命令将其添加到您的应用程序中:

dotnet add package Serilog.AspNetCore

您还需要添加一个或多个“sink”包,以控制日志的写入位置。在这种情况下,我将安装控制台接收器,但如果您想一次写入多个目的地,您也可以添加其他接收器。

dotnet add package Serilog.Sinks.Console

Serilog.AspNetCore 包UseSerilog()WebHostBuilder实例上提供了一个扩展方法。这用ILoggerFactorySerilog 的实现替换了默认值。您可以传入现有Serilog.ILogger实例,也可以内联配置记录器。例如,以下代码配置将写入的最低日志级别 ( info) 并注册控制台接收器:

public static IWebHostBuilder CreateWebHostBuilder(string[] args) =>WebHost.CreateDefaultBuilder(args).UseSerilog((ctx, config) =>{config.MinimumLevel.Information().Enrich.FromLogContext().WriteTo.Console();}).UseStartup<Startup>();
}

当您使用 Serilog 而不是默认记录器时再次运行应用程序会提供以下控制台输出:

使用 Serilog 而不是默认的控制台记录器的控制台输出

输出类似于默认记录器,但重要的是它是非常可配置的。您可以随意更改输出模板。例如,您可以通过包含SourceContext参数来显示生成日志的类的名称。

有关 Serilog.AspNetCore 包的更多详细信息和示例,请参阅 GitHub 存储库[2]。有关控制台格式选项,请参阅Serilog.Sinks.Console 存储库[3]

除了对输出模板的简单更改外,控制台接收器还允许完全控制消息的呈现方式。我们将使用该功能将日志呈现为 Fluentd 的 JSON,而不是人性化的格式。

自定义Serilog Console Sink的输出格式写入JSON

要更改数据的呈现方式,您可以添加自定义ITextFormatter. Serilog 包含一个JsonFormatter您可以使用的,但建议您考虑使用Serilog.Formatting.Compact包[4]

CompactJsonFormatter与 Serilog 的默认值相比,大大减少了小日志事件的字节数JsonFormatter,同时保持人类可读。它通过更短的内置属性名称、更精简的格式以及排除冗余信息来实现这一点。”

我们不会将这个包用于我们的 Fluentd/Elasticsearch 用例,但我将展示如何在任何情况下插入它。使用 添加包dotnet add package Serilog.Formatting.Compact,创建格式化程序的新实例,并将其传递给调用中的WriteTo.Console()方法UseSerilog()

.UseSerilog((ctx, config) =>
{config.MinimumLevel.Information().Enrich.FromLogContext().WriteTo.Console(new CompactJsonFormatter());
})

现在,如果您运行您的应用程序,您将看到以 JSON 格式写入控制台的日志:

使用 CompactJsonFormatter 以 JSON 格式写入控制台的日志图像

这个格式化程序可能对您有用,但就我而言,我希望编写 JSON 以便 Elasticsearch 能够理解它。您可以看到紧凑的 JSON 格式(在下面打印得很漂亮),正如承诺的那样,为时间戳 ( @t)、消息模板 ( @mt) 和呈现的消息 ( @r)使用了紧凑的名称:

{"@t": "2018-05-17T10:23:47.0727764Z","@mt": "{HostingRequestStartingLog:l}","@r": ["Request starting HTTP\/1.1 GET http:\/\/localhost:5000\/  "],"Protocol": "HTTP\/1.1","Method": "GET","ContentType": null,"ContentLength": null,"Scheme": "http","Host": "localhost:5000","PathBase": "","Path": "\/","QueryString": "","HostingRequestStartingLog": "Request starting HTTP\/1.1 GET http:\/\/localhost:5000\/  ","EventId": {"Id": 1},"SourceContext": "Microsoft.AspNetCore.Hosting.Internal.WebHost","RequestId": "0HLDRS135F8A6:00000001","RequestPath": "\/","CorrelationId": null,"ConnectionId": "0HLDRS135F8A6"
}

对于最简单的 Fluentd/Elasticsearch 集成,我希望使用标准 Elasticsearch 名称(例如@timestamp时间戳)输出 JSON 。幸运的是,所需要的只是更换格式化程序。

使用与 Elasticsearch 兼容的 JSON 格式化程序

Serilog.Sinks.Elasticsearch

包包含正是我们所需要的格式ElasticsearchJsonFormatter。这使用标准 Elasticsearch 字段(如@timestamp和 )呈现数据fields

不幸的是,目前除了复制和粘贴源代码首先检查许可证之外,将格式化程序添加到您的项目的唯一方法是安装整个Serilog.Sinks.Elasticsearch包,它有很多依赖项。

理想情况下,我希望将格式化程序视为它自己的独立包,就像Serilog.Formatting.Compac

一我提出了一个问题[5]如果这对您来说不是问题(这对我来说不是问题,因为我已经依赖Elasticsearch.Net,那么添加 Elasticsearch Sink 来访问格式化程序是最简单的解决方案。使用添加接收器dotnet add package Serilog.Sinks.ElasticSearch,并更新您的 Serilog 配置使用ElasticsearchJsonFormatter

.UseSerilog((ctx, config) =>
{config.MinimumLevel.Information().Enrich.FromLogContext().WriteTo.Console(new ElasticsearchJsonFormatter();
})

连接此格式化程序后,控制台输出将包含常见的 Elasticsearch 字段,如@timestamp,如下面(漂亮打印)输出所示:

{  "@timestamp": "2018-05-17T22:31:43.9143984+12:00",  "level": "Information",  "messageTemplate": "{HostingRequestStartingLog:l}",  "message": "Request starting HTTP\/1.1 GET http:\/\/localhost:5000\/  ",  "fields": {    "Protocol": "HTTP\/1.1",    "Method": "GET",    "ContentType": null,    "ContentLength": null,    "Scheme": "http",    "Host": "localhost:5000",    "PathBase": "",    "Path": "\/",    "QueryString": "",    "HostingRequestStartingLog": "Request starting HTTP\/1.1 GET http:\/\/localhost:5000\/  ",    "EventId": {      "Id": 1    },    "SourceContext": "Microsoft.AspNetCore.Hosting.Internal.WebHost",    "RequestId": "0HLDRS5H8TSM4:00000001",    "RequestPath": "\/",    "CorrelationId": null,    "ConnectionId": "0HLDRS5H8TSM4"  },  "renderings": {    "HostingRequestStartingLog": [      {        "Format": "l",        "Rendering": "Request starting HTTP\/1.1 GET http:\/\/localhost:5000\/  "      }    ]  }}

现在日志以一种可以直接从 Fluentd 传输到 Elasticsearch 的格式呈现。我们可以只写到控制台。

根据托管环境在输出格式化程序之间切换

最后的提示。如果您想在本地开发时获得人类可读的控制台输出,并且只在 Staging 或 Production 中使用 JSON 格式化程序怎么办?

这很容易实现,因为UseSerilog扩展提供了IHostingEnvironment通过WebHostBuilderContext. 例如,在以下代码段中,我将应用程序配置为在开发中使用人类可读的控制台,并在其他环境中使用 JSON 格式化程序。

.UseSerilog((ctx, config) =>
{config.MinimumLevel.Information().Enrich.FromLogContext();if (ctx.HostingEnvironment.IsDevelopment()){config.WriteTo.Console();}else{config.WriteTo.Console(new ElasticsearchJsonFormatter());}
})

除了环境之外,您还可以根据通过IConfiguration对象 at提供的配置值进行切换ctx.Configuration

概括

将日志存储在一个中心位置很重要,尤其是在您构建容器化应用程序时。一种可能的解决方案是将日志输出到控制台,让 Fluentd 监控控制台,并将输出通过管道传输到 Elasticsearch 集群。在这篇文章中,我描述了如何将 Serilog 日志记录添加到您的 ASP.NET Core 应用程序并将其配置为以 Elasticsearch 期望的 JSON 格式将日志写入控制台。

References

[1] 连接许多标准配置选项: https://github.com/aspnet/MetaPackages/blob/2.1.0-rc1-final/src/Microsoft.AspNetCore/WebHost.cs#L150
[2] 请参阅 GitHub 存储库: https://github.com/serilog/serilog-aspnetcore
[3] Serilog.Sinks.Console 存储库: https://github.com/serilog/serilog-sinks-console
[4] 考虑使用Serilog.Formatting.Compact包: https://github.com/serilog/serilog-formatting-compact

[5] 我提出了一个问题: https://github.com/serilog/serilog-sinks-elasticsearch/issues/176

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/299685.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

2021年度最全面JVM虚拟机,类加载过程与类加载器

前言 类装载器子系统是JVM中非常重要的部分&#xff0c;是学习JVM绕不开的一关。 一般来说&#xff0c;Java 类的虚拟机使用 Java 方式如下&#xff1a; Java 源程序&#xff08;.java 文件&#xff09;在经过 Java 编译器编译之后就被转换成 Java 字节代码&#xff08;.class …

做生意最重要的诚信呢??? | 今日最佳

全世界只有3.14 % 的人关注了青少年数学之旅&#xff08;图源网络&#xff0c;侵权删&#xff09;

面试避坑手册之 Java字节流和字符流总结IO流!

从接收输入值说起 在日常的开发应用中&#xff0c;有时候需要直接接收外部设备如键盘等的输入值&#xff0c;而对于这种数据的接收方式&#xff0c;我们一般有三种方法&#xff1a;字节流读取&#xff0c;字符流读取&#xff0c;Scanner 工具类读取。 字节流读取 直接看一个…

这家AI公司用面具破解中国人脸识别系统!微信、支付宝、火车站无一幸免

全世界只有3.14 % 的人关注了青少年数学之旅据外媒报道&#xff0c;一家人工智能公司Kneron用一个特制的3D面具&#xff0c;成功欺骗了包括支付宝和微信在内的诸多人脸识别支付系统&#xff0c;完成了购物支付程序。他们用同样的方式甚至进入了中国的火车站。现如今&#xff0c…

coolite TreeNode NodeClick传id到后台的方法

重点如下&#xff1a; 1 <AjaxEvents>2 <Click OnEvent"PanelTree_Click" >3 <EventMask ShowMask"true" Msg"正在执行,请稍后" />4 <E…

使用JavaScript实现页面选项自动添加行以及删除行 javaweb

2019独角兽企业重金招聘Python工程师标准>>> <% page language"java" import"java.util.*" pageEncoding"UTF-8"%> <% String path request.getContextPath(); String basePath request.getScheme()"://"reques…

C#基础知识之base、this、new、override、abstract梳理

一、Base关键词的几种用法base重要用于OOP的多态上&#xff0c;base 关键字用于在派生类中实现对基类公有或者受保护成员的访问&#xff0c;但是只局限在构造函数、实例方法和实例属性访问器中1、base调用基类构造函数using System;namespace BaseDemo {class Program{static v…

班主任老师推荐这些优质的教育号,建议家长们多阅读!

全世界只有3.14 % 的人关注了青少年数学之旅推荐几个教育类学习号让孩子少走弯路&#xff0c;为孩子成长保驾护航&#xff01;长按二维码&#xff0c;选择【识别图中二维码】关注理想父母 lixiangfumu&#xff08;长按二维码识别关注&#xff09;关注理由&#xff1a;面向家长…

学妹问我Java枚举类与注解,我直接用这个搞定她!

很多人问我学妹长什么样&#xff0c;不多说 上图吧&#xff01; 学妹问我Java枚举类与注解&#xff0c;我直接一篇文章搞定&#xff01;一、枚举类① 自定义枚举类② enum关键字定义枚举类③ enum 枚举类的方法④ enum 枚举类实现接口二、注解① 生成文档相关注解②注解在编译…

设计模式之代理

代理模式介绍啥是代理模式&#xff1f;代理模式 是一种结构型设计模式&#xff0c;让你能够提供对象的替代品或其占位符。代理控制着对于原对象的访问&#xff0c;并允许在将请求提交给对象前后进行一些处理。其实说通俗点&#xff0c;就好比我们平时生活中的购买机票&#xff…

轮子,辛苦你了。 | 今日最佳

全世界只有3.14 % 的人关注了青少年数学之旅&#xff08;图源帅哥李坏的朋友圈&#xff0c;侵权删&#xff09;

这次牛逼了,面试字节被问LinkedList原理了!手足无措啊

概述 LinkedList底层是基于链表实现。链表没有长度限制&#xff0c;内存地址不需要固定长度&#xff0c;也不需要是连续的地址来进行存储&#xff0c;只需要通过引用来关联前后元素即可完成整个链表的连续。所以链表的优点就是添加删除元素比较快&#xff0c;只需要移动指针&a…

[WP8.1UI控件编程]Windows Phone自定义布局规则

3.2 自定义布局规则 上一节介绍了Windows Phone的系统布局面板和布局系统的相关原理&#xff0c;那么系统的布局面板并不一定会满足所有的你想要实现的布局规律&#xff0c;如果有一些特殊的布局规律&#xff0c;系统的布局面板是不支持&#xff0c;这时候就需要去自定义实现一…

聊聊编程语言的选择

我适合学什么编程语言呢&#xff1f;大家好&#xff0c;我是鱼皮&#xff0c;今天聊聊编程语言的选择问题&#xff0c;通过对 10 主流编程语言的特点、优劣、应用场景、发展前景等简单分析&#xff0c;希望帮还在迷茫的小伙伴们选择最适合自己的语言去学习。编程语言选择本文大…

IIS6文件权限不对触发了Windows身份认证问题解决方法

今天在iis上调试程序的时候突然发现需要登录: 通过csdn提问得知可能是权限设置有问题于是设置了下internet来宾用户: 结果问题没有解决.后来想想应该不是问题,因为我在自己机器上调试用的是Everyone权限,应该都可以访问. 于是我又去用户管理中重置internet来宾用户密码: 重置In…

C++ Exercises(十五)--排序算法的简单实现

structNode {//队列结点 int data; struct Node* pNext;};classCQueue{//队列类(带头结点&#xff09;public: CQueue(void); ~CQueue(void); bool isEmpty()const;//是否为空 void EnQueue(int num);//入队列 int DeQueue();//出队列 int Front()cons…

朋友圈终于能斗表情包了,会发表情包您就多发点!

全世界只有3.14 % 的人关注了青少年数学之旅今日&#xff0c;微信ios端更新至7.0.9版本&#xff0c;又上了一次微博热搜。版本新增了朋友圈图片评论功能&#xff0c;动态图、静态图均可&#xff0c;点击图片评论即可查看大图&#xff0c;评论图片同步聊天表情包库。各路网友收到…

EF Core 异步编程注意要点

????欢迎点赞 &#xff1a;???? 收藏 ⭐留言 ???? 如有错误敬请指正&#xff0c;赐人玫瑰&#xff0c;手留余香&#xff01;????本文作者&#xff1a;由webmote 原创&#xff0c;????作者格言&#xff1a;生活在于折腾&#xff0c;当你不折腾生活时&#x…

看电影的第一大禁忌 | 今日最佳

全世界只有3.14 % 的人关注了青少年数学之旅&#xff08;图源网络&#xff0c;侵权删&#xff09;

求职华为,被问观察者模式,从没有这种体验!!!

求职华为&#xff0c;被问观察者模式&#xff0c;从没有这种体验&#xff01;&#xff01;&#xff01;模式的定义与特点模式的结构与实现1. 模式的结构2. 模式的实现模式的应用实例模式的应用场景模式的扩展1. Observable类2. Observer 接口[ 观察者模式可以说是非常贴近我们…