3

我正在尝试使用角色表、用户表和具有用户 ID、角色 ID 的外部参照表来实现用户身份验证和授权。

为了实现通用存储库来更新角色、插入角色、添加用户、将用户添加到角色、更新用户、更新用户角色、验证用户、将用户会话添加到审计等,我是否为每个函数编写了单独的函数,或者我可以使用一种通用方法对于类似的功能。还有一些其他操作,例如将用户加入其他表并根据条件获取前 5 行,使用单个表单插入 3 个表(在键上连接)等

我对阅读许多文章和示例感到困惑,我看到的 bcos 示例除了 CRUD 操作之外没有深入实施。

有人可以指导我或指导我找到一个好的样本/文章吗?

4

3 回答 3

7

首先,遵循弗兰克施维特曼所说的。让您的存储库随着使用量的增长而增长。此外,了解和使用 IQueryable 接口。L2S,以及实体框架、LINQ to nHibernate,以及一些较新的 ORM,如 SubSonic 和 Telerik 的 ORM,都支持 IQueryable 接口。

如果您需要来自存储库的可变查询,但仍希望在需要时交换 OR 映射器的好处,IQueryable 是一个强大的工具。假设如下:

public class ProductRepository: IProductRepository
{
    public Product GetByID(int id);
    public IList<Product> GetAll();
    public void Insert(Product product);
    public Product Update(Product product);
    public void Delete(Product product);
}

这是一个非常常见的存储库,具有基本的常用方法。随着时间的推移,你可能会得到更多的方法:

public IList<Product> GetByOrder(Order order);
public IList<Product> GetByCategory(Category category);
public IList<Product> GetByQuantityInStock(int quantityInStock);

这也很常见,并且取决于您喜欢如何解决问题,完全可以接受。但是,从长远来看,您的存储库可能会增长到难以处理的大小,并且其界面将始终在变化。您还失去了在幕后使用 OR 映射器的真正好处。

如果您更改一种方法,您可以保留原始的、简单的存储库界面,但仍为自己提供很大的灵活性:

public IQueryable<Product> GetAll();

您的存储库现在返回一个查询,而不是已检索对象的列表。您现在可以像使用任何其他启用了 LINQ 的对象一样自由使用此查询:

var productsWithLowStock = productRepository.GetAll().Where(p => p.Quantity < 10);

var orders = orderRepository.GetAll();
var productsWithOrders = productRepository.GetAll().Where(p => orders.OrderLines.Any(ol => ol.ProductID == p.ProductID));

一旦您开始在存储库中使用 IQueryable 接口,您将获得两全其美:围绕低级数据访问的可模拟抽象,以及代码中动态查询的强大功能。您可以更深入地了解这个概念,并创建一个实现 IQueryable 本身的基本 Repository 类,从而使您无需调用 GetAll() 并直接查询存储库(尽管复杂程度有所不同。)

于 2009-10-15T17:13:31.933 回答
1

理想情况下,您不应该猜测存储库的要求。一种方法是先编写使用存储库的代码,然后根据需要扩展存储库的接口。如果您编写为存储库提供测试替身的单元测试,这是可以实现的。

于 2009-10-15T16:56:26.337 回答
-2

linq2sql 是 ActiveRecord 模式的一种实现,它有点像反模式,所以如果你想使用存储库模式,那么你不能使用 linq2sql 而是其他可以分离关注点的东西(实体的单独类和数据访问的单独类)

或者也许你可以不知何故,我不知道:D

于 2009-10-15T16:56:51.800 回答