Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/unit-testing/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/arduino/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Unit testing 单元测试-我应该使用mock还是让私有方法更可见_Unit Testing_Mocking - Fatal编程技术网

Unit testing 单元测试-我应该使用mock还是让私有方法更可见

Unit testing 单元测试-我应该使用mock还是让私有方法更可见,unit-testing,mocking,Unit Testing,Mocking,我正在为我正在开发的应用程序的一个新模块寻找一些设计建议,特别是关于如何使设计可测试 问题很常见-从数据库加载一些数据,对数据运行一些操作,然后将结果保存到数据库中。应用程序中的大多数其他模块具有以下模式: private repo; //Set in constructor public void Run() { Stuff stuff = repo.LoadStuff() Result result = RunOperationsInPrivateMethod(stuff)

我正在为我正在开发的应用程序的一个新模块寻找一些设计建议,特别是关于如何使设计可测试

问题很常见-从数据库加载一些数据,对数据运行一些操作,然后将结果保存到数据库中。应用程序中的大多数其他模块具有以下模式:

private repo; //Set in constructor
public void Run() 
{
    Stuff stuff = repo.LoadStuff()
    Result result = RunOperationsInPrivateMethod(stuff); //private method
    repo.SaveResult(result);
}
为了测试这一点,我有两个选择:

  • 注入一个模拟回购协议,我可以用它返回一个东西并验证结果
  • 重构RunOperationsPrivate方法以保护访问,并测试 直接操作

  • 我是否错过了其他选择?人们的偏好是什么?

    一般来说,不要测试私有方法,而是考虑您的私有方法是否真的应该是另一个类的公共方法。也就是说,使用聚焦功能将对象分解为更小的对象

    也许跑步应该是个好主意

    private repo; //Set in constructor
    private IOperation operation; // injected in constructor or through dependency injection.
    public void Run() 
    {
        Stuff stuff = repo.LoadStuff()
        Result result = operation.Run(stuff); //private instance with public method
        repo.SaveResult(result);
    }
    
    然后Run将是一个operations类的公共方法

    class SecretOperation : IOperation
    {
       public void Run(Stuff stuff) { /* secret stuff */ }
    }
    

    然后,您也不必从数据库加载东西进行测试,只需在专注于测试SecretOperation的fixture中创建一个东西。现在您的单元测试可以更加集中。

    一般来说,不要测试私有方法,而是考虑您的私有方法是否真的应该是另一个类的公共方法。也就是说,使用聚焦功能将对象分解为更小的对象

    也许跑步应该是个好主意

    private repo; //Set in constructor
    private IOperation operation; // injected in constructor or through dependency injection.
    public void Run() 
    {
        Stuff stuff = repo.LoadStuff()
        Result result = operation.Run(stuff); //private instance with public method
        repo.SaveResult(result);
    }
    
    然后Run将是一个operations类的公共方法

    class SecretOperation : IOperation
    {
       public void Run(Stuff stuff) { /* secret stuff */ }
    }
    

    然后,您也不必从数据库加载东西进行测试,只需在专注于测试SecretOperation的fixture中创建一个东西。现在,您的单元测试可以更加专注。

    重构方法的可见性,以便您可以对其进行测试,这很有味道。如果您希望测试的行为是RunOperationsInPrivateMethod,那么是的,您应该模拟您的repo.refactoring方法的可见性,以便您可以测试它-这很难闻。如果您希望测试的行为是RunOperationsInPrivateMethod,那么是的,您应该模拟您的回购。那太好了,谢谢Keith。。这就是为什么单元测试会带来好的设计。只有一件事——IOOperation中的Run方法应该返回一个结果。但你知道这是对的;)太好了,谢谢你,基思。。这就是为什么单元测试会带来好的设计。只有一件事——IOOperation中的Run方法应该返回一个结果。但你知道这是对的;)