从 Artisan 命令调用 PHPUnit 将忽略 XML 文件

Calling PHPUnit from Artisan command will ignore the XML File

我有一个我认为不常见的问题,但我会尽量解释清楚。我创建了一个简单的 artisan 命令来执行此操作

 /**
 * Execute the console command.
 */
public function handle()
{
    $this->info("==> Cleaning up reports and docs...");

    $command = new Process("rm -f tests/docs/* && rm -rf test/reports/*");
    $command->run();

    $this->warn("==> Reports and docs are clean");

    $this->info("==> Executing Tests Suite...");
    $command = new Process("vendor/bin/phpunit --coverage-html tests/reports --testdox-html tests/docs/reports.html -v --debug");
    $command->run();
    $this->info($command->getIncrementalOutput());

    $this->warn("==> report generated >> test/reports. Documentation generated >> test/docs/reports.html");
}

这看起来有点奇怪,但实际上非常有用,它启动了具有覆盖率支持和其他内容的 PHPUnit。问题是,如果我 运行 这个命令像 php artisan ludo237:full-test 它会完全忽略 phpunit.xml 事实上它会显示和错误说 MySQL 数据库不存在,甚至虽然我已经在我的 phpunit.xml 中设置了 sqlite 连接,但是你可以清楚地看到它是正确的:

<?xml version="1.0" encoding="UTF-8"?>
<phpunit backupGlobals="false"
         backupStaticAttributes="false"
         bootstrap="bootstrap/autoload.php"
         colors="true"
         convertErrorsToExceptions="true"
         convertNoticesToExceptions="true"
         convertWarningsToExceptions="true"
         processIsolation="false"
         stopOnFailure="false">
    <testsuites>
        <testsuite name="Application Test Suite">
            <directory suffix="Test.php">./tests</directory>
        </testsuite>
    </testsuites>
    <filter>
        <whitelist processUncoveredFilesFromWhitelist="true">
            <directory suffix=".php">./app</directory>
        </whitelist>
    </filter>
    <php>
        <env name="APP_ENV" value="testing"/>
        <env name="APP_DEBUG" value="true"/>
        <env name="APP_URL" value="http://localhost:8000"/>
        <env name="DB_CONNECTION" value="sqlite"/>
        <env name="DB_DATABASE" value=":memory:" />
        <env name="CACHE_DRIVER" value="array"/>
        <env name="SESSION_DRIVER" value="array"/>
        <env name="QUEUE_DRIVER" value="sync"/>
        <env name="MAIL_DRIVER" value="log"/>
        <env name="MAIL_PRETEND" value="true"/>
    </php>
</phpunit>

我知道我可以简单地为该命令行创建一个 bash 别名,事实上这是我当前的热修复,但此时我只是想知道为什么我启动 phpunit来自 artisan 命令的命令会忽略 XML 文件。

有人知道这件事吗?谢谢!

调试这个真的花了我很多时间,但最后我找到了为什么它不起作用。

首先,让我澄清一下,您的代码没有任何问题,即使 Process class 没有任何问题,即使使用本机 [=],您也会得到相同的行为11=]函数。

其次,phpunit.xml 文件完全被读取,完全没有问题。

说,真正的问题在于 PHPUnit 不允许您重新定义(或覆盖)任何环境变量,因为 there is a check that prevents that.

这是因为 Laravel 没有解析 phpunit.xml 文件本身,在你调用它的那一刻,已经太晚了 the environment variables are defined,要么通过 putenv, $_SERVER and/or $_ENV.

因此,I created an Issue on PHPUnit, which even in latest versions ( as of today ), this issue persist, even if this was already asked in the past

不幸的是,我还没有适合您的解决方案,但让我们祈祷吧,让我们等待 PHPUnit 添加建议的 force 属性 :)

此致, 朱利安