如何测试一个自称的方法?

时间:2015-12-22 18:27:10

标签: php unit-testing

鉴于此代码:

function testMe($a)
{
    if ($a)
    {
        return 1;
    }
    else
    {
        return $this->testMe(true);
    }
}

testMe()无法嘲笑,因为我无法称之为。另一方面,它必须被嘲笑......

1 个答案:

答案 0 :(得分:0)

我说你的问题具有一定的哲学潜力。我会尝试以你提出的方式回答它,但在此之前,请允许我评论你的理解:

  

testMe()无法嘲笑,因为我无法称之为。 另一方面,它必须被嘲笑...... [我的斜体]

未完成的句子是错误的。你可能已经感觉到它已经因为你没有完成它。在单元测试中,您不要模拟单元。所以你把单元放在测试中,单位是方法。这是可以测试的最小部分(单位)。

实际上可能产生一些混乱的是方法中的递归。

所以你实际上问的是如何在递归中对递归或单个方法调用进行单元测试。但你真的需要测试吗?

我会说不。这是因为递归是方法的实现细节。从外部来看,如果将内部算法从递归交换到基于堆栈的循环,它应该没有任何区别。

但是尽管我说你不需要它(我希望你已经理解了我所概述的论证),但技术上 可能对你的特定场景来测试这样的方法-call无需通过重新绑定$this重新编写测试代码。然后,您可以在调用时用模拟替换测试中的主题($this)。因此,您有两种方法:要测试的方法和可以通过$this->testMe()访问的模拟方法。

这可以通过实例化测试中的主题,创建一个模拟,使用PHP's reflection to obtain the closure of testMe()然后re-bind $this on the closure到模拟,然后调用闭包来测试断言。

我不再称之为单元测试,因为正如我之前所述,你正在测试内部/私有,因此你可以更多地使用它来实际测试在某些情况下递归的片段和其他类似的详细信息将更实际地证明/调试代码片段。在代码非常有价值的情况下,通常只在非常特殊的情况下需要它。

不要对递归使用你的小混淆,认为这是一个完全重要的地方来测试它自己。但是如果你想弄脏手指,那么学习PHP反射,闭包和重新绑定$this可能是值得的。