Skip to content

Commit a3b4f69

Browse files
committed
Replace log4net with Serilog
1 parent 7c0f1c3 commit a3b4f69

File tree

8 files changed

+109
-186
lines changed

8 files changed

+109
-186
lines changed

Directory.Packages.props

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,15 @@
44
</PropertyGroup>
55
<ItemGroup>
66
<PackageVersion Include="CommandLineParser" Version="2.9.1" />
7-
<PackageVersion Include="log4net" Version="2.0.17" />
87
<PackageVersion Include="Microsoft.Build" Version="17.10.4" />
8+
<PackageVersion Include="Microsoft.Extensions.Logging" Version="8.0.0" />
99
<PackageVersion Include="Microsoft.NET.Test.Sdk" Version="17.10.0" />
1010
<PackageVersion Include="NuGet.Commands" Version="6.10.1" />
11+
<PackageVersion Include="Serilog" Version="4.0.1" />
12+
<PackageVersion Include="Serilog.Extensions.Logging" Version="8.0.0" />
13+
<PackageVersion Include="Serilog.Sinks.Async" Version="2.0.0" />
14+
<PackageVersion Include="Serilog.Sinks.Console" Version="6.0.0" />
15+
<PackageVersion Include="Serilog.Sinks.File" Version="6.0.0" />
1116
<PackageVersion Include="Shouldly" Version="4.2.1" />
1217
<PackageVersion Include="xunit" Version="2.9.0" />
1318
<PackageVersion Include="xunit.runner.visualstudio" Version="2.8.2" />

src/PackagesConfigConverter.UnitTests/E2ETests.cs

Lines changed: 1 addition & 107 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,6 @@
22
//
33
// Licensed under the MIT license.
44

