2

我正在创建一个示例应用程序以一起了解存储库和工厂方法模式,因为将在更大的项目中使用。

我想要实现的是能够使网站使用不同的 ORM 工具。

例如,网站将实现 LINQ to SQL 和 Ado 实体框架工作类,然后使用工厂方法将使用这些 ORM 之一“使用配置值”将数据加载到存储库对象中。

到目前为止我得到的是如下

interface IRepository : IDisposable
{
  IQueryable GetAll();  
}

interface ICustomer : IRepository
{
}

public class CustomerLINQRepository : ICustomer
{
    public IQueryable GetAll()
    {
       // get all implementation using linqToSql
    }
    public void Dispose()
    {
      throw;
    }
    public IRepository GetObject()
    {
        return this;
    }
}


public class CustomerADORepository : ICustomer
{
    public IQueryable GetAll()
    {
       // get all implementation using ADO
    }
    public void Dispose()
    {
      throw new NotImplementedException();
    }
    public IRepository GetObject()
    {
        return this;
    }
}


// Filling a grid with data in a page
IRepository customers = GetCustomerObject();
this.GridView1.DataSource = customers.GetAll();
this.GridView1.DataBind();
////

public IRepository GetCustomerObject()
{
    return new CustomerLINQRepository(); // this will return object based on a config value later
}

但我能感觉到有很多设计错误希望你能帮助我找出更好的设计。

4

3 回答 3

4

我的两分钱:

A. 我会添加通用基础存储库类。无论类型是什么,许多存储库操作都是相同的。它可以为您节省大量打字。

B. 我不明白您的存储库为什么要实现 ICustomer 接口。您的数据对象的接口是一个很好的做法,但我认为您的存储库不应该实现它。

C. 如果您的数据对象有一个通用实现,我将为它们创建一个基类,并将存储库限制为仅与该类型的派生类一起使用。

我会做这样的事情:

public interface IEntity
{
     // Common to all Data Objects
}

public interface ICustomer : IEntity
{
     // Specific data for a customer
}


public interface IRepository<T, TID> : IDisposable where T : IEntity
{
     T Get(TID key);
     IList<T> GetAll();
     void Save (T entity);
     T Update (T entity);

     // Common data will be added here
}

public class Repository<T, TID> : IRepository<T, TID>
{
     // Implementation of the generic repository
}

public interface ICustomerRepository
{
     // Specific operations for the customers repository
}

public class CustomerRepository : Repository<ICustomer, int>, ICustomerRepository
{
     // Implementation of the specific customers repository
}

用法:

CustomerRepository repository = new CustomerRepository();
IList<ICustomer> customers = repository.GetAll();
// Do whatever you want with the list of customers

这就是我使用 NHibernate 实现 DAL 的方式。您可以在“NHibernate in Action”中找到这种用法的一些变化。

我还建议使用 Matt 建议的某种 IoC 控制器。

于 2009-09-29T05:21:01.340 回答
1

我不确定GetWanted. 你到底想要什么?这个名字应该更具描述性,也许GetCustomerRepository

GetCustomerObject一样的GetWanted吗?

throw为了什么?

于 2009-09-29T03:38:04.900 回答
1

大部分看起来都不错。我有两个意见:

  1. 我不会调用您的客户存储库 ICustomer。我将其称为 ICustomerRepository。这更直接,并且澄清了接口的基于存储库的责任。ICustomer 听起来像是封装了客户数据的 DataObject。
  2. 考虑使用 IOC 容器(谷歌结构图、城堡温莎或统一)而不是使用工厂方法。你最终可能会得到很多可能导致混乱的工厂方法。相反,在你的代码中有一个地方,你的 IOC 连接你的所有存储库可能会更干净。
于 2009-09-29T03:51:03.057 回答