截至 2019 年,这里是进行 Laravel PHPunit 测试以使用内存数据库的方法。
为 Laravel / Lumen 测试设置 SQLite 内存
您必须具备以下条件:
- 数据库中所有表和字段的所有数据库迁移就像您通常对实际数据库所做的那样,请参阅Laravel 迁移官方文档 https://laravel.com/docs/5.8/migrations.
- Use the
RefreshDatabase
trait (DatabaseMigrations
Lumen 的特征)在你的 PHPUnit 测试类中(官方文档 https://laravel.com/docs/5.8/database-testing#resetting-the-database-after-each-test).
- 在您的中设置以下内容
config/database.php
文件输入connection
setion:
'testing' => [
'driver' => 'sqlite',
'database' => ':memory:',
],
- 在您的中设置以下行
phpunit.xml
文件输入<php>
部分:
<env name="DB_CONNECTION" value="testing"/>
因此,一旦您运行 PHPUnit 测试,PHPUnit 将读取phpunit.xml
, 更换.env
's DB_CONNECTION
变量与testing
。它将触发数据库配置testing
(这是内存中的sqlite DB)要使用的。
内存数据库与磁盘数据库的测试(根据我的经验)大约快 5-30 倍。大约 200 个 CRUD 测试的小型测试套件存在 30 倍的差异,所有测试都在六个表上运行数据库查询,其中一些表hasMany
and belongsToMany
枢轴关系。
每次测试刷新数据库
运行数据库迁移每次测试前都有一个干净的数据库 https://laravel.com/docs/6.x/database-testing#resetting-the-database-after-each-test将以下特征添加到测试类(Laravel)的顶部:
use Illuminate\Foundation\Testing\RefreshDatabase;
// ... then in the class body:
use RefreshDatabase;
对于流明它应该是 https://lumen.laravel.com/docs/6.x/testing#working-with-databases
use Laravel\Lumen\Testing\DatabaseMigrations;
// ...then
use DatabaseMigrations;
不要忘记使用模型工厂 https://laravel.com/docs/6.x/database-testing#writing-factories如果需要,用测试数据为数据库播种。
是的,迁移将在每次测试之前和之后运行,以便在测试完成后以干净的数据库开始和结束(如果您在磁盘数据库中植入一些数据并偶尔将测试切换到在其上运行而不是在内存数据库上运行)。
修复 SQLiteCannot add a NOT NULL column with default value NULL
error
现在您已经成功地为您的应用程序设置了内存数据库测试。当您尝试使用外键对某些相关表进行级联更改时,预计会出现上述错误。
如果您快速将测试切换到磁盘上的数据库(注释掉<env name="DB_CONNECTION" value="testing"/>
在你的phpunit.xml
文件)错误消失。切换回内存数据库后,检查磁盘数据库不为空。如果是这样运行migrate:refresh
and db:seed
(这里假设您已经提前准备好所需的数据库种子)artisan
.
默认情况下,SQLite 禁用外键。将以下代码片段添加到您的 PHPUnit 测试类中以解决此问题:
// At the file's top to import the DB facade
use Illuminate\Support\Facades\DB;
// In the setUp() method
parent::setUp();
if (DB::connection() instanceof \Illuminate\Database\SQLiteConnection) {
DB::statement(DB::raw('PRAGMA foreign_keys=on'));
}
See 详细的解释和更多、更好、不同解决方案在这里 https://stackoverflow.com/questions/31228950/laravel-5-1-enable-sqlite-foreign-key-constraints.
希望这足以澄清这个主题,以便顺利工作。