关于c#:MVC控制器对静态服务类的依赖性 – 可测性问题

MVC controller dependency on static service class — testability concern

我是新来的测试人员,正在研究在维护中对一些遗留代码进行单元测试。控制器是围绕静态服务调用来获取数据的。我不确定前进的最佳路径,但我正在考虑要么将静态类重组为实例类,要么深入研究可测试性方法。这个代码片段只是我一次又一次遇到的一个简单的例子。事先谢谢你的建议。StaticMedServiceHelper是一个静态类,有一个静态使用方法,使用wcf channelFactory等。顺便说一句,如果您有wcf/mvc/testing的良好学习资源,请告诉我。再次感谢。

1
2
3
4
5
6
7
8
9
10
11
12
public ActionResult Documents(DocumentsForRequirementViewModel model)
{
        staticMedServiceHelper<IMedService>.Use(proxy =>
        {
            var requirment = proxy.GetRequirementById(model.Id);
            var dtos = (IEnumerable<DocumentDTO>)requirement.GetType().GetProperty(model.PropertyName).GetValue(requirement, null);

            model.Documents = Mapper.Map(dtos, new List<DocumentViewModel>());
        });

        return PartialView(model);
}


我打破依赖关系的技巧很简单:对于静态,将它们包装在实例类中。

假设您有一个静态记录器(我在生产代码中确实看到过这一点,请记住)

1
2
3
4
5
6
7
8
9
10
11
12
13
public static class Logger
{
  public static void Log(string message)
  {
    //logging logic here..
  }
}

public ActionResult Documents(DocumentsForRequirementViewModel model)
{
  Logger.Log("GET action on Documents");
  //bla bla
}

在这种情况下,对记录器的静态实现的依赖性是明确的。

我们可以创建一个新的记录器:

1
2
3
4
5
6
7
public class LogWrapper
{
  public void Log(string message)
  {
    Logger.Log(message);
  }
}

在我们的代码中使用它:

1
2
3
4
5
public ActionResult Documents(DocumentsForRequirementViewModel model)
{
  LogWrapper logger = new LogWrapper();
  loggerr.Log("GET action on Documents");
}

注:

这只是一个简单的例子。通常,所有外部依赖项都首先是接口的,然后对于静态实现,只需创建一个实例包装器。

如果您是更复杂的依赖场景,那么您可以创建装饰器来帮助您从静态转换为实例,并将代码委托给静态实现。