Php 在套件中的每个测试之前运行安装程序代码
我有一个正在开发的Laravel 5应用程序,它有两套测试套件:Php 在套件中的每个测试之前运行安装程序代码,php,laravel,unit-testing,testing,laravel-5,Php,Laravel,Unit Testing,Testing,Laravel 5,我有一个正在开发的Laravel 5应用程序,它有两套测试套件:单元和功能。我在phpunit.xml中定义了这些: <testsuite name="Unit"> <directory>./tests/unit</directory> </testsuite> <testsuite name="Functional"> <directory>./tests/functional</directory&
单元
和功能
。我在phpunit.xml
中定义了这些:
<testsuite name="Unit">
<directory>./tests/unit</directory>
</testsuite>
<testsuite name="Functional">
<directory>./tests/functional</directory>
</testsuite>
/测试/单元
/测试/功能
为了使功能测试能够正确运行,它们需要有一个有效的数据库。这意味着在运行功能测试之前执行一些设置,以便迁移数据库
通常,我会在测试中使用DatabaseMigrations
特性,以确保在每次测试之前迁移数据库。不幸的是,这大大降低了我们的测试速度(我们有数百个)。我将测试切换到使用DatabaseTransactions
trait,这使它们运行得更快,但是现在在运行测试之前数据库没有迁移。如果我在项目的新克隆上运行测试套件,它会失败,因为我在运行功能测试套件之前没有迁移数据库
显而易见的解决方案是添加$this->artisan('migrate')
到tests/TestCase.php的setUp
方法。但这有两个问题:
这会导致在每次测试之前迁移数据库,这是我最初试图避免的
这也会在运行单元测试套件时尝试迁移数据库,这显然是不理想的
对于我来说,确保在运行任何测试之前迁移功能测试的数据库的最佳方法是什么,但仅针对功能测试?您可以创建一个从Laravel的TestCase继承的基本testClase类,并且只有您的functional
套件类可以继承新类,在新课程中添加以下内容:
/**
* Creates the application.
*
* @return \Illuminate\Foundation\Application
*/
public function createApplication()
{
return self::initialize();
}
private static $configurationApp = null;
public static function initialize(){
if(is_null(self::$configurationApp)){
$app = require __DIR__.'/../bootstrap/app.php';
$app->loadEnvironmentFrom('.env.testing');
$app->make(Illuminate\Contracts\Console\Kernel::class)->bootstrap();
if (config('database.default') == 'sqlite') {
$db = app()->make('db');
$db->connection()->getPdo()->exec("pragma foreign_keys=1");
}
Artisan::call('migrate');
Artisan::call('db:seed');
self::$configurationApp = $app;
return $app;
}
return self::$configurationApp;
}
public function tearDown()
{
if ($this->app) {
foreach ($this->beforeApplicationDestroyedCallbacks as $callback) {
call_user_func($callback);
}
}
$this->setUpHasRun = false;
if (property_exists($this, 'serverVariables')) {
$this->serverVariables = [];
}
if (class_exists('Mockery')) {
Mockery::close();
}
$this->afterApplicationCreatedCallbacks = [];
$this->beforeApplicationDestroyedCallbacks = [];
}
即使使用内存中的数据库,它的速度也要快100倍
PS:适用于Laravel而非流明应用。好主意。我最终创建了一个FunctionalTestCase,只有我的功能测试可以扩展,它负责所有数据库设置工作。谢谢