【问题标题】:Php unit testing, protected method with mockingPHP单元测试,带模拟的受保护方法
【发布时间】:2013-10-10 02:19:50
【问题描述】:

我是 TDD 新手。我被困在一些单元测试中...请看一下我的代码...提前谢谢...

class Parser{

    protected function _checkCurlExistence()
    {
        // Unable to to mock function_exists, thats why fallback with this method

        return function_exists('curl_version');
    }


    public function checkCurlExtension()
    {

        // I want to test 2 situations from this method...
        // 1. if curl extension exists
        // 2. or when curl extension does not exists...throw error

        if($this->_checkCurlExistence() === false){

            try{
                throw new CurlException(); //Some curl error handler exception class
            }catch(CurlException $error){
                exit($error->getCurlExtensionError());
            }

        }

        return true;
    }
}

想测试:

class ParserTest{

    /**
    * @expectedException CurlException
    */
    public function testCheckCurlExtensionDoesNotExists()
    {
        //Some testing code with mocking...
    }

    public function testCheckCurlExtensionExists()
    {
       //Some testing code with mocking..and assertion 

    }

}

我的问题/请求:

请您填写这些测试。我永远被困在这上面……无法继续我的 TDD 之旅。

一些步骤(您可以跳过这些行):

我已尽力自己解决此问题,但无法解决。有些步骤是..

我尝试了 phpunit 的原生 mockerypadraic/mockery (git)、codeception/aspect-mock (git) 来模拟 _checkCurlExistence() 两种情况的方法...我不确定我是否做得对...这就是为什么,不发布那些代码...

我尝试了 Reflection Api,通过 ma​​gic method __call()... 将受保护方法动态转换为公共方法以帮助模拟...

我也做了很多谷歌搜索。了解最佳实践是仅测试公共方法。但是我的公共方法依赖于受保护的方法......所以我该如何测试???

【问题讨论】:

  • 我更愿意通过 checkCurlExtension() 对其进行测试,我的意思是如果找不到扩展名,它会抛出异常。在您的测试用例中使用它。 F.e $this->setExpectedException("CurlException");你就完成了。那将是在您删除“exit()”函数之后。只是利用例外来发挥你的优势
  • 如果你想测试一个受保护/私有的方法,你可以用一个特殊的测试类来扩展这个类,公开这些方法?
  • 不应测试受保护/私有方法。

标签: php oop unit-testing mocking tdd


【解决方案1】:

找到了一种模拟 php 内置函数的方法 PHPUnit function mocker extension

所以我现在可以轻松测试这 2 个场景。

namespace 'myNameSpace';

class Parser{

    public function checkCurlExtension()
    {
        // I want to test 2 situations from this method...
        // 1. if curl extension exists
        // 2. or when curl extension does not exists...throw error

        if(function_exists('curl_version') === false){
            throw new CurlException(); //Some curl error handler exception class
        }

        return true;
    }


}

class ParserTest{

    private $parser;

    /**
    * @expectedException CurlException
    */
    public function testCheckCurlExtensionDoesNotExists()
    {
        $funcMocker = \PHPUnit_Extension_FunctionMocker::start($this, 'myNameSpace')
        ->mockFunction('function_exists')
        ->getMock();

        $funcMocker->expects($this->any())
        ->method('function_exists')            
        ->will($this->returnValue(false));

        $this->parser->checkCurlExtension(); 

    }

    public function testCheckCurlExtensionExists()
    {
       //we can do same here...please remember DRY...

    }
}

【讨论】:

    猜你喜欢
    • 2012-01-08
    • 1970-01-01
    • 2017-06-24
    • 2012-11-05
    • 1970-01-01
    • 1970-01-01
    • 2022-08-05
    • 1970-01-01
    相关资源
    最近更新 更多