PHPUnit5.0中文手册8. 数据库测试数据库测试的难点

数据库测试的难点

为什么所有单元测试的范例都不包含数据库交互?这里有个很好的理由:这类测试的建立和维护都很复杂。对数据库进行测试时,需要考虑以下这些变数:

  • 数据库和表

  • 向表中插入测试所需要的行

  • 测试运行完毕后验证数据库的状态

  • 每个新测试都要清理数据库

许多数据库 API,比如 PDO、MySQLi 或者 OCI8,都十分繁琐且书写起来十分冗长,因此,手工进行这些步骤绝对是噩梦。

测试代码应当尽可能简短精确,这有若干原因:

  • 你不希望因为生产代码的小变更而需要对测试代码进行数量可观的修改。

  • 你希望在哪怕好几个月以后也能轻松地阅读并理解测试代码。

另外,必须认识到,对于代码而言,本质上来说数据库是全局输入变量。测试套件中的两个不同的测试可能是运行在同一个数据库上的,并且可能把数据重用好多次。一个测试中出现的失败很容易影响到后继测试的结果,从而让整个测试过程变得非常艰难。前面提到的清理步骤对于解决“数据库是全局输入”的问题是非常重要的。

DbUnit 以一种优雅的方式来帮助简化数据库测试中的所有这些问题。

PHPUnit 无法帮你解决的问题是,相对于不使用数据的测试而言,数据库测试是非常慢的。随着数据库交互规模的增大,运行测试可能需要耗费可观的时间。然而,只要保持每个测试所使用的数据量较小并且尽可能用非数据库测试来对代码进行测试,即使很大的测试套件也能轻松在一分钟内跑完。

以 Doctrine 2 为例,此项目的测试套件目前包含了大约1000个测试,其中将近一半访问了数据库。但是在一台安装了MySQL的普通的台式机上,整个测试套件依然能在15秒钟内跑完。