如何在洋葱架构上实现服务和存储库?

时间:2012-05-04 03:47:40

标签: .net domain-driven-design ddd-repositories onion-architecture ddd-service

我一直在研究洋葱建筑几天。我知道依赖关系应始终走向中心,以及如何使用依赖注入来实现这一目标。但是我还有几个问题我还是想不通。

  1. 模型(或实体)可以引用存储库接口或服务接口吗?

    例如:Order实体通过DeliveryCity属性建立Oder.DeliveryZip关系,外键,但是唯一。要获得拉链城市,我必须致电ICityRepository.FindByZip(zip)

    我的模型中有以下代码

    class Order
    { 
        . . .
    
        [Inject]
        public ICityRepository CityRepository { get; set; }
    
        private City _dCity;
    
        public City DeliveryCity {
            get {
                if (_dCity == null)
                    _dCity = this.CityRepository.FindByZip(this.DeliveryZip);
    
                return _dCity;
            }
        }
        . . .
    }
    
  2. 上述代码会出现什么问题?它应该使用域名服务吗?

  3. 是否应在核心内部或基础架构层中定义域服务实现?

3 个答案:

答案 0 :(得分:5)

  

上述代码会出现什么问题?它应该使用域名服务吗?

这里要考虑两件事:

  1. ICityRepository不是Order的真正依赖,换句话说,Order不需要它的其他方法。真正的依赖是对象无法使用的东西。因此,您可能需要考虑将其作为参数传递给方法,例如“GetDeliveryCity”(有关详细信息,请参阅this)。

  2. 按邮政编码查找城市似乎不是订单的责任。对于订单为cohesive,它必须仅处理与订单相关的功能。您可能希望将此功能从订单类中删除。

  3.   

    域服务实现应该在核心内部还是在基础架构层中定义?

    如果这是真正的域服务(不是应用程序服务),则在核心内部。

答案 1 :(得分:5)

这是工厂适应领域的地方。 OrderFactory可以采用依赖关系,例如对IOrderRepository的依赖关系以及对ICityRepository的依赖关系。当工厂用于创建(或重组)Order实体时,工厂可以查找City并相应地设置Order属性。或者,正如herzmeister建议的那样,使用Lazy设置它,因此只在需要时才执行查找。

答案 2 :(得分:0)

  1. 怎么样

    private Lazy<City> _dCityLazy;
    
    public City DeliveryCity {
        get {
            return _dCityLazy.Value;
        }
    }
    

    您是否通过某种机制注入Lazy<City>

  2. 您可以在此示例中通过外部注射灵活决定。

  3. 我说这实际上取决于特定域名服务的用途和使用位置。