C# 通用存储库工厂和服务组合
在《老乡帮我解决了存储库生存期问题》一书中,现在有一个问题是如何使它在组合服务中很好地工作 假设我有服务:C# 通用存储库工厂和服务组合,c#,castle-windsor,ioc-container,C#,Castle Windsor,Ioc Container,在《老乡帮我解决了存储库生存期问题》一书中,现在有一个问题是如何使它在组合服务中很好地工作 假设我有服务: public class OrderService : IOrderService { IRepository<Order> orderRepository; public OrderService(IRepositoryFactory repositoryFactory) { order
public class OrderService : IOrderService
{
IRepository<Order> orderRepository;
public OrderService(IRepositoryFactory repositoryFactory)
{
orderRepository = repositoryFactory.GetRepository<Order>();
}
public void CreateOrder(OrderData orderData)
{
...
orderRepository.SubmitChanges();
}
}
public class ReservationService : IReservationService
{
IRepository<Reservation> reservationRepository;
public ReservationService(IRepositoryFactory repositoryFactory)
{
reservationRepository = repositoryFactory.GetRepository<Reservation>();
}
public void MakeReservations(OrderData orderData)
{
...
reservationService.SubmitChanges();
}
}
问题是,如果IRepositoryFactory的生活方式是暂时的,它将无法正常工作(因为您将获得两个不同的数据上下文,这将需要启用分布式事务,我们试图避免这种情况)。你知道如何正确地写这篇文章吗?我的观察:
在我看来,这些都像是围绕一个更基本的问题(在你的第一个问题中描述)的变通办法,这些变通办法只会使问题变得更复杂。除非您解决了根本问题,否则最终将得到一个复杂的依赖关系模式和一个难闻的代码。IMO-这是一个分布式事务场景 在您提到的示例中,
OrderService
&ReservationService
使用相同的数据上下文是隐藏在代码中的实现细节
我认为,通过将服务调用包装到TransactionScope中,将这一知识传递给CompositionService
是不正确的,因为现在合成服务知道共享数据上下文&因此需要使用TransactionScope来正确运行代码
在我看来,组合服务代码应该如下所示:
try{
if(orderService.TryCreateOrder(orderData)){
if(reservationService.TryMakeReservation(orderData)){
reservationService.Commit();
orderService.Commit();
}
else{
orderService.TryRollbackOrder(orderData);
throw new ReservationCouldNotBeMadeException();
}
}
else{
throw new OrderCouldNotBeCreatedException();
}
}
catch(CouldNotRollbackOrderServiceException){
// do something here...
}
catch(CouldNotCommitServiceException){
// do something here...
}
在这种情况下,OrderService.TryCreateOrder方法将插入一个具有Pendingrervation状态或其他相关状态的订单,该状态指示该订单已插入,但尚未完成。在服务上调用提交时,此状态将更改(UnitOfWork模式?)
在这种情况下,服务的实现细节对服务的使用者完全隐藏,而组合也是可能的,独立于底层的实现细节
所以问题是如何解决根本问题?不敢相信,以前没有人面对过这个问题。
try{
if(orderService.TryCreateOrder(orderData)){
if(reservationService.TryMakeReservation(orderData)){
reservationService.Commit();
orderService.Commit();
}
else{
orderService.TryRollbackOrder(orderData);
throw new ReservationCouldNotBeMadeException();
}
}
else{
throw new OrderCouldNotBeCreatedException();
}
}
catch(CouldNotRollbackOrderServiceException){
// do something here...
}
catch(CouldNotCommitServiceException){
// do something here...
}