Android 清洁架构及相关实体

3
这主要是一个设计问题。我有两个实体PaymentUser,它们之间是一对一的关系。API调用返回一个Payments列表,每个Payment都包含一个User。这些支付信息在Recycler View中显示,每一行都包含来自PaymentUser实体的信息。为了从DB(使用Room)获取它们,我需要执行联接查询,返回两个实体的组合:
@Query("SELECT payment.*, user.* FROM payment INNER JOIN user ON payment.user_id = user.userId")
fun findPaymentsAndUsers(): List<PaymentAndUser>

data class PaymentAndUser(
    @Embedded val payment: Payment,
    @Embedded val user: User)

我的问题是如何在不违反任何 Clean Architecture 原则的情况下创建我的存储库?
  • 当然,我不能创建 2 个独立的存储库,并通过调用 UseCase 在它们之间传递数据,因为它们已经在 API 调用或 Room DAO 查询中一起返回。
  • 单一职责原则 指出每个存储库只能处理自己的实体,因此我不能创建一个 PaymentRepository 并从那里处理所有内容。
  • 我也不能将两个实体分组到一个 Aggregate 中,并创建一个处理它们两个的存储库,因为它们是两个独立的实体,可以相互独立存在。

我找到的每个 Android Clean Architecture 示例都有一个或两个完全独立的实体,没有联接查询或任何形式的分组,这在现实生活应用程序中是完全不切实际的。

有没有办法正确实现这个?


你在项目中使用Interactors吗? - Onik
是的,这就是我所说的“使用案例”。 - wise.potato
我会这样做。创建一个复合 UseCase,其中包括通过第一个 UseCase 检索到的 Payments 中的 Ids 获取 Payments 和获取 Users 的 UseCase。这样做,您的 Presenter 仅依赖于复合 UseCase。 - Onik
请纠正我,但是当您创建用例时,应该考虑业务交易,而不是CRUD方法。因此,在您的建议中,我们有3个用例,其中2个永远不会被任何其他Presenter或用例使用,并且如果例如API响应被修改,则很可能变得无用。我开始认为问题的根源是存储库模式本身。 - wise.potato
1个回答

2
根据我的理解,SRP并不是说每个仓库只应处理其自己的实体 - 相反,每个仓库只应有“一个被更改的原因”。
应该解决您问题的模式是“工作单元”模式:只需创建一个“工作单元”仓库,确切地处理此查询。
事实上,在他的书“干净架构”中,Uncle Bob指出,仓库接口应设计为方便其用户。它应该对用例提出的每个查询都有一个方法来响应仓库。
最初的回答。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接