Winforms-MVP 和 WPF-MVVM 中通知最终用户异常的方法

7
在Winforms-MVP的半年时间里,我设计了以下异常处理策略。我有一个基础抽象Presenter类,其中包含几个以委托作为输入参数的Execute方法(签名不同)。视图和Presenter之间的交互是通过在IView中定义的事件(输入)和设置公共属性(输出)或调用IView中定义并由View实现的方法来完成的。Presenter中的每个事件处理程序都调用其中一个提供具体实现的Execute方法。
在执行方法中,我有几个catch块,用于可能发生的非常明确的异常(主要是由于广泛使用的外部组件存在一些问题)。每个这些异常都会停止当前操作的执行,并通过调用View的方法记录和向用户显示有意义的解释。
不久前(事实上非常不久之前),我开始学习WPF-MVVM,从第一眼看起来似乎与MVP有很多相似之处。我正在寻找关于异常处理策略的一些方便建议(主要是通知用户有关问题),但是这些问题通常很难搜索-我的意思是说,虽然有很多内容,但主要是原则性的。我已经找到了20多个关于在app.xaml.cs中“处理”未处理的异常的示例,这非常好,但是老实说-如果您知道可能崩溃应用程序的确切异常,您不会尽早处理它们吗(即使您将被迫关闭应用程序)?我绝不是抓取所有可能的异常的粉丝。由网络问题、暂时数据库不可用等引起的相当多的异常应该在不关闭应用程序并给普通用户重复请求的机会的情况下进行处理。
因此,作为一个实验,我尝试了几乎与我之前描述的相同的方法-我为ViewModel中的异常转换创建了事件,并订阅了View。但老实说,这种方式让我毛骨悚然。
(这是一个非常长的演讲,我知道)问题:在使用MVVM时如何处理异常以及通知用户?不,现在我对数据验证不感兴趣。任何关于MVP的批评和/或建议也受欢迎。

你关心的是哪一部分?是早期捕捉还是晚期捕捉?如果你没有早期捕捉,你认为这与WPF/MVVM有关吗? - Merlyn Morgan-Graham
2个回答

7
我们在Wpf应用程序中针对不同类型的错误条件有几种不同的策略。
对于代码可以处理并且可以在不通知用户的情况下继续进行的预期错误,我们使用常规的Try Catch块。
对于预期的但是从用户角度看会导致失败的错误,我们在ViewModels上公开了一个Notifications集合,该集合绑定到View上的ItemsControl,其模板类似于Firefox / IE / Chrome中的通知栏。每个通知都有一个显示持续时间属性(使用调度计时器自动修剪Notifications集合),以及视图中的关闭按钮,因此它们可以在特定时间内出现或可以由用户显式关闭。这种模型的好处是它可以用于完成消息、警告和异常,以及一些可能不表现为异常但从用户角度仍然是错误条件的情况。通知经常是消息框的良好替代品,因为它们不会中断用户的工作流程。
对于我们没有预料到的错误,我们使用Red Gate SmartAssembly来捕获完整的详细信息,以便用户可以将其发送给我们的支持团队进行分析。我们的观点是,在未预料到的异常之后捕获并继续运行您的应用程序是一种非常冒险的策略,因为未预料到的异常堆栈不会被解除,导致应用程序在错误之后处于不一致的状态(这可能导致任何奇怪的 UI 到数据损坏),并且可能会有无法预测的副作用。应用程序崩溃并不是一个好的用户体验,但由于应用程序忽略了错误而导致数据损坏的未预料状态,其体验要更糟糕得多。我们的策略是捕获有关崩溃的尽可能多的详细信息,以便用户知道我们认真对待问题,并且我们将在未来的更新中修复/捕获它 - 而不仅仅是继续前进并面临潜在的更严重的问题。

简洁明了的解释,概括了更具体的信息。 - Jake Berger
尽可能处理所有异常,对于那些你没有明确预料到的异常崩溃,并建立一个系统来“处理”它们。 - Marijn

1

我同意,在 app.xaml.cs 中留下异常处理不好,因为基本上为时已晚!

对于潜在异常较高的操作(例如文件处理,网络 IO),请确保您积极捕获异常。 我通过以下两种方式之一将其公开到视图中:

  1. 对于指示某些长期运行问题(例如网络问题)的错误,我会公开一个 'ErrorState' 属性
  2. 对于短暂问题,例如文件未找到,公开一个事件。

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