gpt4 book ai didi

c# - MVVM 和 IOC : Handling View Model's Class Invariants

转载 作者:IT王子 更新时间:2023-10-29 04:11:33 25 4
gpt4 key购买 nike

自从我开始使用 MVVM 以来,这是一个我一直在努力解决的问题,首先是在 WPF 中,现在是在 Silverlight 中。

我使用 IOC 容器来管理 View 和 View 模型的分辨率。 View 往往是非常基本的,具有默认的构造函数,但 ViewModel 倾向于访问真实的服务,所有这些都是它们构建所必需的。同样,我使用 IOC 容器进行解析,因此注入(inject)服务不是问题。

真正成为问题的是使用 IOC 将所需数据传递给 ViewModel。举一个简单的例子,考虑一个允许编辑客户的屏幕。除了它可能需要的任何服务之外,此屏幕的 ViewModel 还需要一个客户对象来显示/编辑客户数据。

在进行任何类型的(非 MVVM)库开发时,我认为通过构造函数传递类不变量是一个不可改变的规则。如果我需要针对类构建时间的上下文特定数据并且所讨论的类是容器管理的,我倾向于使用抽象工厂* 作为桥梁。在 MVVM 中,这似乎有些矫枉过正,因为大多数 ViewModel 将需要它们自己的工厂。

我尝试/考虑过的其他一些方法包括 (1) 初始化/加载方法,我在其中传递数据,这违反了通过构造函数强制类不变量的规则,(2) 通过容器传递数据作为参数覆盖 (Unity),以及 (3) 通过全局状态包传递数据 (ugh)。

有哪些替代方法可以将特定于上下文的数据从一个 ViewModel 传递到下一个?是否有任何 MVVM 框架解决了这个特定问题?

*这可能有其自身的问题,例如需要在调用 Container.Resolve() 或不让 ViewModel 容器管理之间做出选择。 CaSTLe Windsor 对此有一个很好的解决方案,但据我所知,其他框架都没有。

编辑:

我忘了补充:如果您正在执行“View First”MVVM,我列出的一些选项甚至是不可能的,除非您先将数据传递给 View,然后再传递给 ViewModel。

最佳答案

我不太确定问题出在哪里,所以我将使用一个简单而人为的示例。

假设您有一个 CustomerListViewModel,其中列出了每个客户的摘要。选择客户时,您希望显示 CustomerDetailViewModel。这可以采用客户 ID 或 ICustomer 类型,该类型先前在 CustomerListViewModel 中填充了客户详细信息(例如,取决于您要加载数据的时间) .

我认为您要问的是,如果 CustomerDetailViewModel 也将一系列服务作为您希望通过容器解析的依赖项(通常用于依赖链),会发生什么情况。

当您首先执行 View 模型时,您需要从 CustomerListViewModel 实例化 CustomerDetailViewModel,并且您希望通过容器执行此操作,以便依赖项是适当注入(inject)。

因此,正如您提到的,您通常会通过抽象工厂模式来执行此操作,例如 ICustomerDetailViewModelFactory,它作为服务传递给 CustomerListViewModel

这个工厂类型有一个 ICustomerDetailViewModel GetCustomerDetailViewModel(ICustomer customer) 方法。此工厂类型需要引用您的 IoC 容器。

GetCustomerDetailViewModel 工厂方法中解析 ICustomerDetailViewModel 时,您可以在容器上调用 Resolve 时指定希望用于 ICustomer 构造函数参数的值。

例如,Unity 有 parameter overrides ,并查看 here获得温莎城堡的支持。温莎城堡也有一个 typed factory facility ,这样您就不需要实现具体的工厂类型,只需实现抽象。

所以我会选择选项 2!我们使用 Caliburn.Micro,它解决了很多 MVVM 问题,但我不知道有任何框架可以解决这个问题。

关于c# - MVVM 和 IOC : Handling View Model's Class Invariants,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6267360/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com