diff --git a/Directory.Packages.props b/Directory.Packages.props index 03deeb6..e57d4bc 100644 --- a/Directory.Packages.props +++ b/Directory.Packages.props @@ -22,6 +22,7 @@ + diff --git a/src/NetEvolve.Logging.XUnit/XUnitLogger.cs b/src/NetEvolve.Logging.XUnit/XUnitLogger.cs index c837f93..80f9340 100644 --- a/src/NetEvolve.Logging.XUnit/XUnitLogger.cs +++ b/src/NetEvolve.Logging.XUnit/XUnitLogger.cs @@ -45,7 +45,17 @@ public static XUnitLogger CreateLogger( IMessageSink messageSink, IExternalScopeProvider? scopeProvider = null, IXUnitLoggerOptions? options = null - ) => CreateLogger(messageSink, TimeProvider.System, scopeProvider, options); + ) + { + Argument.ThrowIfNull(messageSink); + + return new XUnitLogger( + message => _ = messageSink.OnMessage(new DiagnosticMessage(message)), + TimeProvider.System, + scopeProvider, + options + ); + } /// /// Creates a new instance of . @@ -65,7 +75,12 @@ public static XUnitLogger CreateLogger( Argument.ThrowIfNull(messageSink); Argument.ThrowIfNull(timeProvider); - return new XUnitLogger(messageSink, timeProvider, scopeProvider, options); + return new XUnitLogger( + message => _ = messageSink.OnMessage(new DiagnosticMessage(message)), + timeProvider, + scopeProvider, + options + ); } /// @@ -81,7 +96,12 @@ public static XUnitLogger CreateLogger( IExternalScopeProvider? scopeProvider = null, IXUnitLoggerOptions? options = null ) - where T : notnull => CreateLogger(messageSink, scopeProvider, options); + where T : notnull + { + Argument.ThrowIfNull(messageSink); + + return new XUnitLogger(messageSink, TimeProvider.System, scopeProvider, options); + } /// /// Creates a new instance of . @@ -98,7 +118,13 @@ public static XUnitLogger CreateLogger( IExternalScopeProvider? scopeProvider = null, IXUnitLoggerOptions? options = null ) - where T : notnull => new XUnitLogger(messageSink, timeProvider, scopeProvider, options); + where T : notnull + { + Argument.ThrowIfNull(messageSink); + Argument.ThrowIfNull(timeProvider); + + return new XUnitLogger(messageSink, timeProvider, scopeProvider, options); + } /// /// Creates a new instance of . @@ -111,7 +137,17 @@ public static XUnitLogger CreateLogger( ITestOutputHelper testOutputHelper, IExternalScopeProvider? scopeProvider = null, IXUnitLoggerOptions? options = null - ) => CreateLogger(testOutputHelper, TimeProvider.System, scopeProvider, options); + ) + { + Argument.ThrowIfNull(testOutputHelper); + + return new XUnitLogger( + testOutputHelper.WriteLine, + TimeProvider.System, + scopeProvider, + options + ); + } /// /// Creates a new instance of . @@ -131,7 +167,7 @@ public static XUnitLogger CreateLogger( Argument.ThrowIfNull(testOutputHelper); Argument.ThrowIfNull(timeProvider); - return new XUnitLogger(testOutputHelper, timeProvider, scopeProvider, options); + return new XUnitLogger(testOutputHelper.WriteLine, timeProvider, scopeProvider, options); } /// @@ -147,8 +183,12 @@ public static XUnitLogger CreateLogger( IExternalScopeProvider? scopeProvider = null, IXUnitLoggerOptions? options = null ) - where T : notnull => - CreateLogger(testOutputHelper, TimeProvider.System, scopeProvider, options); + where T : notnull + { + Argument.ThrowIfNull(testOutputHelper); + + return new XUnitLogger(testOutputHelper, TimeProvider.System, scopeProvider, options); + } /// /// Creates a new instance of . @@ -165,36 +205,22 @@ public static XUnitLogger CreateLogger( IExternalScopeProvider? scopeProvider = null, IXUnitLoggerOptions? options = null ) - where T : notnull => - new XUnitLogger(testOutputHelper, timeProvider, scopeProvider, options); - - private protected XUnitLogger( - ITestOutputHelper testOutputHelper, - TimeProvider timeProvider, - IExternalScopeProvider? scopeProvider, - IXUnitLoggerOptions? options - ) + where T : notnull { Argument.ThrowIfNull(testOutputHelper); Argument.ThrowIfNull(timeProvider); - ScopeProvider = scopeProvider ?? NullExternalScopeProvider.Instance; - _timeProvider = timeProvider; - _options = options ?? XUnitLoggerOptions.Default; - - _loggedMessages = []; - - _writeToLog = testOutputHelper.WriteLine; + return new XUnitLogger(testOutputHelper, timeProvider, scopeProvider, options); } - private protected XUnitLogger( - IMessageSink messageSink, + internal XUnitLogger( + Action writeToAction, TimeProvider timeProvider, IExternalScopeProvider? scopeProvider, IXUnitLoggerOptions? options ) { - Argument.ThrowIfNull(messageSink); + Argument.ThrowIfNull(writeToAction); Argument.ThrowIfNull(timeProvider); ScopeProvider = scopeProvider ?? NullExternalScopeProvider.Instance; @@ -203,7 +229,7 @@ private protected XUnitLogger( _loggedMessages = []; - _writeToLog = message => _ = messageSink.OnMessage(new DiagnosticMessage(message)); + _writeToLog = writeToAction; } /// diff --git a/src/NetEvolve.Logging.XUnit/XUnitLoggerProvider.cs b/src/NetEvolve.Logging.XUnit/XUnitLoggerProvider.cs index 7a3556e..c12d41a 100644 --- a/src/NetEvolve.Logging.XUnit/XUnitLoggerProvider.cs +++ b/src/NetEvolve.Logging.XUnit/XUnitLoggerProvider.cs @@ -7,6 +7,7 @@ using NetEvolve.Arguments; using NetEvolve.Logging.Abstractions; using Xunit.Abstractions; +using Xunit.Sdk; [ProviderAlias("XUnit")] internal sealed class XUnitLoggerProvider @@ -14,8 +15,7 @@ internal sealed class XUnitLoggerProvider ISupportExternalScope, IXUnitLoggerOptions { - private readonly ITestOutputHelper? _testOutputHelper; - private readonly IMessageSink? _messageSink; + private readonly Action _writeToAction; private readonly IExternalScopeProvider _scopeProvider = NullExternalScopeProvider.Instance; private readonly XUnitLoggerOptions _options; @@ -55,7 +55,7 @@ public XUnitLoggerProvider( _timeProvider = timeProvider; _loggers = new ConcurrentDictionary(StringComparer.Ordinal); - _messageSink = messageSink; + _writeToAction = message => messageSink.OnMessage(new DiagnosticMessage(message)); } public XUnitLoggerProvider( @@ -74,7 +74,7 @@ public XUnitLoggerProvider( _timeProvider = timeProvider; _loggers = new ConcurrentDictionary(StringComparer.Ordinal); - _testOutputHelper = testOutputHelper; + _writeToAction = testOutputHelper.WriteLine; } /// @@ -84,30 +84,7 @@ public ILogger CreateLogger(string categoryName) return _loggers.GetOrAdd( $"{categoryName}_Default", - name => - { - if (_testOutputHelper is not null) - { - return XUnitLogger.CreateLogger( - _testOutputHelper, - _timeProvider, - _scopeProvider, - this - ); - } - - if (_messageSink is not null) - { - return XUnitLogger.CreateLogger( - _messageSink, - _timeProvider, - _scopeProvider, - this - ); - } - - throw new InvalidOperationException(); - } + name => new XUnitLogger(_writeToAction, _timeProvider, _scopeProvider, this) ); } @@ -116,30 +93,7 @@ public ILogger CreateLogger() where T : notnull => _loggers.GetOrAdd( $"{typeof(T).FullName}_Default", - _ => - { - if (_testOutputHelper is not null) - { - return XUnitLogger.CreateLogger( - _testOutputHelper, - _timeProvider, - _scopeProvider, - this - ); - } - - if (_messageSink is not null) - { - return XUnitLogger.CreateLogger( - _messageSink, - _timeProvider, - _scopeProvider, - this - ); - } - - throw new InvalidOperationException(); - } + _ => new XUnitLogger(_writeToAction, _timeProvider, _scopeProvider, this) ); /// diff --git a/src/NetEvolve.Logging.XUnit/XUnitLogger`T.cs b/src/NetEvolve.Logging.XUnit/XUnitLogger`T.cs index f129233..81dcd3a 100644 --- a/src/NetEvolve.Logging.XUnit/XUnitLogger`T.cs +++ b/src/NetEvolve.Logging.XUnit/XUnitLogger`T.cs @@ -3,6 +3,7 @@ using System; using Microsoft.Extensions.Logging; using Xunit.Abstractions; +using Xunit.Sdk; /// public sealed class XUnitLogger : XUnitLogger, ILogger @@ -14,7 +15,14 @@ internal XUnitLogger( IExternalScopeProvider? scopeProvider, IXUnitLoggerOptions? options ) - : base(messageSink, timeProvider, scopeProvider, options) { } + : base( + messageSink is not null + ? message => messageSink.OnMessage(new DiagnosticMessage(message)) + : throw new ArgumentNullException(nameof(messageSink)), + timeProvider, + scopeProvider, + options + ) { } internal XUnitLogger( ITestOutputHelper testOutputHelper, @@ -22,5 +30,20 @@ internal XUnitLogger( IExternalScopeProvider? scopeProvider, IXUnitLoggerOptions? options ) - : base(testOutputHelper, timeProvider, scopeProvider, options) { } + : base( + testOutputHelper is not null + ? testOutputHelper.WriteLine + : throw new ArgumentNullException(nameof(testOutputHelper)), + timeProvider, + scopeProvider, + options + ) { } + + internal XUnitLogger( + Action writeToAction, + TimeProvider timeProvider, + IExternalScopeProvider? scopeProvider, + IXUnitLoggerOptions? options + ) + : base(writeToAction, timeProvider, scopeProvider, options) { } } diff --git a/tests/NetEvolve.Logging.XUnit.Tests.Unit/NetEvolve.Logging.XUnit.Tests.Unit.csproj b/tests/NetEvolve.Logging.XUnit.Tests.Unit/NetEvolve.Logging.XUnit.Tests.Unit.csproj index aa354f3..4d394ed 100644 --- a/tests/NetEvolve.Logging.XUnit.Tests.Unit/NetEvolve.Logging.XUnit.Tests.Unit.csproj +++ b/tests/NetEvolve.Logging.XUnit.Tests.Unit/NetEvolve.Logging.XUnit.Tests.Unit.csproj @@ -14,6 +14,7 @@ runtime; build; native; contentfiles; analyzers; buildtransitive + all diff --git a/tests/NetEvolve.Logging.XUnit.Tests.Unit/XUnitLoggerOfTTests.cs b/tests/NetEvolve.Logging.XUnit.Tests.Unit/XUnitLoggerOfTTests.cs new file mode 100644 index 0000000..f1cf8aa --- /dev/null +++ b/tests/NetEvolve.Logging.XUnit.Tests.Unit/XUnitLoggerOfTTests.cs @@ -0,0 +1,41 @@ +namespace NetEvolve.Logging.XUnit.Tests.Unit; + +using System; +using Xunit; +using Xunit.Abstractions; + +public partial class XUnitLoggerOfTTests +{ + [Fact] + public void Constructor_WithMessageSinkNull_ThrowArgumentNullException() + { + IMessageSink messageSink = null!; + + _ = Assert.Throws( + "messageSink", + () => _ = new XUnitLogger(messageSink, null!, null!, null!) + ); + } + + [Fact] + public void Constructor_WithTestOutputHelperNull_ThrowArgumentNullException() + { + ITestOutputHelper testOutputHelper = null!; + + _ = Assert.Throws( + "testOutputHelper", + () => _ = new XUnitLogger(testOutputHelper, null!, null!, null!) + ); + } + + [Fact] + public void Constructor_WithWriteToActionNull_ThrowArgumentNullException() + { + Action writeToAction = null!; + + _ = Assert.Throws( + "writeToAction", + () => _ = new XUnitLogger(writeToAction, null!, null!, null!) + ); + } +} diff --git a/tests/NetEvolve.Logging.XUnit.Tests.Unit/XUnitLoggerTests.cs b/tests/NetEvolve.Logging.XUnit.Tests.Unit/XUnitLoggerTests.cs index 55b4671..c25d68d 100644 --- a/tests/NetEvolve.Logging.XUnit.Tests.Unit/XUnitLoggerTests.cs +++ b/tests/NetEvolve.Logging.XUnit.Tests.Unit/XUnitLoggerTests.cs @@ -1,7 +1,10 @@ namespace NetEvolve.Logging.XUnit.Tests.Unit; +using System; using Microsoft.Extensions.Logging; +using NSubstitute; using Xunit; +using Xunit.Abstractions; public partial class XUnitLoggerTests { @@ -28,4 +31,144 @@ public void LogLevelToString_Theory_Expected(string expected, LogLevel logLevel) { "CRIT", LogLevel.Critical }, { "NONE", LogLevel.None } }; + + [Fact] + public void CreateLogger_WithMessageSinkNull_ThrowsArgumentNullException() + { + IMessageSink messageSink = null!; + + _ = Assert.Throws( + "messageSink", + () => XUnitLogger.CreateLogger(messageSink) + ); + } + + [Fact] + public void CreateLogger_WithMessageSinkNullAndTimeProviderNull_ThrowsArgumentNullException() + { + IMessageSink messageSink = null!; + TimeProvider timeProvider = null!; + + _ = Assert.Throws( + "messageSink", + () => XUnitLogger.CreateLogger(messageSink, timeProvider) + ); + } + + [Fact] + public void CreateLogger_WithMessageSinkSubstituteAndTimeProviderNull_ThrowsArgumentNullException() + { + var messageSink = Substitute.For(); + TimeProvider timeProvider = null!; + + _ = Assert.Throws( + "timeProvider", + () => XUnitLogger.CreateLogger(messageSink, timeProvider) + ); + } + + [Fact] + public void CreateLoggerGeneric_WithMessageSinkNull_ThrowsArgumentNullException() + { + IMessageSink messageSink = null!; + + _ = Assert.Throws( + "messageSink", + () => XUnitLogger.CreateLogger(messageSink) + ); + } + + [Fact] + public void CreateLoggerGeneric_WithMessageSinkNullAndTimeProviderNull_ThrowsArgumentNullException() + { + IMessageSink messageSink = null!; + TimeProvider timeProvider = null!; + + _ = Assert.Throws( + "messageSink", + () => XUnitLogger.CreateLogger(messageSink, timeProvider) + ); + } + + [Fact] + public void CreateLoggerGeneric_WithMessageSinkSubstituteAndTimeProviderNull_ThrowsArgumentNullException() + { + var messageSink = Substitute.For(); + TimeProvider timeProvider = null!; + + _ = Assert.Throws( + "timeProvider", + () => XUnitLogger.CreateLogger(messageSink, timeProvider) + ); + } + + [Fact] + public void CreateLogger_WithTestOutputHelperNull_ThrowsArgumentNullException() + { + ITestOutputHelper testOutputHelper = null!; + + _ = Assert.Throws( + "testOutputHelper", + () => XUnitLogger.CreateLogger(testOutputHelper) + ); + } + + [Fact] + public void CreateLogger_WithTestOutputHelperNullAndTimeProviderNull_ThrowsArgumentNullException() + { + ITestOutputHelper testOutputHelper = null!; + TimeProvider timeProvider = null!; + + _ = Assert.Throws( + "testOutputHelper", + () => XUnitLogger.CreateLogger(testOutputHelper, timeProvider) + ); + } + + [Fact] + public void CreateLogger_WithTestOutputHelperSubstituteAndTimeProviderNull_ThrowsArgumentNullException() + { + var testOutputHelper = Substitute.For(); + TimeProvider timeProvider = null!; + + _ = Assert.Throws( + "timeProvider", + () => XUnitLogger.CreateLogger(testOutputHelper, timeProvider) + ); + } + + [Fact] + public void CreateLoggerGeneric_WithTestOutputHelperNull_ThrowsArgumentNullException() + { + ITestOutputHelper testOutputHelper = null!; + + _ = Assert.Throws( + "testOutputHelper", + () => XUnitLogger.CreateLogger(testOutputHelper) + ); + } + + [Fact] + public void CreateLoggerGeneric_WithTestOutputHelperNullAndTimeProviderNull_ThrowsArgumentNullException() + { + ITestOutputHelper testOutputHelper = null!; + TimeProvider timeProvider = null!; + + _ = Assert.Throws( + "testOutputHelper", + () => XUnitLogger.CreateLogger(testOutputHelper, timeProvider) + ); + } + + [Fact] + public void CreateLoggerGeneric_WithTestOutputHelperSubstituteAndTimeProviderNull_ThrowsArgumentNullException() + { + var testOutputHelper = Substitute.For(); + TimeProvider timeProvider = null!; + + _ = Assert.Throws( + "timeProvider", + () => XUnitLogger.CreateLogger(testOutputHelper, timeProvider) + ); + } }