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

.NET 8运行Program.cs遇System.AggregateException的解决求助

依赖注入与IHostedService生命周期问题排查

问题背景

基于IHostedService实现邮件后台服务时,启动Program.cs触发System.AggregateException,此前未添加邮件后台发送逻辑时功能正常。

错误详情

System.AggregateException: 'Some services are not able to be constructed (Error while validating the service descriptor 'ServiceType: Business.Abstract.ICustomerService Lifetime: Scoped ImplementationType: Business.Concrete.CustomerManager': Unable to resolve service for type 'DataAccess.Concrete.EntityFramework.SqlContext' while attempting to activate 'DataAccess.Concrete.EntityFramework.EfCustomerDal'.) (Error while validating the service descriptor 'ServiceType: DataAccess.Abstract.ICustomerDal Lifetime: Scoped ImplementationType: DataAccess.Concrete.EntityFramework.EfCustomerDal': Unable to resolve service for type 'DataAccess.Concrete.EntityFramework.SqlContext' while attempting to activate 'DataAccess.Concrete.EntityFramework.EfCustomerDal'.) (Error while validating the service descriptor 'ServiceType: Microsoft.Extensions.Hosting.IHostedService Lifetime: Singleton ImplementationType: KodiksProject.API.Services.EmailBackgroundService': Unable to resolve service for type 'Business.Concrete.CustomerManager' while attempting to activate 'KodiksProject.API.Services.EmailBackgroundService'.)'

相关代码片段

ICustomerService

public interface ICustomerService
{
    IResult Add(Customer customer);
    IResult Update(Customer customer);
    IResult Delete(int id);
    IDataResult<Customer> Get(int id);
    IDataResult<List<Customer>> GetAll();
    Task SendEmailsToCustomersAsync();
}

CustomerManager

public class CustomerManager : ICustomerService
{
    ICustomerDal _customerDal;
    private readonly IEmailService _emailService;

    public CustomerManager(ICustomerDal customerDal, IEmailService emailService)  
    { 
        _customerDal = customerDal;
        _emailService = emailService;
    }

    public IResult Add(Customer customer)
    {
        _customerDal.Add(customer);
        return new SuccessResult();
    }

    public IResult Delete(int id)
    {
        _customerDal.Delete(id);
        return new SuccessResult();
    }

    public IDataResult<Customer> Get(int id)
    {
        return new SuccessDataResult<Customer>(_customerDal.Get(c => c.CustomerId == id));
    }

    public IDataResult<List<Customer>> GetAll()
    {
        return new SuccessDataResult<List<Customer>>(_customerDal.GetAll());
    }

    public IResult Update(Customer customer)
    {
        _customerDal.Update(customer);
        return new SuccessResult();
    }

    public async Task SendEmailsToCustomersAsync()
    {
        var customerEmails = await _customerDal.GetAllCustomerEmailsAsync();
        var tasks = new List<Task>();

        foreach (var email in customerEmails)
        {
            var task = _emailService.SendEmailAsync(email, "asdasas", "asasadasdasd");
            tasks.Add(task);
        }

        await Task.WhenAll(tasks);
    }
}

SqlContext

public class SqlContext : DbContext
{
    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        optionsBuilder.UseSqlServer(@"my connection string");
    }

    public DbSet<Customer> Customers { get; set; }
    public DbSet<Order> Orders { get; set; }
    public DbSet<Product> Products { get; set; }
}

EfCustomerDal

public class EfCustomerDal : EfEntityRepositoryBase<Customer, SqlContext>, ICustomerDal
{
    private readonly SqlContext _context;

    public EfCustomerDal(SqlContext context)
    {
        _context = context;
    }

    public async Task<List<string>> GetAllCustomerEmailsAsync()
    {
        var emails = await _context.Customers
                                    .Select(c => c.Email)
                                    .ToListAsync();

        return emails;
    }
}

ICustomerDal

public interface ICustomerDal : IEntityRepository<Customer>
{
    Task<List<string>> GetAllCustomerEmailsAsync();
}

EmailService

public class EmailService : IEmailService
{
    private readonly SmtpClient _smtpClient;

    public EmailService()
    {
        _smtpClient = new SmtpClient("server")
        {
            Port = 465,
            Credentials = new NetworkCredential("username", "password"),
            EnableSsl = true,
        };
    }

    public async Task SendEmailAsync(string to, string subject, string body)
    {
        var mailMessage = new MailMessage("username", to, subject, body);
        await _smtpClient.SendMailAsync(mailMessage);
    }
}

问题根源与解决方法

问题分析

  1. 核心底层问题:SqlContext未注册到依赖注入容器,导致EfCustomerDal无法被构造
  2. 连锁问题:CustomerManager依赖EfCustomerDal,因此也无法完成构造
  3. 生命周期冲突:EmailBackgroundService是Singleton生命周期,直接依赖Scoped的ICustomerService,即使前面的问题解决,也会出现生命周期不兼容的错误

解决步骤

步骤1:注册SqlContext到DI容器

在Program.cs的服务配置中添加:

builder.Services.AddDbContext<SqlContext>(options =>
    options.UseSqlServer(@"my connection string"));

(建议将连接字符串存入配置文件,避免硬编码)

步骤2:修正Singleton依赖Scoped服务的问题

IHostedService是Singleton,不能直接注入Scoped服务,需通过IServiceScopeFactory手动创建作用域。修改EmailBackgroundService:

public class EmailBackgroundService : BackgroundService
{
    private readonly IServiceScopeFactory _scopeFactory;

    public EmailBackgroundService(IServiceScopeFactory scopeFactory)
    {
        _scopeFactory = scopeFactory;
    }

    protected override async Task ExecuteAsync(CancellationToken stoppingToken)
    {
        while (!stoppingToken.IsCancellationRequested)
        {
            using (var scope = _scopeFactory.CreateScope())
            {
                var customerService = scope.ServiceProvider.GetRequiredService<ICustomerService>();
                await customerService.SendEmailsToCustomersAsync();
            }

            // 设置邮件发送间隔,示例为每小时一次
            await Task.Delay(TimeSpan.FromHours(1), stoppingToken);
        }
    }
}

步骤3:确保其他服务正确注册

检查Program.cs中是否完成以下服务注册:

builder.Services.AddScoped<ICustomerDal, EfCustomerDal>();
builder.Services.AddScoped<ICustomerService, CustomerManager>();
builder.Services.AddScoped<IEmailService, EmailService>();
builder.Services.AddHostedService<EmailBackgroundService>();

内容的提问来源于stack exchange,提问作者Umut Konmus

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.21 18:05:15