vtsmedia/paratest

PHP的并行测试


README

Build Status HHVM Status Scrutinizer Code Quality Packagist

ParaTest的目标是支持PHPUnit的并行测试。只要你编写了良好的PHPUnit测试,你就可以将paratest添加到项目中,并开始使用它而无需额外的引导或配置!

优点

为什么要在现有的并行测试运行程序中选择paratest

  • 代码覆盖率报告合并。在N个并行进程中运行测试,所有代码覆盖率输出将合并为一个报告。
  • 零配置。在composer安装后,使用vendor/bin/paratest -p4 path/to/tests运行。这就足够了!
  • 灵活。在单独的进程中隔离测试文件或利用WrapperRunner以实现更快的运行。

安装

Composer

要使用composer安装,请将以下内容添加到您的composer.json文件中

"require": {
    "brianium/paratest": "dev-master"
}

然后运行php composer.phar install

用法

安装后,二进制文件可以在vendor/bin/paratest中找到。用法如下

Usage:
 paratest [-p|--processes="..."] [-f|--functional] [--no-test-tokens] [-h|--help] [--coverage-clover="..."] [--coverage-html="..."] [--coverage-php="..."] [-m|--max-batch-size="..."] [--filter="..."] [--phpunit="..."] [--runner="..."] [--bootstrap="..."] [-c|--configuration="..."] [-g|--group="..."] [--exclude-group="..."] [--stop-on-failure] [--log-junit="..."] [--colors] [--testsuite[="..."]] [--path="..."] [path]

Arguments:
 path                  The path to a directory or file containing tests. (default: current directory)

Options:
 --processes (-p)      The number of test processes to run. (default: 5)
 --functional (-f)     Run methods instead of suites in separate processes.
 --no-test-tokens      Disable TEST_TOKEN environment variables. (default: variable is set)
 --help (-h)           Display this help message.
 --coverage-clover     Generate code coverage report in Clover XML format.
 --coverage-html       Generate code coverage report in HTML format.
 --coverage-php        Serialize PHP_CodeCoverage object to file.
 --max-batch-size (-m) Max batch size (only for functional mode). (default: 0)
 --filter              Filter (only for functional mode).
 --phpunit             The PHPUnit binary to execute. (default: vendor/bin/phpunit)
 --runner              Runner or WrapperRunner. (default: Runner)
 --bootstrap           The bootstrap file to be used by PHPUnit.
 --configuration (-c)  The PHPUnit configuration file to use.
 --group (-g)          Only runs tests from the specified group(s).
 --exclude-group       Don't run tests from the specified group(s).
 --stop-on-failure     Don't start any more processes after a failure.
 --log-junit           Log test execution in JUnit XML format to file.
 --colors              Displays a colored bar as a test result.
 --testsuite           Filter which testsuite to run
 --path                An alias for the path argument.

优化速度

