WPF,MVVM,ICommand和存储库

8
我有一个类似于以下展示的WPF应用程序: enter image description here viewmodel封装了model,通过INotifyChanged暴露给视图相关属性。视图也绑定到多个ICommand对象,用于处理由视图触发的某些行为。我有一个外部ICommand,其唯一目的是将模型保存到数据库中。
所有我所读到的都表明,视图或viewmodel都不应引用存储库。这就是命令3在viewmodel之外的原因。
我的问题有两个方面。首先,这是合理的架构吗?第二,将模型实例传递给命令3的好方法是什么?

Command 1Command 2在虚拟机中,而Command 3在虚拟机之外,这是怎么做到的呢?难道不是所有命令都是在各自的类中单独实现,然后作为虚拟机的属性‘添加’进去的吗?在这种情况下,一个命令如何在虚拟机中,而另一个命令却在虚拟机之外? - hyankov
2个回答

10

我个人认为,让ViewModel引用Repository没有问题。避免这样做将导致不必要的复杂性。

在MVVM中,ViewModel通常是位于Model之上的“粘合”层 - 而Repository是Model的一部分(它是特定领域数据/逻辑的一部分)。我在MVVM系列博客中展示了我个人对此的看法:

MVVM Diagram

让VM直接使用Repository通过将Command 3放入VM中可能比试图将其分离出来更加清晰。


我想对Reed所说的内容稍作补充:如果你愿意,你可以通过抽象化存储库的细节来使它们有所解耦。但是我同意,没有理由完全按照那张图表所示的方式将它们分开。 - Tim
@Tim 很好的观点。将存储库细节抽象化非常有用,但几乎是一个单独的问题(对于可测试性等非常有帮助)。 - Reed Copsey
我同意这有点是一个独立的问题,但我有些想知道是否这种抽象可能是导致 OP 听到他应该解耦它们的原因。只是想在他问之前回答“那么为什么 [谁] 说我应该这样做,如果我不需要呢?”这个问题! - Tim
@Tim 我认为你可能是对的。我发现很多时候,当人们谈论MVVM时,他们包含了许多并不真正属于MVVM的问题。大多数“框架”包括大量非常好和有用的代码,但实际上将关注点分离到核心架构模式之外。我认为这使得刚接触MVVM并试图理解它的人们感到非常困惑。 - Reed Copsey
谢谢,这是一个很好的答案。我们的存储库已经抽象成了自己的类。现在我明白为什么有人会说不要在视图模型中包含存储库“代码”(SQL语句等),而是包含对抽象化存储库类的引用。 - ConditionRacer

0
视图模型应该与业务层(领域对象+领域服务)通信,而不是直接与存储库通信。更进一步地,这种通信应该通过命令来完成。
所以你有:
视图 -> 视图模型 -> 命令 -> 领域对象/领域服务 -> 存储库
除非你正在开发一个非常简单的CRUD应用程序...

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