2017-06-12 58 views
1

使用Codeception为我们的自定义(使用Symfony组件和Doctrine)框架编写验收测试。我们有一套实用方法,由我们的Phpunit测试单独使用,用于创建各种要测试的实体。这包括用户和其他相关数据。MySQL上的数据库事务中的代码验收测试

对于我们的Codeception测试,我们希望利用这个功能,允许我们将自定义数据播种并在之后进行清理。在我们的单元测试中,这是由一个事务处理的。鉴于Codeception通过HTTP通过Phantomjs向我们的应用程序提出请求,它不能使用事务作为单独的数据库连接创建到测试所使用的连接(看起来这可能使用Dbh,但不支持这种连接由于MySQL不支持嵌套事务)。这样做的结果是验收测试可以播种数据,但除非数据持续存在,否则这些数据不会存在于外部请求中。

我能想到的唯一的其他解决方案是在测试套件运行之前触发数据库转储。将我们的测试数据保存到数据库,以便可以访问外部请求,然后在测试套件完成时恢复转储的数据库。尽管我们有一个非常大的数据库,但这会增加运行测试套件的大量开销。

我希望有其他选择可用,或其他我们可以尝试。 谢谢。

回答

1

总是有其他选择:)。

在我的情况下,使用转储是不可能的,因为我们也有一个非常大的数据库(1.2 GB的时候剥离到基本要素,> 250GB的实况)。 相反,我有一堆.sql文件,用于删除特定测试插入的任何记录。

我有一个类DbHelper具有该功能运行查询:

public function executeOnDatabase($path_to_sql_file) 
{ 
    $sql = file_get_contents($path_to_sql_file); 
    $dbh = $this->getModule('Db')->dbh; 
    $this->debugSection('Query', $sql); 
    $sth = $dbh->prepare($sql); 

    return $sth->execute(); 
} 

作品作为一种魅力,并没有更多的开销运行测试。

更新:

如果处理用户和他们相关的数据,它通常是很容易的目标,你需要删除所有记录。用户名和电子邮件很可能是唯一的,您可以使用它们来获取用户的id(自动增加主键)。该ID很可能用于相关表格中。 例如:

SET @user_id = (SELECT `id` FROM `users` WHERE `username` = 'rgsfdg'); 
SET @email = '[email protected]'; 
DELETE FROM `mail_queue` WHERE `send_to` = @email; 
DELETE FROM `user_settings` WHERE `user_id` = @user_id; 
DELETE FROM `users` WHERE `id` = @user_id; 
+0

如何跟踪需要删除的内容?从每个表中获取最大主键并删除id> stored_key? – robjmills

+0

我已更新答案,以显示如何定位需要删除的记录。 – sunomad