5-
using log4net;
6-
using log4net.Core;
75
using System;
86
using System.Collections.Generic;
97
using System.Diagnostics;
@@ -108,7 +106,7 @@ public void E2ETest(string testCase)
108106
var converterSettings = new ProjectConverterSettings()
109107
{
110108
Include = ConverterInclude,
111-
Log = new TestLog(TestOutputHelper),
109+
Log = new XUnitLogger(TestOutputHelper),
112110
RepositoryRoot = workingDir,
113111
};
114112
var converter = new ProjectConverter(converterSettings);
@@ -121,109 +119,5 @@ public void E2ETest(string testCase)
121119
string actualProjectContent = File.ReadAllText(Path.Combine(workingDir, BeforeProjectName));
122120
Assert.Equal(expectedProjectContent, actualProjectContent);
123121
}
124-
125-
private sealed class TestLog : ILog
126-
{
127-
private const string DebugLevel = "Debug";
128-
private const string ErrorLevel = "Error";
129-
private const string FatalLevel = "Fatal";
130-
private const string InfoLevel = "Info";
131-
private const string WarnLevel = "Warn";
132-
133-
private readonly ITestOutputHelper _testOutputHelper;
134-
135-
public TestLog(ITestOutputHelper testOutputHelper)
136-
{
137-
_testOutputHelper = testOutputHelper;
138-
}
139-
140-
public bool IsDebugEnabled => true;
141-
142-
public bool IsInfoEnabled => true;
143-
144-
public bool IsWarnEnabled => true;
145-
146-
public bool IsErrorEnabled => true;
147-
148-
public bool IsFatalEnabled => true;
149-
150-
public ILogger Logger => throw new NotImplementedException();
151-
152-
public void Debug(object message) => Log(DebugLevel, message);
153-
154-
public void Debug(object message, Exception exception) => Log(DebugLevel, message, exception);
155-
156-
public void DebugFormat(string format, params object[] args) => Log(DebugLevel, format, args);
157-
158-
public void DebugFormat(string format, object arg0) => Log(DebugLevel, string.Format(format, arg0));
159-
160-
public void DebugFormat(string format, object arg0, object arg1) => Log(DebugLevel, string.Format(format, arg0, arg1));
161-
162-
public void DebugFormat(string format, object arg0, object arg1, object arg2) => Log(DebugLevel, string.Format(format, arg0, arg2));
163-
164-
public void DebugFormat(IFormatProvider provider, string format, params object[] args) => Log(DebugLevel, string.Format(provider, format, args));
165-
166-
public void Error(object message) => Log(ErrorLevel, message);
167-
168-
public void Error(object message, Exception exception) => Log(ErrorLevel, message, exception);
169-
170-
public void ErrorFormat(string format, params object[] args) => Log(ErrorLevel, format, args);
171-
172-
public void ErrorFormat(string format, object arg0) => Log(ErrorLevel, string.Format(format, arg0));
173-
174-
public void ErrorFormat(string format, object arg0, object arg1) => Log(ErrorLevel, string.Format(format, arg0, arg1));
175-
176-
public void ErrorFormat(string format, object arg0, object arg1, object arg2) => Log(ErrorLevel, string.Format(format, arg0, arg2));
177-
178-
public void ErrorFormat(IFormatProvider provider, string format, params object[] args) => Log(ErrorLevel, string.Format(provider, format, args));
179-
180-
public void Fatal(object message) => Log(FatalLevel, message);
181-
182-
public void Fatal(object message, Exception exception) => Log(FatalLevel, message, exception);
183-
184-
public void FatalFormat(string format, params object[] args) => Log(FatalLevel, format, args);
185-
186-
public void FatalFormat(string format, object arg0) => Log(FatalLevel, string.Format(format, arg0));
187-
188-
public void FatalFormat(string format, object arg0, object arg1) => Log(FatalLevel, string.Format(format, arg0, arg1));
189-
190-
public void FatalFormat(string format, object arg0, object arg1, object arg2) => Log(FatalLevel, string.Format(format, arg0, arg2));
191-
192-
public void FatalFormat(IFormatProvider provider, string format, params object[] args) => Log(FatalLevel, string.Format(provider, format, args));
193-
194-
public void Info(object message) => Log(InfoLevel, message);
195-
196-
public void Info(object message, Exception exception) => Log(InfoLevel, message, exception);
197-
198-
public void InfoFormat(string format, params object[] args) => Log(InfoLevel, format, args);
199-
200-
public void InfoFormat(string format, object arg0) => Log(InfoLevel, string.Format(format, arg0));
201-
202-
public void InfoFormat(string format, object arg0, object arg1) => Log(InfoLevel, string.Format(format, arg0, arg1));
203-
204-
public void InfoFormat(string format, object arg0, object arg1, object arg2) => Log(InfoLevel, string.Format(format, arg0, arg2));
205-
206-
public void InfoFormat(IFormatProvider provider, string format, params object[] args) => Log(InfoLevel, string.Format(provider, format, args));
207-
208-
public void Warn(object message) => Log(WarnLevel, message);
209-
210-
public void Warn(object message, Exception exception) => Log(WarnLevel, message, exception);
211-
212-
public void WarnFormat(string format, params object[] args) => Log(WarnLevel, format, args);
213-
214-
public void WarnFormat(string format, object arg0) => Log(WarnLevel, string.Format(format, arg0));
215-
216-
public void WarnFormat(string format, object arg0, object arg1) => Log(WarnLevel, string.Format(format, arg0, arg1));
217-
218-
public void WarnFormat(string format, object arg0, object arg1, object arg2) => Log(WarnLevel, string.Format(format, arg0, arg2));
219-
220-
public void WarnFormat(IFormatProvider provider, string format, params object[] args) => Log(WarnLevel, string.Format(provider, format, args));
221-
222-
private void Log(string level, object message) => _testOutputHelper.WriteLine($"[{level}] {message}");
223-
224-
private void Log(string level, object message, Exception exception) => _testOutputHelper.WriteLine($"[{level}] {message}. Exception: {exception}");
225-
226-
private void Log(string level, string format, params object[] args) => _testOutputHelper.WriteLine($"[{level}] {format}", args);
227-
}
228122
}
229123
}
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
// Copyright (c) Jeff Kluge. All rights reserved.
2+
//
3+
// Licensed under the MIT license.
4+
5+
using Microsoft.Extensions.Logging;
6+
using System;
7+
using Xunit.Abstractions;
8+
9+
namespace PackagesConfigConverter.UnitTests
10+
{
11+
internal sealed class XUnitLogger : ILogger
12+
{
13+
private readonly ITestOutputHelper _testOutputHelper;
14+
15+
public XUnitLogger(ITestOutputHelper testOutputHelper)
16+
{
17+
_testOutputHelper = testOutputHelper;
18+
}
19+
20+
public bool IsEnabled(LogLevel logLevel) => logLevel != LogLevel.None;
21+
22+
public IDisposable BeginScope<TState>(TState state)
23+
where TState : notnull => null;
24+
25+
public void Log<TState>(LogLevel logLevel, EventId eventId, TState state, Exception exception, Func<TState, Exception, string> formatter)
26+
=> _testOutputHelper.WriteLine(formatter(state, exception));
27+
}
28+
}

src/PackagesConfigConverter/PackagesConfigConverter.csproj

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,14 @@
55
</PropertyGroup>
66
<ItemGroup>
77
<PackageReference Include="CommandLineParser" />
8-
<PackageReference Include="log4net" />
98
<PackageReference Include="Microsoft.Build" />
9+
<PackageReference Include="Microsoft.Extensions.Logging" />
1010
<PackageReference Include="NuGet.Commands" />
11+
<PackageReference Include="Serilog" />
12+
<PackageReference Include="Serilog.Extensions.Logging" />
13+
<PackageReference Include="Serilog.Sinks.Async" />
14+
<PackageReference Include="Serilog.Sinks.Console" />
15+
<PackageReference Include="Serilog.Sinks.File" />
1116
</ItemGroup>
1217
<ItemGroup>
1318
<InternalsVisibleTo Include="PackagesConfigConverter.UnitTests" />

src/PackagesConfigConverter/Program.cs

Lines changed: 40 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -3,38 +3,26 @@
33
// Licensed under the MIT license.
44

