When i try to run the app i get:
System.AggregateException: 'Some services are not able to be constructed (Error while validating the service descriptor 'ServiceType: ProductManager.Core.ServiceContracts.IProductAdderService Lifetime: Scoped ImplementationType: ProductManager.Core.Services.ProductAdderService': Unable to resolve service for type 'ProductManager.Core.Domain.RepositoryContracts.IProductRepository' while attempting to activate 'ProductManager.Core.Services.ProductAdderService'.)'
the service interface:
using ProductManager.Core.DTO;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ProductManager.Core.ServiceContracts
{
public interface IProductAdderService
{
Task<ProductAddResponse> AddProduct(ProductAddRequest? productAddRequest);
}
}
the service:
using ProductManager.Core.Domain.Entities;
using ProductManager.Core.Domain.RepositoryContracts;
using ProductManager.Core.DTO;
using ProductManager.Core.ServiceContracts;
using System;
using System.Collections.Generic;
using System.Diagnostics.Metrics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ProductManager.Core.Services
{
public class ProductAdderService : IProductAdderService
{
// private field
private readonly IProductRepository _productRepository;
// constructor
public ProductAdderService(IProductRepository productRepository) {
_productRepository = productRepository;
}
// method
public async Task<ProductAddResponse> AddProduct(ProductAddRequest? productAddRequest)
{
if (productAddRequest == null)
{
throw new ArgumentNullException(nameof(productAddRequest));
}
/* //Validation: CountryName can't be null
if (productAddRequest.CountryName == null)
{
throw new ArgumentException(nameof(productAddRequest.CountryName));
}*/
//Validation: CountryName can't be duplicate
/* if (await _countriesRepository.GetCountryByCountryName(countryAddRequest.CountryName) != null)
{
throw new ArgumentException("Given country name already exists");
}*/
//Convert object from CountryAddRequest to Country type
Product product = productAddRequest.ToProduct();
//generate CountryID
product.ProductId = Guid.NewGuid();
//Add country object into _countries
await _productRepository.AddPerson(product);
return product.ToProductResponse();
}
}
}
they are inside the .Core class library
;
Then inside the .Infrastructure
folder i have repository:
using ProductManager.Core.Domain.Entities;
using ProductManager.Core.Domain.RepositoryContracts;
using ProductsManager.Infrastructure;
using System;
using System.Collections.Generic;
using System.Diagnostics.Metrics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace UserManager.Infrastructure.Repositories
{
internal class ProductRepository : IProductRepository
{
// db context
private readonly EntityDbContext _db;
// constructor
public ProductRepository(EntityDbContext db)
{
_db = db;
}
// methods
public async Task<Product> AddPerson(Product product)
{
_db.Products.Add(product);
await _db.SaveChangesAsync();
return product;
}
public Task<List<Product>> GetAllProducts()
{
throw new NotImplementedException();
}
public Task<Product?> GetCountryByProductID(Guid productID)
{
throw new NotImplementedException();
}
public Task<Product?> GetProductByCountryName(string productName)
{
throw new NotImplementedException();
}
}
}
that implements a interface from .Core library class
using ProductManager.Core.Domain.Entities;
using System;
using System.Collections.Generic;
using System.Diagnostics.Metrics;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ProductManager.Core.Domain.RepositoryContracts
{
public interface IProductRepository
{
Task<Product> AddPerson(Product product);
Task<List<Product>> GetAllProducts();
Task<Product?> GetCountryByProductID(Guid productID);
Task<Product?> GetProductByCountryName(string productName);
}
}
And the program.cs inside the .UI
using Microsoft.EntityFrameworkCore;
using ProductManager.Core.Domain.RepositoryContracts;
using ProductManager.Core.ServiceContracts;
using ProductManager.Core.Services;
using ProductsManager.Infrastructure;
var builder = WebApplication.CreateBuilder(args);
// Adding Entity Framework
builder.Services.AddDbContext<EntityDbContext>(options => {
options.UseSqlServer(builder.Configuration.GetConnectionString("DefaultConnection"));
});
//
builder.Services.AddControllers();
// Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle
builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen();
//
var app = builder.Build();
// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment())
{
app.UseSwagger();
app.UseSwaggerUI();
}
app.UseHttpsRedirection();
app.UseAuthorization();
app.MapControllers();
app.Run();
I have a project refernce to
from UI to Infrascture and Core
from Infrastructure to Core
I’m following:
https://github.com/Harsha-Global/AspNetCore-Harsha/tree/main/23.%20Clean%20Architecture
and i dont really undestand why i get this error.
In the role project,
there’s no builder.Services.AddScoped...
or there’s no:
builder.Services.AddScoped<IProductRepository, ProductRepository>();
builder.Services.AddScoped<IProductAdderService, ProductAdderService>();
but still works…
so maybe the problem is with DI? Or with project references?