diff --git a/CliFx.Tests/CliFx.Tests.csproj b/CliFx.Tests/CliFx.Tests.csproj index a3588ce..b8c278f 100644 --- a/CliFx.Tests/CliFx.Tests.csproj +++ b/CliFx.Tests/CliFx.Tests.csproj @@ -14,6 +14,7 @@ + diff --git a/CliFx.Tests/TypeActivationSpecs.cs b/CliFx.Tests/TypeActivationSpecs.cs index 86be4ec..4e1e6c7 100644 --- a/CliFx.Tests/TypeActivationSpecs.cs +++ b/CliFx.Tests/TypeActivationSpecs.cs @@ -4,6 +4,7 @@ using System.Threading.Tasks; using CliFx.Infrastructure; using CliFx.Tests.Utils; using FluentAssertions; +using Microsoft.Extensions.DependencyInjection; using Xunit; using Xunit.Abstractions; @@ -87,7 +88,7 @@ public class Command : ICommand } [Fact] - public async Task Delegate_type_activator_can_initialize_a_type_using_a_custom_function() + public async Task Custom_type_activator_can_initialize_a_type_using_a_given_function() { // Arrange var commandType = DynamicCommandBuilder.Compile( @@ -110,7 +111,7 @@ public class Command : ICommand var application = new CliApplicationBuilder() .AddCommand(commandType) .UseConsole(FakeConsole) - .UseTypeActivator(type => Activator.CreateInstance(type, "hello world")!) + .UseTypeActivator(type => Activator.CreateInstance(type, "Hello world")!) .Build(); // Act @@ -123,11 +124,55 @@ public class Command : ICommand // Assert exitCode.Should().Be(0); - stdOut.Trim().Should().Be("hello world"); + stdOut.Trim().Should().Be("Hello world"); } [Fact] - public async Task Delegate_type_activator_fails_if_the_underlying_function_returns_null() + public async Task Custom_type_activator_can_initialize_a_type_using_a_service_provider() + { + // Arrange + var commandType = DynamicCommandBuilder.Compile( + // language=cs + @" +[Command] +public class Command : ICommand +{ + private readonly string _foo; + + public Command(string foo) => _foo = foo; + + public ValueTask ExecuteAsync(IConsole console) + { + console.Output.WriteLine(_foo); + return default; + } +}"); + + var serviceProvider = new ServiceCollection() + .AddSingleton(commandType, Activator.CreateInstance(commandType, "Hello world")!) + .BuildServiceProvider(); + + var application = new CliApplicationBuilder() + .AddCommand(commandType) + .UseConsole(FakeConsole) + .UseTypeActivator(serviceProvider) + .Build(); + + // Act + var exitCode = await application.RunAsync( + Array.Empty(), + new Dictionary() + ); + + var stdOut = FakeConsole.ReadOutputString(); + + // Assert + exitCode.Should().Be(0); + stdOut.Trim().Should().Be("Hello world"); + } + + [Fact] + public async Task Custom_type_activator_fails_if_the_underlying_function_returns_null() { // Arrange var commandType = DynamicCommandBuilder.Compile( diff --git a/CliFx/CliApplicationBuilder.cs b/CliFx/CliApplicationBuilder.cs index b4a72b8..6c5d47b 100644 --- a/CliFx/CliApplicationBuilder.cs +++ b/CliFx/CliApplicationBuilder.cs @@ -182,6 +182,12 @@ public partial class CliApplicationBuilder public CliApplicationBuilder UseTypeActivator(Func typeActivator) => UseTypeActivator(new DelegateTypeActivator(typeActivator)); + /// + /// Configures the application to use the specified service provider for activating types. + /// + public CliApplicationBuilder UseTypeActivator(IServiceProvider serviceProvider) => + UseTypeActivator(serviceProvider.GetService); + /// /// Creates a configured instance of . ///