1

在 ASP.net MVC(不一定限于 MVC,只是一个例子)中,我们的 action 方法中总是有前置条件,类似于下面的:

[HttpPost]
public ActionResult Edit(FooModel viewModel)
{
    if (viewModel == null)
    {
        throw new ArugmentNullException("viewModel");
    }

    if (viewModel.Foo < 1)
    {
        throw new InvalidOperationException();
    }

    // Perform real tasks on viewModel (e.g. map it to model, persist to database)

}

现在我知道我们可以将检查重构为存储库类中的静态方法:

[HttpPost]
public ActionResult Edit(FooModel viewModel)
{
    if (FooModelRepostory.IsValid(viewModel)
    {
    }

    // Perform real tasks
}

FooModelRepository.cs

public static bool IsValid(FooModel viewModel)
{
    if (viewModel == null)
    {
        throw new ArgumentNullException("viewModel");
    }

    if (viewModel.Foo < 1)
    {
        throw new InvalidOperationException();
    }

    // ...many more checks and throw exceptions accordingly

    // if we reach up to here, we are good, return true
    return true;
}

我的问题是,我们有没有更好的方法来重构代码,而不用像这样的检查使存储库混乱?

4

2 回答 2

0

我没有更清楚地看到您已经提供了某些东西。Code Contracts是的,让你在程序中添加声明性行为,但也隐藏了清晰的逻辑。所以,就像任何事情一样,它有两个方面:好的和坏的。

我个人会选择您选择的解决方案,因此具有简单的控制方法。我想请您注意的唯一一件事是:

public static bool IsValid(FooModel viewModel)
{
 ...
}

returs bool,所以在失败/否定响应的情况下,我希望false/true值被返回而不是引发异常。这是程序的控制流,如此简单return truereturn false足够,并且可以从您的方法的使用者那里得到。

于 2013-11-05T07:43:37.700 回答
0

另一种选择是创建验证类。您只需将这些类的对象添加到列表中,并询问列表是否每个验证都有效。只是一些优点:

  • 相同的验证可以重复用于其他控制器。
  • 如果添加了验证,则现有代码保持不变(打开关闭/原则)
  • 单元测试验证更容易,因为您不必调用控制器来查看它是否有效
  • 如果您在验证中“查找所有参考”,您可以看到所有使用验证的控制器
  • 您可以稍后选择是否只需要一个布尔异常而不更改验证。

更多信息和示例: 在此处输入链接描述

于 2014-01-17T15:12:00.363 回答