Spectre.Console.Cli注入服务的几种姿势

简介: 【7月更文挑战第13天】要在 Spectre.Console.Cli 中注入服务,可采用以下方法:1. 使用依赖注入容器: - 配置如 `Microsoft.Extensions.DependencyInjection` 这样的依赖注入容器,并注册服务2. 自定义类型注册器: - 创建自定义的 `TypeRegistrar` 类实现 `ITypeRegistrar` 接口,用于注册服务。 - 同时创建 `TypeResolver` 类实现 `ITypeResolver` 接口,用于解析服务。3. 直接手动设置依赖:

要在 Spectre.Console.Cli 中注入服务,通常可以采用以下几种方式(以下内容参考了博客园文章Spectre.Console-处理依赖注入 ):


  1. 使用依赖注入容器(如 Microsoft.Extensions.DependencyInjection):在创建 CommandApp 之前,配置依赖注入容器,将需要的服务注册到容器中。然后,通过某种方式将容器传递给 CommandApp 或相关的命令类,以便它们能够获取所需的服务。
    示例代码如下:


static void Main(string[] args)
{
    createHostBuilder(args).Build().Run();
}
public static IHostBuilder createHostBuilder(string[] args) =>
    Host.CreateDefaultBuilder(args)
      .ConfigureServices((hostContext, services) =>
       {
           services.AddSingleton<YourService>(); // 注册服务
           services.AddCommandApp(); 
       });
}
internal static IServiceCollection AddCommandApp(this IServiceCollection services)
{
    return services.AddSingleton(w =>
    {
        var app = new CommandApp();
        app.Configure(config =>
        {
            config.CaseSensitivity(CaseSensitivity.None); 
            // 配置 CommandApp 
        });
        return app;
    });
}


在上述代码中,首先在 createHostBuilder 方法中使用 ConfigureServices 注册了一个名为 YourService 的单例服务。然后在 AddCommandApp 扩展方法中创建 CommandApp 实例。


  1. 自定义类型注册器(TypeRegistrar):如果 Spectre.Console.Cli 不自带注册器或无法直接使用现有的依赖注入容器,可以创建自定义的类型注册器。这个注册器需要实现相应的接口(如 ITypeRegistrar),并提供注册服务的方法。然后将注册器传递给 CommandApp 的构造函数或其他相关设置。
    示例代码如下:


using Microsoft.Extensions.DependencyInjection; 
using Spectre.Console.Cli; 
namespace YourNamespace
{
    public sealed class TypeRegistrar : ITypeRegistrar
    {
        private readonly IServiceCollection _builder;
        public TypeRegistrar(IServiceCollection builder)
        {
            _builder = builder;
        }
        public ITypeResolver Build()
        {
            return new TypeResolver(_builder.BuildServiceProvider());
        }
        public void Register(Type service, Type implementation)
        {
            _builder.AddSingleton(service, implementation);
        }
        public void RegisterInstance(Type service, object implementation)
        {
            _builder.AddSingleton(service, implementation);
        }
        public void RegisterMethod(Type service, Func<object> func)
        {
            if (func == null)
            {
                throw new ArgumentNullException(nameof(func));
            }
            _builder.AddSingleton(service, (provider) => func());
        }
    }
    public sealed class TypeResolver : ITypeResolver, IDisposable
    {
        private readonly IServiceProvider _provider;
        public TypeResolver(IServiceProvider provider)
        {
            _provider = provider?? throw new ArgumentNullException(nameof(provider));
        }
        public object? Resolve(Type? type)
        {
            if (type == null)
            {
                return null;
            }
            return _provider.GetService(type);
        }
        public void Dispose()
        {
            if (_provider is IDisposable disposable)
            {
                disposable.Dispose();
            }
        }
    }
}


在上述代码中,自定义了 TypeRegistrar 类实现 ITypeRegistrar 接口,用于注册服务。TypeResolver 类实现 ITypeResolver 接口,用于解析服务。然后在使用 CommandApp 时,可以这样创建并传递注册器:


public static int Main(string[] args)
{
    // 创建类型注册器并注册依赖
    var registrations = new ServiceCollection();
    registrations.AddSingleton<IGreeter, HelloWorldGreeter>(); 
    var registrar = new TypeRegistrar(registrations); 
    // 使用注册器创建 CommandApp 实例
    var app = new CommandApp<DefaultCommand>(registrar); 
    // 运行 CommandApp 
    return app.Run(args); 
}


  1. 直接在 CommandApp 中手动设置依赖:如果无法使用上述方式,或者 CommandApp 提供了一些设置依赖的方法,可以直接在创建 CommandApp 后,通过相应的方法或属性设置所需的服务实例。


具体采用哪种方式,取决于 Spectre.Console.Cli 的具体实现和项目的架构需求。可能需要根据实际情况进行调整和适配。同时,确保在注入服务后,相关的命令类能够正确地获取和使用注入的服务来完成其功能。

相关文章
|
缓存 JavaScript
运行vue报错npm ERR! A complete log of this run can be found in解决办法
在这里我们需要清除npm的缓存: (1)在cmd命令行窗口中输入:npm cache clean --force (2)然后再运行我们需要安装模块的命令,输入npm install。 有时是网络问题,依赖包加载不完整,删掉node_modules文件后,重新执行npm install即可。
1940 0
|
1月前
【Azure Function】Function App和Powershell 集成问题, 如何安装PowerShell的依赖模块
【Azure Function】Function App和Powershell 集成问题, 如何安装PowerShell的依赖模块
|
1月前
|
JavaScript
【Azure Function App】Nodejs Function遇见WorkerProcessExitException : node exited with code -1073740791 (0xC0000409) 错误
【Azure Function App】Nodejs Function遇见WorkerProcessExitException : node exited with code -1073740791 (0xC0000409) 错误
|
3月前
|
JavaScript
vue : 无法加载文件 D:\module\npm_module\npm_modules\vue.ps1,因为在此系统上禁止运行脚本。有关详细信息,请参阅 https:/go.microsoft.c
vue : 无法加载文件 D:\module\npm_module\npm_modules\vue.ps1,因为在此系统上禁止运行脚本。有关详细信息,请参阅 https:/go.microsoft.c
|
4月前
|
JavaScript 前端开发 开发者
使用`console.log()`查看运行结果非常简单
【4月更文挑战第18天】使用`console.log()`查看运行结果非常简单
192 1
|
4月前
去除生产环境的debugger 和console
去除生产环境的debugger 和console
39 0
|
4月前
|
JavaScript 前端开发 Linux
vue3在Linux下无法正常启动:esbuild-linux-64、cantnot start service :host version “0.13.15“,esbuild EACCESS
vue3在Linux下无法正常启动:esbuild-linux-64、cantnot start service :host version “0.13.15“,esbuild EACCESS
302 0
|
9月前
> Construction@0.1.0 serve > vue-cli-service serve ‘vue-cli-service‘ 不是内部或外部命令,也不是可运行的程序
> Construction@0.1.0 serve > vue-cli-service serve ‘vue-cli-service‘ 不是内部或外部命令,也不是可运行的程序
122 1
|
9月前
|
前端开发 JavaScript
Module build failed: TypeError: this.getResolve is not a function,vue写css时启动出错
Module build failed: TypeError: this.getResolve is not a function,vue写css时启动出错
42 0
|
10月前
|
JavaScript 前端开发 Ubuntu
nginx部署vue后显示500 Internal Server Error解决方案
nginx部署vue后显示500 Internal Server Error解决方案
297 0