+测试编辑数据库的artisan命令

时间:2015-04-17 16:18:07

标签: php database laravel codeception artisan

我正在尝试测试用于执行某些数据库维护的artisan命令。

特别是,它会搜索没有填充列的记录,并填充它。

这是命令的fire()方法的简化版本:

public function fire()
{
    $items = Item::all();

    $total = $items->count();
    $updated = 0;

    foreach ($items as $item) {
        if ($item->myColumn != 'x') {
            $item->myColumn = 'x';
            $item->save();

            $updated++;
        }
    }

    $this->info("total: $total updated: $updated");
}

我的(接受)测试非常简单,并且执行以下操作:

  • 在db
  • 中插入记录
  • 调用artisan命令
  • 检查插入的记录是否已更新

这是代码:

public function doTheTest(AcceptanceTester $I)
{
    $I->wantTo('setup the myColumn when it is not set');

    $id = $I->haveRecord('items', [
        'myColumn' => '',
    ]);

    $I->runShellCommand('php artisan items:updater');

    $I->seeRecord('items', [
        'id'       => $id,
        'myColumn' => 'x',
    ]);
}

然而测试失败,我得到以下消息:

Couldn't see record "items",{"id":101,"myColumn":"x"}:
Couldn't find items with {"id":101,"code":"x"}

如您所见,新记录的id为101,因为db转储中已有100个项目,但奇怪的是命令中的$this->info()打印< / p>

total: 100 updated: 100

好像测试中使用的数据库和artisan内使用的数据库不同。

此外,如果在测试结束时我尝试抓取添加的记录并打印出来,如下面的代码段所示

public function doTheTest(AcceptanceTester $I)
{
    /* ... */

    $item = $I->grabRecord('items', [
        'id'       => $id,
    ]);

    \Codeception\Util\Debug::debug($item);
}

并运行codecept run acceptance --debug命令,我得到添加的记录

stdClass Object
(
    [id] => 101
    [myColumn] =>
)

我很困惑,因为有一个数据库,但我肯定误解了一些重要的事情。

有人能给我一个帮助吗?

非常感谢,

1 个答案:

答案 0 :(得分:1)

问题是每个使用Laravel4模块的查询都在一个事务中运行,默认情况下,该事务将在最后回滚。如果您查看Laravel4文档的Config部分,请说明

  

cleanup:boolean,默认为true - 所有数据库查询都将在事务中运行,并将在测试结束时回滚。

如果你重新启动MySQL服务器,你可以检查一下(在这种情况下,当你再次运行测试时,你仍然会看到id 101),或者看一下将有如下条目的MySQL日志每个测试:

  

150417 23:24:24 2在laravel-test上连接root @ localhost               2准备集名称'utf8'collat​​e'utf8_unicode_ci'
              2执行set names'utf8'collat​​e'utf8_unicode_ci'
              2关闭stmt
              2查询START TRANSACTION
              2准备插入itemsmyColumn)值(?)
              2执行插入itemsmyColumn)值('')的插入               2关闭stmt
              2查询ROLLBACK
              2退出

要解决此问题,您需要在cleanup文件中配置Laravel4模块的codeception.yml选项,如下所示:

modules:
    config:
        Laravel4:
        cleanup: false