web-dev-qa-db-ja.com

サービス記述子の検証中にエラーが発生しました 'ServiceType:INewsRepository Lifetime:Singleton ImplementationType:NewsRepository':

リポジトリパターンでデータベースからデータを取得しようとしました。

Bmu.Mode「これはデータベースを作成するモデル用です」

Bmu.Repo「リポジトリには2つのフォルダが含まれ、contract/InewsRepository.csが含まれます」と「インターフェイスを実装するための「Repository/NewsRepository」」

Repoプロジェクトからデータを呼び出すためのBmu.Api

モデルプロジェクトのニュースクラス

namespace bmu.model
{
   public class News
   {
    public int Id { get; set; }

    public string SubTitle { get; set; }

    public string Title { get; set; }

    public string Summery { get; set; }
  }
}

モデルプロジェクトのコンテキストクラス

namespace bmu.model
 {
   public class BmuContext : DbContext
    {
       public BmuContext(DbContextOptions<BmuContext> options): base(options)
      {

      }
    public DbSet<News> News { get; set; }
   }
}

Repoプロジェクトの私のインターフェース

namespace bmu.repo.Contracts
{
  public interface INewsRepository
  {
    Task<IEnumerable<News>> GetAllAsync();
    Task<IEnumerable<News>> GetAllActiveAsync();
  }
}

bmu.repoにインターフェースを実装する

namespace bmu.repo.IRepository
{
 public class NewsRepository : INewsRepository
 {
    private readonly BmuContext _context;
    private readonly MemoryCache _memoryCache;

    public NewsRepository(BmuContext context, MemoryCache memoryCache)
    {
        _context = context;
        _memoryCache = memoryCache;
    }
    public async Task<IEnumerable<News>> GetAllAsync()
    {
        return await _context.News.ToListAsync(); 
    }
    public async Task<IEnumerable<News>> GetAllActiveAsync()
    {
      return   await _context.News.Where(x => x.Active).ToListAsync();
    }

}
}

また追加

services.AddControllers(); 
        services.AddSingleton<INewsRepository, NewsRepository>();

apiプロジェクトの起動時、これは私のコントローラーです

namespace bmu.api.Controllers
{
[ApiController]
[Route("[controller]")]
public class NewsController : ControllerBase
{
     private readonly ILogger<NewsController> _logger;
     private readonly INewsRepository _newsRepository;

    public NewsController(ILogger<NewsController> logger,INewsRepository newsRepository)
    {
        _logger = logger;
        _newsRepository = newsRepository; 
    }
    [HttpGet]
    public async Task<IEnumerable<News>> Get()
    {
        return await _newsRepository.GetAllActiveAsync();
    }
}
}

しかし、プロジェクトを実行すると、このエラーが発生しました

AggregateException:一部のサービスを構築できません(サービス記述子「ServiceType:bmu.repo.Contracts.INewsRepository Lifetime:Singleton ImplementationType:bmu.repo.IRepository.NewsRepository」の検証中にエラーが発生しました:タイプ「bmu。 'bmu.repo.IRepository.NewsRepository'をアクティブ化しようとしているときにmodel.BmuContext 'を返します。)

また、マルチプロジェクトのため、これでDbContextを追加します

UPDATE:

namespace bmu.model
{
public class BmuContextFactory : IDesignTimeDbContextFactory<BmuContext>
{
    public BmuContext CreateDbContext(string[] args)
    {
        var optionsBuilder = new DbContextOptionsBuilder<BmuContext>();
        optionsBuilder.UseSqlite("Data Source=bmu.db");

        return new BmuContext(optionsBuilder.Options);
    }
}
}

このエラーの解決策はありますか?

1
sunny

Sotiris Koukios-Panopoulosさんのコメントのように

Startup.csではなく、デザインタイムのオプションのみを設定しているようです。 services.AddDbContext(options => options.UseSqlite(your connection string));を期待しています。代わりに–

私の場合、startup.csにこれを設定するのを忘れていました

services.AddDbContext<myDbContext>(o => o.UseSqlServer(myConnectionString));

インターフェースサービスを使用しているため、これについて言及するのを忘れていました。

services.AddScoped<IMyTruckService, MyTruckService>();
0
rtfmpliz

まず、変更する必要があります。

services.AddSingleton<INewsRepository, NewsRepository>();

に:

services.AddTransient<INewsRepository, NewsRepository>();

次に、IMemoryCacheMemoryCacheではなくNewsRepositoryを挿入する必要があります。

以下は簡単なデモです。

1.Startup.cs:

public void ConfigureServices(IServiceCollection services)
{
    services.AddControllersWithViews();
    services.AddSession();
    services.AddTransient<INewsRepository, NewsRepository>();
    services.AddDbContext<BmuContext>(options =>
                options.UseSqlServer(Configuration.GetConnectionString("Connectionstring")));
    services.AddMemoryCache();
}

2.appsettings.json:

"ConnectionStrings": {
    "Connectionstring": "Server=(localdb)\\mssqllocaldb;Database=Bmu;Trusted_Connection=True;MultipleActiveResultSets=true"  
}

3.NewsRepository:

public class NewsRepository : INewsRepository
{
    private readonly BmuContext _context;
    private readonly IMemoryCache _memoryCache;

    public NewsRepository(BmuContext context, IMemoryCache memoryCache)
    {
        _context = context;
    }
    //...
}
0
Rena

APIにライフタイムタイプの不一致があります。 EntityFramework DbContextはスコープサービスであり、NewsRepositoryのシングルトンインスタンスを持つことはできません。リクエストごとに生成されるインスタンスに依存しているためです。

NewsRepositoryをスコープサービスとして使用するか、次のように依存関係の解決を再構築する必要がありますSO回答: se DbContext in ASP .Netシングルトン注入クラス