55
using CommandLine;
6-
using log4net;
7-
using log4net.Appender;
8-
using log4net.Core;
6+
using Microsoft.Extensions.Logging;
7+
using Serilog;
8+
using Serilog.Events;
99
using System;
1010
using System.Diagnostics;
1111
using System.IO;
12-
using System.Linq;
1312
using System.Threading;
1413

14+
using ILogger = Microsoft.Extensions.Logging.ILogger;
15+
1516
namespace PackagesConfigConverter
1617
{
1718
internal class Program
1819
{
19-
private static readonly CancellationTokenSource CancellationTokenSource = new ();
20-
21-
private static readonly ILog Log = LogManager.GetLogger(typeof(Program));
22-
2320
public static int Main(string[] args)
2421
{
2522
int ret = 0;
2623

2724
try
2825
{
29-
Console.CancelKeyPress += (_, e) =>
30-
{
31-
e.Cancel = false;
32-
33-
Log.Info("Cancelling...");
34-
35-
CancellationTokenSource.Cancel();
36-
};
37-
3826
new Parser(parserSettings =>
3927
{
4028
parserSettings.CaseInsensitiveEnumValues = true;
@@ -71,19 +59,22 @@ public static void Run(ProgramArguments arguments)
7159

7260
ConfigureLogger(arguments);
7361

62+
using ILoggerFactory factory = LoggerFactory.Create(builder => builder.AddSerilog());
63+
ILogger logger = factory.CreateLogger("PackagesConfigConverter");
64+
7465
ProjectConverterSettings settings = new ProjectConverterSettings
7566
{
7667
RepositoryRoot = arguments.RepoRoot,
7768
Include = arguments.Include.ToRegex(),
7869
Exclude = arguments.Exclude.ToRegex(),
79-
Log = Log,
70+
Log = logger,
8071
TrimPackages = arguments.Trim,
8172
};
8273

83-
Log.Info($" RepositoryRoot: '{settings.RepositoryRoot}'");
84-
Log.Info($" Include regex: '{settings.Include}'");
85-
Log.Info($" Exclude regex: '{settings.Exclude}'");
86-
Log.Info(string.Empty);
74+
logger.LogInformation($" RepositoryRoot: '{settings.RepositoryRoot}'");
75+
logger.LogInformation($" Include regex: '{settings.Include}'");
76+
logger.LogInformation($" Exclude regex: '{settings.Exclude}'");
77+
logger.LogInformation(string.Empty);
8778

8879
if (!arguments.Yes)
8980
{
@@ -94,39 +85,44 @@ public static void Run(ProgramArguments arguments)
9485
}
9586
}
9687

88+
var cancellationTokenSource = new CancellationTokenSource();
89+
Console.CancelKeyPress += (_, e) =>
90+
{
91+
e.Cancel = false;
92+
93+
logger.LogInformation("Cancelling...");
94+
95+
cancellationTokenSource.Cancel();
96+
};
97+
9798
using IProjectConverter projectConverter = ProjectConverterFactory.Create(settings);
9899

99-
projectConverter.ConvertRepository(CancellationTokenSource.Token);
100+
projectConverter.ConvertRepository(cancellationTokenSource.Token);
100101
}
101102

102103
private static void ConfigureLogger(ProgramArguments arguments)
103104
{
104-
foreach (AppenderSkeleton appender in Log.Logger.Repository.GetAppenders().OfType<AppenderSkeleton>())
105+
var loggingConfiguration = new LoggerConfiguration();
106+
107+
loggingConfiguration.MinimumLevel.Is(arguments.Verbose ? LogEventLevel.Verbose : LogEventLevel.Debug);
108+
109+
// Always write to the console.
110+
LogEventLevel consoleLogLevel = arguments.Verbose ? LogEventLevel.Verbose : LogEventLevel.Information;
111+
loggingConfiguration.WriteTo.Console(consoleLogLevel);
112+
113+
if (arguments.LogFile != null)
105114
{
106-
switch (appender)
115+
string logFile = Path.Combine(Environment.CurrentDirectory, Path.GetFileName(arguments.LogFile));
116+
if (File.Exists(logFile))
107117
{
108-
case FileAppender fileAppender:
109-
if (arguments.LogFile != null)
110-
{
111-
fileAppender.File = Path.Combine(Environment.CurrentDirectory, Path.GetFileName(arguments.LogFile));
112-
}
113-
else
114-
{
115-
fileAppender.Threshold = Level.Off;
116-
}
117-
118-
fileAppender.ActivateOptions();
119-
120-
break;
118+
File.Delete(logFile);
121119
}
122120

123-
if (arguments.Verbose)
124-
{
125-
appender.Threshold = Level.Verbose;
126-
127-
appender.ActivateOptions();
128-
}
121+
LogEventLevel fileLogLevel = arguments.Verbose ? LogEventLevel.Verbose : LogEventLevel.Debug;
122+
loggingConfiguration.WriteTo.Async(a => a.File(logFile, fileLogLevel));
129123
}
124+
125+
Log.Logger = loggingConfiguration.CreateLogger();
130126
}
131127
}
132128
}

0 commit comments

Comments
 (0)