.NET Core 和 ASP.NET Core 中的日志框架

前言:

本文使用的 .NET Core SDK 3.1 版本。
本文将主要介绍ASP.NET Core自带的日志 Microsoft.Extensions.Logging 程序包的使用,
主要演示如何在 ASP.NET Core Web 应用程序控制台应用程序 中使用 Microsoft.Extensions.Logging 程序包。

首先我创建了两个项目,一个 ASP.NET Core Web 应用程序 ,另一个是 .NET Core 的 控制台应用程序
由于ASP.NET Core Web 框架已经自带了日志包,所以不用再引入。
在控制台应用程序中引入如下包:

	PM> Install-Package Microsoft.Extensions.Configuration.Json -Version 3.1.2
	PM> Install-Package Microsoft.Extensions.Logging -Version 3.1.2
	PM> Install-Package Microsoft.Extensions.Logging.Console -Version 3.1.2
	PM> Install-Package Microsoft.Extensions.Logging.Debug -Version 3.1.2
	PM> Install-Package Microsoft.Extensions.Logging.EventLog -Version 3.1.2

其中 Microsoft.Extensions.Logging 和核心包,Console 是在控制台中显示日志记录的包,
剩余的 Debug 可以在Visual Studio中的输出栏中显示日志记录,EventLog 可以将日志记录到系统(Windows)的日志记录中。

日志消息模板:
推荐使用日志模板 logger.LogInformation("Getting item {Id}", 1);,日志模板在不输出时将不会消耗字符串拼接的资源。

一、在控制台应用程序中使用日志框架

以下介绍控制台应用程序中使用日志框架

1) 日志的简单使用

首先上代码:

#region Main Function
	// 创建日志工厂对象
    var loggerFactory = LoggerFactory.Create(builder =>
    {
    
    
        builder
            .AddFilter("ConsoleLoggingTest.Program", LogLevel.Warning)
            .AddFilter((provider, category, logLevel) =>
            {
    
    
                if (provider == "Microsoft.Extensions.Logging.Console" && 
                	logLevel == LogLevel.Warning)
                {
    
    
                    return false;
                }
                return true;
            })
            .AddConsole(configure => {
    
     configure.IncludeScopes = true; })
            .AddDebug()
            .AddEventLog();
    });
    // 创建 Logger 对象
    var logger_1 = loggerFactory.CreateLogger("ConsoleLoggingTest.Program");
    var logger_2 = new Logger<Program>(loggerFactory);
    // 记录日志
	logger_1.LogInformation(eventId: 1, message: "info log");
    logger_1.LogWarning(2, "warn log");
    var ex = new Exception("error log");
    logger_1.LogError(3, ex, "warn log");
    // 记录日志-作用域
    using (logger_2.BeginScope("ScopeId: {scopeId}", Guid.NewGuid()))
    {
    
    
        logger_2.LogInformation("LogInformation");
        logger_2.LogWarning("LogInformation");
        logger_2.LogError("LogInformation");
    }
#endregion

我们先直接运行看一下,控制台得到的结果是:
日志简单使用Img

在以上代码中,我们首先使用了 LoggerFactory.Create() 方法进行创建LoggerFactory实例,
并用 ILoggingBuilderLoggerFactory进行进行了配置,
其中配置的内容有:
     1. 使用 ILoggingBuilder.AddFilter() 配置日志过滤添加到工厂,对名为 ConsoleLoggingTest.Program 的日志进行过滤,只记录日志等级大于等于LogLevel.Warning的日志。
     2. 使用 ILoggingBuilder.AddConsole() 配置控制台记录添加到工厂,配置后将能在控制台看到日志的记录。
     3. 使用 ILoggingBuilder.AddDebug() 配置调试记录添加到工厂,配置后将能够在调试时在Visual Studio的Debug窗口看到日志。
     4. 使用 ILoggingBuilder.AddEventLog() 配置事件记录添加到工厂,配置后能够在系统(Windows)的系统日志中看到,Linux本人没有测试。

然后创建了两个Logger对象,我当前 Main函数 所在的 Program 类的 namespaceConsoleLoggingTest
所以在这里 logger_1 和 logger_2 两个不同的写法,其实他们是一样的,
如果你开了 反编译源码,跟踪进 loggerFactory.CreateLogger 你会发现返回的其实还是一个 new Logger<T> 实例。

随后是记录日志,
记录日志时,message 参数是主要参数,还可以选填 eventId 对日志进行标注快速定位到日志的位置。
由于设置了 ConsoleLoggingTest.Program 的记录的日志等级不能小于 LogLevel.Warning,所以我们看不到内容为 info log 的日志。

随后是日志的作用域,
我们用日志的作用域可以清楚的在日志中找到关联的上下文,不会和其他的日志混淆。

2) 日志与容器提供程序结合使用

首先上代码:

