【问题标题】:Dependency Injection - Multiple projects依赖注入 - 多个项目
【发布时间】:2020-08-18 19:38:48
【问题描述】:

我正在创建一个 wep api,这是当前的结构:

API - The Web API  (.net core web api project)
DAL - DbContext and Entities  (.net core class library)
DTO - Data Transfert Objects - The classes I send to the client without sensible data (.net core class library) 
REPO - Contains de Interfaces and Repositories (.net core class library) 

有关信息,我拥有同一个项目的所有内容,并决定拆分为多个类库。
到目前为止我所做的:

  • 添加了每个项目之间的引用
  • 更新使用
  • 已将命名空间名称更改为正确的名称
  • 解决为 0 个错误

我认为我的问题与依赖注入有关,因为当我尝试从邮递员或浏览器访问控制器时,会发生此错误:

InvalidOperationException:验证服务描述符“ServiceType:FootballManager.REPO.ILeagueRepository Lifetime:Scoped ImplementationType:FootballManager.REPO.LeagueRepository”时出错:尝试激活“FootballManager”时无法解析“FootballManager.DAL.FootballManagerAPIContext”类型的服务.REPO.LeagueRepository'。

我的 Startup.cs 看起来像这样:

using FootballManager.REPO;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;

namespace FootballManager.API
{
    public class Startup
    {
        public Startup(IConfiguration configuration)
        {
            Configuration = configuration;
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {

            services.AddCors(options =>
            {
                options.AddDefaultPolicy(
                    builder =>
                    {
                        builder.AllowAnyOrigin().AllowAnyMethod().AllowAnyHeader();
                    });
            });

            services.AddControllers().AddNewtonsoftJson(options =>
                options.SerializerSettings.ReferenceLoopHandling = Newtonsoft.Json.ReferenceLoopHandling.Ignore
            );

            services.AddScoped<ILeagueRepository, LeagueRepository>();
            services.AddScoped<IMatchRepository, MatchRepository>();
            services.AddScoped<IPlayerRepository, PlayerRepository>();
            services.AddScoped<IRefereeRepository, RefereeRepository>();
            services.AddScoped<ITeamRepository, TeamRepository>();

        }

        public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
            }

            app.UseRouting();

            app.UseCors();

            app.UseAuthorization();

            app.UseEndpoints(endpoints =>
            {
                endpoints.MapControllers();
            });
        }
    }
}

这是我进行注入的控制器代码:

public class LeaguesController : ControllerBase
    {
        private readonly ILeagueRepository _repo;

        public LeaguesController(ILeagueRepository repo)
        {
            _repo = repo;
        }

        [HttpGet]
        public async Task<ActionResult<IEnumerable<LeagueDto>>> GetLeagues()
        {
            return await _repo.GetAll();
        }
    }

对于我的 DbContext 连接,我直接在 DAL 项目上做了这样的(我不认为问题出在这里):

public partial class FootballManagerAPIContext : DbContext
    {
        public FootballManagerAPIContext()
        {
        }

        protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
        {
            if (!optionsBuilder.IsConfigured)
            {
                optionsBuilder.UseSqlServer(@"Server =.\SQLEXPRESS; Database = FootballManagerAPI; Trusted_Connection = True;");
            }
        }
}

在网上和 stackoverflow 上几个小时后,我仍然找不到任何可行的解决方案...
我该如何解决这个错误以及为什么会出现这个错误?谢谢。

【问题讨论】:

    标签: c# asp.net-core .net-core dependency-injection asp.net-core-webapi


    【解决方案1】:

    您永远不会实例化您的 DbContext - 错误非常明确;

    无法解析“FootballManager.DAL.FootballManagerAPIContext”类型的服务

    你还需要在启动时注册你需要的DbContext包括配置

    【讨论】:

    • 真的,试过了,这对我有用:services.AddDbContext&lt;FootballManagerAPIContext&gt;();
    【解决方案2】:

    我无法将 cmets 添加到您的问题中,所以我将其留在这里:

    也许这是一个愚蠢的问题,但也许你忘记了:

    LeagueRepository 是否继承自 ILeagueRepository?

    【讨论】:

    • 是的:public class LeagueRepository : ILeagueRepository
    • 试试这个:var builder = new ContainerBuilder(); builder.RegisterType().As(); var container = builder.Build();
    【解决方案3】:

    我认为这会对您有所帮助。 查看这个视频,我在其中解释了如何使用 autofac 实现依赖注入。 https://studio.youtube.com/video/XvklkAj7qPg/edit

    我还建议您应该使用一次性数据库连接,在每种方法中连接和断开连接。所以不要对数据库上下文使用依赖注入。

    检查您是否注册了数据库上下文。 services.AddDbContext(options => options.UseSqlServer(Configuration["ConnectionStrings:DefaultConnection"]));

    在服务配置中我看不到它。

    谢谢, 利维乌

    【讨论】:

    • 我正在制作一个 Owin 不需要的简单项目。只是想弄清楚我的问题。
    • 我明白了,问题是依赖解析器不知道 FootballManagerAPIContext 是什么。
    猜你喜欢
    • 2017-07-23
    • 2020-11-09
    • 2020-12-20
    • 2020-03-14
    • 1970-01-01
    • 1970-01-01
    • 2016-03-04
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多