C# 向ViewModel添加扩展方法是否维护ViewModel规则?

C# 向ViewModel添加扩展方法是否维护ViewModel规则?,c#,wpf,database,mvvm,viewmodel,C#,Wpf,Database,Mvvm,Viewmodel,在我的ViewModel中有一些方法可以访问数据库连接。我知道这是不正确的,因为ViewModel不应该负责连接到数据库 因此,作为解决方案,我将一些方法作为扩展方法移动到另一个类中。即 Public static void (this MainViewModel viewModel){ viewModel.Textbox = "hello"; viewModel.Tables = GetDatabaseConnectionAndReturnTables(); //...// } 这真的是从v

在我的ViewModel中有一些方法可以访问数据库连接。我知道这是不正确的,因为ViewModel不应该负责连接到数据库

因此,作为解决方案,我将一些方法作为扩展方法移动到另一个类中。即

Public static void (this MainViewModel viewModel){
viewModel.Textbox = "hello";
viewModel.Tables = GetDatabaseConnectionAndReturnTables();
//...//
}
这真的是从viewmodel中获取数据库连接功能的一种方法吗?这是我能想出的唯一解决办法

谢谢

卢克

这真的是一种让数据库连接功能失效的方法吗 视图模型

简短回答:没有

答案不太长:扩展方法的目的是在源代码不可用、无法派生类或希望将它们添加到结构(结构不可继承…)时向类型添加方法

实际上,您正在将方法添加到视图模型中,就好像它们是作为直接类成员添加的一样。如果将它们实现为视图模型实例成员,或者使用扩展方法,那么就是在视图模型中实现方法

如果要有效地从视图模型中提取数据,应检查一些设计模式,如:

很难为您提供更多关于如何以问答形式实现真正的关注点分离的指导(我需要在这里写一本书),但我将开始学习更多关于这些设计模式的知识


另外,我还想看看什么是领域驱动设计。

走这条路可能会很奇怪。如果可以在扩展方法和在视图模型中嵌套函数之间进行选择,则最好选择后者

然而。。。这两种做法都很糟糕。你应该仔细阅读设计模式。使用
DAO
模式,可以隐藏数据库的详细信息,只公开
持久性
层的知识。然后,使用
存储库
模式,您可以公开允许您操作特定数据集的方法,而不必关心如何检索和/或存储该数据


然后使用将存储库注入到使用该数据执行特定任务的模型中。同样,您可以将该模型传递到视图模型中,视图模型只显示模型中可用的信息。

在MVVM中将数据访问排除在视图模型之外的一个重要原因是帮助进行测试。使用MVVM的一个巨大优势是使更多的代码可测试,而不依赖于视图。通过使视图模型调用成为扩展方法,您无法抽象出数据存储调用。这意味着当您进行单元测试时,数据库中必须始终有数据,随时可以查询。这也意味着当你的单元测试运行时,你的数据库将充满一堆垃圾数据。在编写集成测试时,您希望访问数据库,但在测试视图模型的功能时,则不希望访问数据库

将隐藏在接口后面的对服务或存储库的数据访问抽象出来,允许您测试代码,而无需处理与数据库的连接。你会创造或创造

这样,您的代码将执行以下操作:

private IMyRepository repository;
public MainWindowViewModel(IMyRepository repo)
{
    this.repository = repo;
}

public Task SaveObject(MyObject obj)
{
    return this.repository.Save(obj);
}
当您进行单元测试时,您只需向视图模型构造函数提供一个mock或false,并让它在这些构造函数上点击
save
方法即可

使用扩展方法仍然意味着与数据层紧密耦合。它可能被抽象到一个不同的文件中,但是您的视图模型仍然是紧密耦合的,因为您不能在不重新编写原始扩展方法的情况下交换数据访问


这样做的另一个好处是,如果其他视图模型需要请求数据,它们可以使用相同的方法。这样就不必将代码复制粘贴到每个可能需要它的视图模型的扩展方法中,也不必创建视图模型的实例来访问它的扩展方法来获取数据。视图模型通常仅限于一个视图,但它们提供的数据可用于n个视图。

DAO?这对我来说太过时了;P@Mat我部分同意。也许在更大的系统中,但作为一个垫脚石,它很好地引入了关注点和抽象的分离,而不必处理太多的层。为什么不应该呢?这应该取决于您的总体系统设计,而不是一些关于什么是和什么不是合适的mvvm的概念。