You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

依赖注入异常排查:已验证工厂方法仍报System.String解析错误

问题:依赖注入容器无法解析MyService的字符串参数

相关代码定义

MyService类

public class MyService : IMyService
{
    private readonly string _version;

    public MyService(string version)
    {
        _version = version;
    }
}

VersionedAssembly类

public class VersionedAssembly : IVersionedAssembly
{
    public string Version { get; } = typeof(VersionedAssembly).Assembly.GetName().Version!.ToString();
}

服务注册代码

services.AddSingleton<IVersionedAssembly, VersionedAssembly>();
services.AddScoped<IMyService>(provider =>
{
    string version = provider.GetRequiredService<IVersionedAssembly>().Version;
    return new MyService(version);
})

报错信息

System.InvalidOperationException: 'Unable to resolve service for type 'System.String' while attempting to activate 'MyService'.'
   at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteFactory.CreateArgumentCallSites(Type implementationType, CallSiteChain callSiteChain, ParameterInfo[] parameters, Boolean throwIfCallSiteNotFound) in /_/src/libraries/Microsoft.Extensions.DependencyInjection/src/ServiceLookup/CallSiteFactory.cs:line 518

已尝试操作

  • 简化注册代码为:
    services.AddScoped<IMyService>(provider => new MyService("1"));
    
  • 在工厂方法的string version = provider.GetRequiredService<IVersionedAssembly>()处添加断点,但断点未触发

解决方案

问题核心是DI容器并未使用你定义的工厂方法创建IMyService实例,而是尝试直接激活MyService类型,这说明你大概率在项目其他地方重复注册了IMyService或MyService,且该注册覆盖了你的工厂方法注册。

排查与修复步骤

  1. 检查重复注册:

    • 全局搜索项目中所有AddScoped<IMyService>、AddTransient<IMyService>、AddSingleton<IMyService>的代码,或是直接注册MyService的语句(如services.AddScoped<MyService>())。
    • 若存在services.AddScoped<IMyService, MyService>()这类注册,它会覆盖你的工厂方法注册——DI容器会以最后一次服务注册为准。
  2. 调整注册顺序:

    • 确保你的工厂方法注册是最后一个针对IMyService的注册,避免被其他注册覆盖。
  3. 验证注册有效性:

    • 可在注册后通过以下代码确认工厂方法是否生效:
      var descriptor = services.FirstOrDefault(d => d.ServiceType == typeof(IMyService));
      // 检查descriptor.ImplementationFactory是否不为null,以此确认工厂方法已被正确注册
      

修复示例

删除或调整重复注册的代码,确保工厂方法注册在最后:

// 移除其他重复的IMyService注册语句
services.AddSingleton<IVersionedAssembly, VersionedAssembly>();
// 确保这是最后一个IMyService的注册
services.AddScoped<IMyService>(provider =>
{
    string version = provider.GetRequiredService<IVersionedAssembly>().Version;
    return new MyService(version);
});

内容的提问来源于stack exchange,提问作者Tam Coton

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.19 05:25:28