为了充分利用paratest,您必须仔细调整参数。

  1. 使用-p调整进程数

    为了充分利用CPU核心,您应该每个核心至少有一个进程。更多的进程允许更好的资源使用,但请注意,每个进程都有自己的启动成本。

  2. 使用-f选项在测试用例-和测试方法-并行化之间进行选择

    如果您有少量测试用例(类)和许多运行时间较长的测试方法,您应使用-f选项启用功能模式,允许同一类的不同方法并行执行。请注意,默认是按测试用例并行化,以解决测试方法之间的依赖关系。请注意,在大多数项目中,使用-f可能会更慢,因为每个测试方法都需要单独引导。

  3. 如果可能,使用WrapperRunner

    PHPUnit的默认运行程序为每个测试用例(或功能模式中的方法)启动一个新的进程。这提供了最高的兼容性,但伴随着许多启动的进程和每个进程的引导成本。特别是当您的测试(如数据库设置)中存在缓慢的引导时,您应尝试使用--runner WrapperRunner的WrapperRunner。它为每个并行进程(-p)启动一个“工作”进程,执行一次引导,并重用这些进程以执行每个测试。这样,进程启动和引导的开销降至最低。

  4. 调整批处理最大大小--max-batch-size

    批处理大小将影响单个测试方法使用的原子测试的最大数量。如果一个方法没有数据提供者,一个原子测试将来自测试类中的一个测试方法;或者将只来自数据集中的一个条目。增加此值可以减少每个进程的开销,但在大多数情况下也会降低并行效率。减少此值可以增加每个进程的开销,但在大多数情况下也会提高并行效率。如果所有测试的数量小于最大批处理大小,则所有内容将在一个进程线程中处理,因此在这种情况下ParaTest是完全无用的。找到最有效的批处理大小的方法是使用不同的批处理大小值进行测试,并选择最佳。最大批处理大小为0表示不使用批处理分组,一个批处理等于所有方法测试(一个或所有来自数据提供者)。最大批处理大小为1表示每个批处理只包含数据提供者中的一个测试或一个方法(如果未使用数据提供者)。更大的最大批处理大小可以显著增加phpunit命令行长度,因此进程可能会失败。减少最大批处理大小可以缩短命令行长度。Windows的限制约为32k,Linux为2048k,Mac OS X为256k。

示例

示例假设您的测试位于./test/unit下。

# Run all unit tests in 8 parallel processes
vendor/bin/paratest -p8 test/unit
# Run all unit tests in 4 parallel processes with WrapperRunner and output html code coverage report to /tmp/coverage
# (Code coverage requires Xdebug to be installed)
vendor/bin/paratest -p8 --runner=WrapperRunner --coverage-html=/tmp/coverage test/unit

Windows

Windows用户请务必使用适当的批处理文件。

例如

vendor\bin\paratest.bat --phpunit vendor\bin\phpunit.bat ...

ParaTest假设使用PSR-0来加载测试。

为了方便,ParaTest的Windows版本使用79列模式,以防止在标准的80x25 Windows控制台中出现空白行。

PHPUnit Xml 配置支持

当运行PHPUnit测试时,ParaTest将通过--configuration开关自动将phpunit.xml或phpunit.xml.dist传递给phpunit运行器。ParaTest还允许手动指定配置路径。

ParaTest将依赖于phpunit的xml配置的testsuites节点来处理套件的加载。

以下phpunit配置文件用于ParaTest的测试用例。

<?xml version="1.0" encoding="UTF-8"?>
<phpunit backupGlobals="false"
         backupStaticAttributes="false"
         bootstrap="../bootstrap.php"
         colors="true"
         convertErrorsToExceptions="true"
         convertNoticesToExceptions="true"
         convertWarningsToExceptions="true"
         processIsolation="false"
         stopOnFailure="false"
         syntaxCheck="false"
        >
    <testsuites>
        <testsuite name="ParaTest Fixtures">
            <directory>./tests/</directory>
        </testsuite>
    </testsuites>
</phpunit>

测试令牌

TEST_TOKEN环境变量保证具有一个不同于其他当前正在运行的测试的值。这对于例如为每个测试使用不同的数据库非常有用。

if (getenv('TEST_TOKEN') !== false) {  // Using partest
    $dbname = 'testdb_' . getenv('TEST_TOKEN');
} else {
    $dbname = 'testdb';
}

对于贡献者:测试paratest本身

ParaTest的测试套件依赖于通过composer安装的PHPUnit。请确保在克隆后运行composer install

请注意,必须将php.ini指令display_errors设置为stderr才能运行测试套件。

要运行单元测试:vendor/bin/phpunit test/unit

要运行功能测试:vendor/bin/phpunit test/functional

您可以通过在项目目录中运行phpunit来一次性运行所有测试。vendor/bin/phpunit

ParaTest可以通过从bin目录运行来运行其自己的测试套件。bin/paratest

要查看ParaTest的实际使用示例,请查看示例