phpunit运行测试两次 - 获得两个答案.为什么?

Ian*_*Ian 5 php phpunit

这是我的phpunit测试文件

<?php // DemoTest - test to prove the point

function __autoload($className) {
    //  pick file up from current directory
    $f = $className.'.php'; 
    require_once $f;
}

class DemoTest extends PHPUnit_Framework_TestCase {
    // call same test twice - det different results 
    function test01() {
        $this->controller = new demo();
        ob_start();
        $this->controller->handleit();
        $result = ob_get_clean();  
        $expect = 'Actions is an array';
        $this->assertEquals($expect,$result);
    }

    function test02() {
        $this->test01();
    }
}
?>
Run Code Online (Sandbox Code Playgroud)

这是受测试的文件

<?php // demo.php
global $actions;
$actions=array('one','two','three');
class demo {
    function handleit() {
        global $actions;
        if (is_null($actions)) {
            print "Actions is null";
        } else {
            print('Actions is an array');
        }
    }
}
?>
Run Code Online (Sandbox Code Playgroud)

结果是第二次测试失败,因为$ actions为null.

我的问题是 - 为什么我不能为这两个测试得到相同的结果?

这是phpunit中的错误还是我对php的理解?

Ant*_*nna 3

PHPUnit 有一个名为“备份全局变量”的功能,如果打开,则在测试开始时会备份全局范围内的所有变量(由当前值组成快照),并且在每次测试完成后,这些值将被恢复再次恢复为原始值。您可以在这里阅读更多相关信息:http://sebastian-bergmann.de/archives/797-Global-Variables-and-PHPUnit.html#content

现在让我们看看您的测试套件。

  1. test01 已准备好
  2. 备份由所有全局变量组成(此时全局范围内的 $actions 尚未设置,因为代码尚未运行)
  3. test01 运行
  4. demo.php 被包含(感谢自动加载)并且 $actions 被设置在全局范围内
  5. 您的断言成功,因为 $actions 是在全局范围内设置的
  6. test01 已被拆除。全局变量返回到其原始值。全局范围内的 $actions此时被销毁,因为它是在测试内部设置的,在测试开始之前它不是全局状态的一部分
  7. test02 运行 .. 并失败,因为全局范围内没有 $actions。

直接解决您的问题:在 DemoTest.php 的开头包含 demo.php,这样 $actions 最终会在每次测试之前和之后备份和恢复的全局范围内结束。

长期修复:尽量避免使用全局变量。这只是坏习惯,总有比使用“global”的全局状态更好的解决方案。