0

我在这个模式上搜索了太多,我想我自己很困惑,所以你的意见将不胜感激。

如果我的小型应用程序有一个数据库,这将描述它:

  • 公司
    • 姓名
    • 地址
    • 模板文件路径
  • 部门
    • 姓名
    • 地址
    • 报告编号
  • 事故
    • 报告编号
    • 地点
    • 司机姓氏
    • 日期

基本上,我已经编写了一些代码,可以将我的模型对象序列化和反序列化为 JSON,但是这些代码是混乱且紧密耦合的。我想基本把这个抽象出来,所以以后决定用DB的时候,随着应用的增长,切换起来会比较容易。

现在,如果我要创建存储库(我假设它不会是一个),方法签名会是什么样子?我会使用任何接口吗?这是我开始做的事情:

IRepository<T>

  • Add(T Entity)
  • Delete(T Entity)
  • Update(T Entity)

ICustomerRepository : IRepository<Customer>

  • GetAllCustomers()
  • GetCustomerByName(string name)

IDepartmentRepository : IRepository<Department>

  • GetAllDepartments()
  • GetDepartmentByName(string name)

然后我开始想,我不会写 DRY 代码......客户和部门存储库基本上在做同样的事情,唯一的区别是方法名称和存储信息的实际数据库表或文件。我做对了吗?

从我一直在阅读的内容来看,存储库只是您实际存储的包装器。就像我使用 SQLite 一样,我会在存储库中建立连接,而我的常规代码只会处理 Customer 和 Department 类,对 SQL 连接或反序列化的方式一无所知,只知道存储库。

4

2 回答 2

0

一些想法:

  • Update()通常不在存储库级别处理,因为您通常希望一次将更改保存在整个实体图中,而不仅仅是一个。一种常见的处理方式是通过应用程序服务/用例级别的工作单元,这可能反过来利用 ORM 的更改跟踪器。

  • 是的,如果您想将不同的 Repository 实现注入到它们的消费者中,您将需要接口,例如测试中的模拟 Repositories。

  • 我喜欢做的是采用需求驱动的方法,而不是试图预先确定接口的层次结构。换句话说,当你发现你需要它们时创建存储库接口——当你意识到你需要与一个模拟存储库对话时,它可能是在单元测试中,它可能是在编写生产代码时。客户端代码使用存储库的方式将塑造您的界面,并且您将保证这些界面中的每一个都是有原因的。

于 2013-07-09T11:16:04.550 回答
0

设计明智,它看起来不错。在基本接口中保留非常通用的方法(例如,Insert/Delete/Update/GetById)并在实体特定接口中保留专门的函数是一种相当标准的方法。

干得好,我想说重要的部分是客户不需要知道除了接口之外的任何东西,所以只要让你的接口尽可能清晰地工作。设置接口后,您可以选择完全独立于客户端的存储库实现。

于 2013-07-06T07:03:18.783 回答