phpunit 测试套件的独立性

标签 php phpunit cruisecontrol

我正在 phpunit 中运行一系列测试,这些测试存在于单独的测试套件中,测试套件的列表由 phpunit 配置文件控制。当测试单独运行时(即不通过配置文件,因此一次测试套件)它们通过了,但是当一起运行时,我失败了。

经过仔细检查,问题是这些测试套件中的每一个都在框架中加载(通过 require_once),并且该框架根据 require_once 时的设置进行一些内部配置。看起来,在运行 phpunit 配置文件中单独列出的测试套件之间,各种事情仍然存在。在这种特殊情况下,框架已被视为已加载。

那么 - 有没有办法让 phpunit 独立执行一系列测试套件,即相当于一次在测试套件上运行 phpunit?(phpunit 由自动测试中的 cruisecontrol 触发机器和开发人员在提交之前在本地进行。)我尝试过诸如“--process-isolation”和“--no-globals-backup”之类的选项但没有成功。

一个说明问题的简单示例是“constant.php”文件:

<?php
if (defined('XYZZY')) define('TEST', 1);
else define('TEST', 2);

测试套件“TestOne.php”:

<?php
define('XYZZY', "");
require_once('constant.php');
class TestOne extends PHPUnit_Framework_TestCase
{
   public function testOne()
   {
      $this->assertEquals(TEST, 1);
   }
}

类似的测试套件“TestTwo.php”:

<?php
require_once('constant.php');
class TestTwo extends PHPUnit_Framework_TestCase
{
   public function testTwo()
   {
      $this->assertEquals(TEST, 2);
   }
}

和一个phpunit配置文件:

<phpunit>
  <testsuites>
    <testsuite name="First">
      <file>./TestOne.php</file>
    </testsuite>

    <testsuite name="Second">
      <file>./TestTwo.php</file>
    </testsuite>
  </testsuites>
</phpunit>

最佳答案

我正在尝试为您提供一些 --process-isolation 和无备份全局的工作示例。

希望您能够使您的测试与这些一起工作。如果不是,请给我留言,我会尽快回复您。

我已经用 3.4.15 测试了其中的大部分内容,并且都针对 HEAD(预计 3.5.x 也可以工作)

最简单的方法是:

<?php
class Test extends PHPUnit_Framework_TestCase
{
    public function testOne()
    {
        define('FOO', 'BAR');
        $this->assertEquals('BAR', FOO);
    }

    public function testTwo()
    {
        define('FOO', 'BAZ');
        $this->assertEquals('BAZ', FOO);
    }
}

并产生:

phpunit --process-isolation processTest.php

PHPUnit @package_version@ by Sebastian Bergmann.

..

Time: 0 seconds, Memory: 1.25Mb

OK (2 tests, 2 assertions)

因此,如果您将测试分组在测试套件中,或者您可以为每个测试用例运行设置(取决于它的成本),那么您可以使用一些简单的方法,例如:

<?php
class Test extends PHPUnit_Framework_TestCase
{
    public function setUp() 
    {
        // your bootstrap for testsuite X
        // Maybe put this in a baseclass for that suite ?
    }

    public function testOne()
    {
        $this->assertEquals('BAR', FOO);
    }

简而言之

确保在进入测试(和进程隔离)后运行设置代码

如果其他一切都失败了并且您/我们无法解决此问题:

随着runkit扩展(即使是 NEAR 生产也不安全,作为最后的手段使用)你可以调用像 runkit-constant-remove() 这样的函数


希望这对您有所帮助。如果没有:让我知道

关于phpunit 测试套件的独立性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/4679287/

相关文章:

php - 为什么我的 MySQL 全文搜索不起作用?

php - .ajax跨域和MySQL无法正常工作

svn - 使用 CruiseControl.net 时将参数传递给 svn

git - 在 post-update hook 中查找 Git 分支名称

svn - 当 svn 指向 url 时 CruiseControl修改集无法执行

php - LinkedIn 二级连接 API

php - ldap_bind 始终返回 true

rest - 如何为Slim Framework中内置的REST API编写单元测试?

php - 使用 Symfony DomCrawler 在选择输入中选择不可能的值

php - 参数计数错误 : Too few arguments to function phpunit