对实现通用服务的抽象 class 实现不同的具体化
Implement different concretions to an abstract class that implements a generic service
我有一个通用接口和一个通用 class 具有查询数据库的通用方法。
public interface IRepositoryBase<Entity> {
IEnumerable<TEntity> GetAll(Func<IQueryable<TEntity>, IncludableQueryable<TEntity, object>> include = null);
}
public class RepositoryBase<TEntity>
: IDisposable, IRepositoryBase<TEntity>
where TEntity : class
{
public IEnumerable<TEntity> GetAll(Func<IQueryable<TEntity>, IIncludableQueryable<TEntity, object>> include = null)
{
IQueryable<TEntity> query = _context.Set<TEntity>();
if (include != null)
query = include(query);
return query.ToList();
}
}
我还有几个我称之为 "services" 的 class 实体,它们具有业务逻辑并实现了另一个通用接口。
public interface IServiceBase<TEntity>
where TEntity : class
{
IEnumerable<TEntity> GetAll(Func<IQueryable<TEntity>, IIncludableQueryable<TEntity, object>> include = null);
}
public class ServiceBase<TEntity>
: IDisposable, IServiceBase<TEntity>
where TEntity : class
{
private readonly IRepositoryBase<TEntity>
_repository;
public ServiceBase(
IRepositoryBase<TEntity> repository)
{
_repository = repository;
}
public ServiceBase()
{
}
public IEnumerable<TEntity> GetAll(Func<IQueryable<TEntity>, IIncludableQueryable<TEntity, object>> include = null)
{
return _repository.GetAll(include);
}
}
public class PizzaService : ServiceBase<Piza>, IPizzaService
{
private readonly IPizzaRepository _pizzaRepository;
public PizzaService (IPizzaRepository pizzaRepository)
: base(pizzaRepository)
{
_pizzaRepository= pizzaRepository;
}
}
这样每个服务都有自己的方法访问自己的 table 加上 ServiceBase 中的方法。
有一个场景,我有 3 个具体的服务,比如 PizzaService,每个服务都查询自己的 table,代码非常相似,因为 table 和逻辑相似。
我想将这些具体服务重构为一个,仅更改方法参数和正在访问的存储库,以符合 DRY 和 ISP。
我目前拥有的:
public interface IStopRule
{
string DsTerm { get; set; }
bool ShouldDelete { get; set; }
}
public interface IExampleRuleStopWordsBase<TEntity> : IServiceBase<TEntity>
where TEntity : class
{
}
public abstract class ExampleRuleStopWordsBase
: ServiceBase<IStopRule>, IExampleRuleStopWordsBase<IStopRule>
{
private readonly IRepositoryBase<IStopRule> _repo;
public ExampleRuleStopWordsBase(IRepositoryBase<IStopRule> repo)
: base()
{
_repo = repo;
}
public virtual string ApplyRule(string input)
{
var terms = GetAll();
foreach (var item in terms)
{
string regexPattern = @"\b(" + item.DsTerm + @")\b";
if (item.ShouldDelete && Regex.Match(input, regexPattern, RegexOptions.IgnoreCase).Success)
input = input.Replace(item.DsTerm, string.Empty);
}
input = input.Trim();
return input;
}
}
public class PizzaService : ExampleRuleStopWordsBase, IImportRule
{
public PizzaService(IRepositoryBase<IStopRule> repo)
: base(repo)
{
}
public void ApplyRule(Pizza pizza)
{
base.ApplyRule(pizza.Name);
}
}
public class PizzaProducerService : ExampleRuleStopWordsBase, IImportRule
{
public PizzaProducerService(IRepositoryBase<IStopRule> repo)
: base(repo)
{
}
public void ApplyRule(Pizza pizza)
{
base.ApplyRule(pizza.Producer.Name);
}
}
但我无法弄清楚如何将正确的实体传递给 ImportRuleStopWordsBase 的构造函数以使其使用正确的存储库...
Obs:所有接口和服务实现都位于域层,而存储库的实现位于基础结构层。
如果我没看错的话,你好像在找.RegisterGeneric
。 类 的示例可能是:
var containerBuilder = new ContainerBuilder();
containerBuilder.RegisterType<PizzaService>();
containerBuilder.RegisterType<PizzaProducerService>();
containerBuilder.RegisterGeneric(typeof(RepositoryBase<>))
.As(typeof(IRepositoryBase<>));
var container = containerBuilder.Build();
using (var scope = container.BeginLifetimeScope())
{
var pizzaService = scope.Resolve<PizzaService>();
var pizzaProducerService = scope.Resolve<PizzaProducerService>();
}
我有一个通用接口和一个通用 class 具有查询数据库的通用方法。
public interface IRepositoryBase<Entity> {
IEnumerable<TEntity> GetAll(Func<IQueryable<TEntity>, IncludableQueryable<TEntity, object>> include = null);
}
public class RepositoryBase<TEntity>
: IDisposable, IRepositoryBase<TEntity>
where TEntity : class
{
public IEnumerable<TEntity> GetAll(Func<IQueryable<TEntity>, IIncludableQueryable<TEntity, object>> include = null)
{
IQueryable<TEntity> query = _context.Set<TEntity>();
if (include != null)
query = include(query);
return query.ToList();
}
}
我还有几个我称之为 "services" 的 class 实体,它们具有业务逻辑并实现了另一个通用接口。
public interface IServiceBase<TEntity>
where TEntity : class
{
IEnumerable<TEntity> GetAll(Func<IQueryable<TEntity>, IIncludableQueryable<TEntity, object>> include = null);
}
public class ServiceBase<TEntity>
: IDisposable, IServiceBase<TEntity>
where TEntity : class
{
private readonly IRepositoryBase<TEntity>
_repository;
public ServiceBase(
IRepositoryBase<TEntity> repository)
{
_repository = repository;
}
public ServiceBase()
{
}
public IEnumerable<TEntity> GetAll(Func<IQueryable<TEntity>, IIncludableQueryable<TEntity, object>> include = null)
{
return _repository.GetAll(include);
}
}
public class PizzaService : ServiceBase<Piza>, IPizzaService
{
private readonly IPizzaRepository _pizzaRepository;
public PizzaService (IPizzaRepository pizzaRepository)
: base(pizzaRepository)
{
_pizzaRepository= pizzaRepository;
}
}
这样每个服务都有自己的方法访问自己的 table 加上 ServiceBase 中的方法。
有一个场景,我有 3 个具体的服务,比如 PizzaService,每个服务都查询自己的 table,代码非常相似,因为 table 和逻辑相似。
我想将这些具体服务重构为一个,仅更改方法参数和正在访问的存储库,以符合 DRY 和 ISP。
我目前拥有的:
public interface IStopRule
{
string DsTerm { get; set; }
bool ShouldDelete { get; set; }
}
public interface IExampleRuleStopWordsBase<TEntity> : IServiceBase<TEntity>
where TEntity : class
{
}
public abstract class ExampleRuleStopWordsBase
: ServiceBase<IStopRule>, IExampleRuleStopWordsBase<IStopRule>
{
private readonly IRepositoryBase<IStopRule> _repo;
public ExampleRuleStopWordsBase(IRepositoryBase<IStopRule> repo)
: base()
{
_repo = repo;
}
public virtual string ApplyRule(string input)
{
var terms = GetAll();
foreach (var item in terms)
{
string regexPattern = @"\b(" + item.DsTerm + @")\b";
if (item.ShouldDelete && Regex.Match(input, regexPattern, RegexOptions.IgnoreCase).Success)
input = input.Replace(item.DsTerm, string.Empty);
}
input = input.Trim();
return input;
}
}
public class PizzaService : ExampleRuleStopWordsBase, IImportRule
{
public PizzaService(IRepositoryBase<IStopRule> repo)
: base(repo)
{
}
public void ApplyRule(Pizza pizza)
{
base.ApplyRule(pizza.Name);
}
}
public class PizzaProducerService : ExampleRuleStopWordsBase, IImportRule
{
public PizzaProducerService(IRepositoryBase<IStopRule> repo)
: base(repo)
{
}
public void ApplyRule(Pizza pizza)
{
base.ApplyRule(pizza.Producer.Name);
}
}
但我无法弄清楚如何将正确的实体传递给 ImportRuleStopWordsBase 的构造函数以使其使用正确的存储库...
Obs:所有接口和服务实现都位于域层,而存储库的实现位于基础结构层。
如果我没看错的话,你好像在找.RegisterGeneric
。 类 的示例可能是:
var containerBuilder = new ContainerBuilder();
containerBuilder.RegisterType<PizzaService>();
containerBuilder.RegisterType<PizzaProducerService>();
containerBuilder.RegisterGeneric(typeof(RepositoryBase<>))
.As(typeof(IRepositoryBase<>));
var container = containerBuilder.Build();
using (var scope = container.BeginLifetimeScope())
{
var pizzaService = scope.Resolve<PizzaService>();
var pizzaProducerService = scope.Resolve<PizzaProducerService>();
}