手动获取IServiceProvider依赖注入的 服务实例
手动获取IServiceProvider依赖注入的 服务实例 Task.Run(() => { try { //Task里创建了新的IServiceScope using var scope = _scopeFactory.CreateScope(); //通过IServiceScope创建具体实例 LibraryContext dbContext = scope.ServiceProvider.GetService<LibraryContext>(); var list = dbContext!.Informations.Where(i => i.IsDelete == 0).Take(100).ToList(); } Task.Run(() => { try { //Task里创建了新的IServiceScope using var scope = _serviceProvider.CreateScope(); //通过IServiceScope创建具体实例 LibraryContext dbContext = scope.ServiceProvider.GetService<LibraryContext>(); var list = dbContext!.Informations.Where(i => i.IsDelete == 0).Take(100).ToList(); } [Route("api/[controller]/[action]")] [ApiController] public class InformationController : ControllerBase { private readonly LibraryContext _libraryContext; private readonly IServiceProvider _serviceProvider; private readonly ILogger<InformationController> _logger; public InformationController(LibraryContext libraryContext, IServiceProvider serviceProvider, ILogger<InformationController> logger) { _libraryContext = libraryContext; _serviceProvider = serviceProvider; _logger = logger; } [HttpGet] public string GetFirst() { var caseInfo = _libraryContext.Informations.Where(i => i.IsDelete == 0).FirstOrDefault(); //这里直接使用了Task方式 Task.Run(() => { try { //Task里创建了新的IServiceScope using var scope = _serviceProvider.CreateScope(); //通过IServiceScope创建具体实例 LibraryContext dbContext = scope.ServiceProvider.GetService<LibraryContext>(); var list = dbContext!.Informations.Where(i => i.IsDelete == 0).Take(100).ToList(); } catch (Exception ex) { _logger.LogError(ex.Message, ex); } }); return caseInfo.Title; } } 报错: Cannot access a disposed object. Object name: 'IServiceProvider'. [Route("api/[controller]/[action]")] [ApiController] public class InformationController : ControllerBase { private readonly LibraryContext _libraryContext; private readonly IServiceScopeFactory _scopeFactory; private readonly ILogger<InformationController> _logger; public InformationController(LibraryContext libraryContext, IServiceScopeFactory scopeFactory, ILogger<InformationController> logger) { _libraryContext = libraryContext; _scopeFactory = scopeFactory; _logger = logger; } [HttpGet] public string GetFirst() { var caseInfo = _libraryContext.Informations.Where(i => i.IsDelete == 0).FirstOrDefault(); //这里直接使用了Task方式 Task.Run(() => { try { //Task里创建了新的IServiceScope using var scope = _scopeFactory.CreateScope(); //通过IServiceScope创建具体实例 LibraryContext dbContext = scope.ServiceProvider.GetService<LibraryContext>(); var list = dbContext!.Informations.Where(i => i.IsDelete == 0).Take(100).ToList(); } catch (Exception ex) { _logger.LogError(ex.Message, ex); } }); return caseInfo.Title; } } //如果想获取根容器的实例则可以通过获取IServiceScopeFactory实例获取,最后请注意IServiceScope的释放问题。 微软给我们的建议是 注入一个IServiceScopeFactory以便在后台工作项中创建一个范围。 IServiceScopeFactory是一个单例对象。 在后台线程中创建一个新的依赖注入范围。 不引用控制器中的任何东西。 不从传入请求中捕获DbContext。 https://learn.microsoft.com/en-us/aspnet/core/performance/performance-best-practices?view=aspnetcore-6.0#do-not-capture-services-injected-into-the-controllers-on-background-threads [HttpGet("/fire-and-forget-3")] public IActionResult FireAndForget3([FromServices]IServiceScopeFactory serviceScopeFactory) { _ = Task.Run(async () => { await Task.Delay(1000); using (var scope = serviceScopeFactory.CreateScope()) { var context = scope.ServiceProvider.GetRequiredService<ContosoDbContext>(); context.Contoso.Add(new Contoso()); await context.SaveChangesAsync(); } }); return Accepted(); } public void Configure(IApplicationBuilder app) { ServiceLocator.Instance = app.ApplicationServices; } public static class ServiceLocator { public static IServiceProvider Instance { get; set; } } public void DemoMethod() { var demoService = ServiceLocator.Instance.GetService<IDemoService>(); } 注意:使用ServiceLocator.Instance.GetService()只能获取AddTransient和AddSingleton注入的对象,而不能获取AddScoped(请求生命周期内唯一)注入的对象,因为获取的对象和构造函数获取的不是同一个(即获取的对象没有共享),使用场景比如IUnitOfWork。 using Microsoft.AspNetCore.Http; using Microsoft.Extensions.DependencyInjection; namespace Domain { public class DemoService : IDemoService { private IUnitOfWork _unitOfWork; public DemoService (IHttpContextAccessor httpContextAccessor) { _unitOfWork = httpContextAccessor.HttpContext.RequestServices.GetService<IUnitOfWork>(); } } } https://www.cnblogs.com/donchen/p/16484705.html 源文:https://www.cnblogs.com/wucy/p/16566495.html private readonly IServiceProvider _serviceProvider; public SomeService(IServiceProvider serviceProvider) { _serviceProvider = serviceProvider; } var eventBus = _serviceProvider.GetService(typeof(IEventBus)) as IEventBus; https://www.codenong.com/50411466/
此随笔或为自己所写、或为转载于网络。仅用于个人收集及备忘。
版权声明
本文仅代表作者观点,不代表xx立场。
本文系作者授权xx发表,未经许可,不得转载。
发表评论:
◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。