#region appsettings.json
{
    
    
  "Logging": {
    
    
    "LogLevel": {
    
    
      "Default": "Debug",
      "Microsoft": "Warning",
      "Microsoft.Hosting.Lifetime": "Information"
    },
    "Console": {
    
    
      "LogLevel": {
    
    
        "Default": "Information",
        "ConsoleLoggingTest.Program": "Warning"
      }
    }
  }
}
#endregion

#region MyService
    public class MyService
    {
    
    
        ILogger<MyService> _logger_1;
        ILogger _logger_2;

        public MyService(ILogger<MyService> logger, ILoggerFactory loggerFactory)
        {
    
    
            _logger_1 = logger;
            _logger_2 = loggerFactory.CreateLogger("loggerFactoryTest"); ;
        }

        public void Show()
        {
    
    
            _logger_1.LogInformation("Show _logger_1");
            _logger_2.LogInformation("Show _logger_2");
        }
    }
#endregion

#region Main Function
    // 从文件中读取配置
    IConfigurationBuilder configBuilder = new ConfigurationBuilder();
    configBuilder.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true);
    var config = configBuilder.Build();
    
    // 构造一个容器
    IServiceCollection serviceCollection = new ServiceCollection();
    //用工厂模式注入将配置对象注册到容器管理
    serviceCollection.AddSingleton<IConfiguration>(p => config);
    // 将实例直接注入进去,容器将不会管理 config 的生命周期
    // serviceCollection.AddSingleton<IConfiguration>(config);
    
    // 日志记录服务添加到容器管理
    serviceCollection.AddLogging(builder =>
    {
    
    
        builder.AddConfiguration(config.GetSection("Logging"));
        builder.AddConsole();
    });
    
    serviceCollection.AddTransient<MyService>();
    // 将容器 Build 出来
    IServiceProvider service = serviceCollection.BuildServiceProvider();
    var order = service.GetService<MyService>();
    order.Show();
    
    var logger_1 = service.GetService<ILogger<Program>>();
    ILoggerFactory loggerFactory = service.GetService<ILoggerFactory>();
    var logger_2 = loggerFactory.CreateLogger<Program>();
    var logger_3 = loggerFactory.CreateLogger("ConsoleLoggingTest.Program");
    
    logger_1.LogInformation("log logger_1");
    logger_1.LogWarning("log logger_1");
    logger_2.LogInformation("log logger_2");
    logger_2.LogWarning("log logger_1");
    logger_3.LogInformation("log logger_3");
    logger_3.LogWarning("log logger_1");
#endregion

我们先直接运行看一下,控制台得到的结果是:
日志与容器提供程序结合使用Img
我们直接看 Main函数 的代码,
在前三行中我们从文件中读取配置,随后的代码构建一个容器并将配置注入进容器。

然后将日志记录添加到容器管理
使用 IServiceCollection.AddLogging() 将日志添加到容器,并对容器进行配置,
     1. 使用 AddConfiguration() 方法给日志添加配置,指定的是配置的根节点下面的Logging节点。
     2. 使用 AddConsole() 方法将使得日志能够在控制台进行展示。

然后我们将事先已经写好的 MyService 注入到容器中,并将容器 Build 出来,
随后用容器创建一个 MyService ,并直接调用 show() 方法,我们可以在 MyService 中看到如何使用以来注入来实例创建日志对象。

随后直接通过容器创建了日志对象,并打印日志,在打印的日志中我们可以看到,
由于我们给日志添加了 "ConsoleLoggingTest.Program": "Warning" 配置, LogInformation 并没有打印出来。

二、在 ASP.NET Core Web 应用程序中使用日志框架

在Web程序中使用日志框架

#region
    public static IHostBuilder CreateHostBuilder(string[] args) =>
        Host.CreateDefaultBuilder(args)
            .ConfigureLogging(logging =>
            {
    
    
                // 删除所有的日志提供程序
                logging.ClearProviders();
                logging.AddConsole(options => options.IncludeScopes = true);
            })
            .ConfigureWebHostDefaults(webBuilder =>
            {
    
    
                webBuilder.UseStartup<Startup>();
            });
#endregion

在Web程序中使用日志框架时,如果我们不想用默认配置,可以使用 ClearProviders() 方法使之前的所有配置都失效。
然后在后面自定义配置,如代码,我启动控制台记录器并开启基于作用域的日志记录。
在使用时,

#region MyService
    public class MyService
    {
    
    
        ILogger<MyService> _logger_1;
        ILogger _logger_2;

        public MyService(ILogger<MyService> logger, ILoggerFactory loggerFactory)
        {
    
    
            _logger_1 = logger;
            _logger_2 = loggerFactory.CreateLogger("loggerFactoryTest"); ;
        }

        public void Show()
        {
    
    
            _logger_1.LogInformation("Show _logger_1");
            _logger_2.LogInformation("Show _logger_2");
        }
    }
#endregion


参考文档

.NET Core 和 ASP.NET Core 中的日志记录

猜你喜欢

转载自blog.csdn.net/Upgrader/article/details/104729674