代码之家  ›  专栏  ›  技术社区  ›  djdd87

在这个领域数据建模场景中,访问参考数据的正确方法是什么?

  •  2
  • djdd87  · 技术社区  · 14 年前

    初始警告 :不管怎样,我可能完全搞错了模式:

    public class Customer : KeyedObject
    {
    
       public Customer(int customerId)
       {
          _customerRepository.Load(this);
       }
    
       private ICustomerRepository _customerRepository = IoC.Resolve(..);  
       private ICustomerTypeRepository = _customerTypeRepository = IoC.Resolve(..);
    
       public virtual string CustomerName {get;set;}
       public virtual int CustomerTypeId [get;set;}
    
       public virtual string CustomerType
       {
          get
          {
             return _customerTypeRepository.Get(CustomerTypeId);
          }
       }
    
    }
    

    CustomerType由值对象表示:

    public class CustomerType : ValueObject
    {
       public virtual int CustomerTypeId {get;set;}
       public virtual string Description {get;set;}
    }
    

    当我有一个CustomerTypeId的customer对象时,这一切都很好。然而,当我想在MVC视图中填充一个DropDownList时,我正在为如何从iccustomertyperepostory中正确获取CustomerType值列表的概念而挣扎。

    这个 ICustomerTypeRepository

    public interface ICustomerTypeRepository
    {
       public CustomerType Get(int customerTypeId);
       public IEnumerable<CustomerType> GetList();
    }
    

    基本上,我想要的是能够打电话 ICustomerTypeRepository存储库 但是我认为最好将DAL(repository)层与控制器分开。我是不是把事情搞得太复杂了?

    这就是我的控制器目前的状况:

    public class CustomerController : ControllerBase
    { 
    
        private ICustomerTypeRepository _customerTypeRepository = IoC.Resolve(..);
    
        public ActionResult Index()
        {
           Customer customer = new Customer(customerId); 
           IEnumerable<CustomerType> customerTypeList = 
              _customerTypeRepository.GetList();
    
           CustomerFormModel model = new CustomerFormModel(customer);
           model.AddCustomerTypes(customerTypeList );
        }
    }
    

    这对我来说似乎是错误的,因为我在控制器和客户机中都有存储库。在我看来,CustomerType应该有一个分段的访问层是合乎逻辑的。即。 CustomerType.GetList() :

    public class CustomerType : ValueObject
    {
       // ... Previous Code
    
       private static ICustomerTypeRepository _customerTypeRepository = IoC.Resolve(..);
    
       public static IEnumerable<CustomerType> GetList()
       {
          _customerTypeRepository.GetList();
       }
    }
    

    暴露 CustomerType 对象通过 CustomerController ?

    2 回复  |  直到 14 年前
        1
  •  2
  •   Jay    14 年前

    我想这里有几件事要考虑。

    首先,如果您真的对域建模感兴趣,那么您应该不惜一切代价保持域实体本身不受横切关注,比如验证、IoC容器和持久性,尽管有活动记录模式。

    这意味着 Customer

    撇开领域建模不谈,我有点担心 IoC 变量初始值设定项中的服务定位器。您将失去捕获异常的机会,并且构造函数抛出的异常是出了名的难以调试(这些初始值设定项在第一个非静态构造函数中的任何代码之前运行)。

    使用静态网关/服务定位器代替注入依赖关系也会使类实际上不稳定(使用自动单元测试方法,也就是说--您可以进行集成和手动测试,但是测试失败不太可能让您轻易地找到零碎的部分--而不是单元测试,在那里你确切地知道你测试的是什么,因此什么是坏的)。

    而不是 客户 _customerRepository.Load(this) 在构造器中,应用程序通常使用存储库来获取实体,因此它从存储库返回,包括 CustomerType 财产。在这种情况下,这可能发生在 CustomerController .

    您指出您希望从包含 客户控制器 该接口的实现(或者在本例中,从IoC实现中获取实现),但是该存储库的实际实现可以存在于单独的层中(甚至可以是另一个程序集)。这是一种称为分离接口的模式。

    public class CustomerController : ControllerBase
    { 
         private ICustomerTypeRepository _customerTypeRepository;
         private ICustomerRepository _customerRepository;
    
         public CustomerController(ICustomerRepository customerRepository,
            ICustomerTypeRepository customerTypeRepository)
         {
            _customerRepository = customerRepository;
            _customerTypeRepository = customerTypeRepository;
         }
    
         public ActionResult Index()
         {
             Customer customer 
                 = _customerRepository.GetCustomerWithId(customerId); 
                 // from where does customerId come?
    
             IEnumerable<CustomerType> customerTypeList 
                 = _customerTypeRepository.GetTypes();
    
            . . .
    
         }
    }
    

    我会把所有对存储库的引用从 客户

        2
  •  0
  •   Tim Murphy    14 年前

    如何更改您的客户域模型以包含CustomerTypes的属性?这还可以避免每次调用CustomerType时都需要访问存储库。

    public class Customer : KeyedObject
    {
    
       public Customer(int customerId)
       {
          _customerRepository.Load(this);
    
          ICustomerTypeRepository _customerTypeRepository = IoC.Resolve(..);
          _customerTypes = _customerTypeRepository.GetList();
       }
    
       private ICustomerRepository _customerRepository = IoC.Resolve(..);  
    
       public virtual string CustomerName {get;set;}
       public virtual int CustomerTypeId {get;set;}
    
       public virtual string CustomerType
       {
          get
          {
             return _customerTypes.Find(CustomerTypeId);
          }
       }
    
       private IEnumerable<CustomerType> _customerTypes;
       public virtual IEnumerable<CustomerType> CustomerTypes
       {
          get
          {
              return _customerTypes
          }
       }
    }
    
    推荐文章