您的位置:首页 > 编程语言 > PHP开发

Yii2框架下,使用Codeception进行单元测试

2016-04-05 03:27 811 查看

前言:

Yii2是一款非常优秀的php框架,Yii2的官方发行版整合了Codeception测试框架。在使用Yii2框架的项目中,我们可以非常方便地利用Codeception进行单元测试、功能测试和验收测试。现在我们就利用Codeception在Yii2下实现简单的单元测试。

 

在进行单元测试前,需要做一些准备工作。

 

1. 首先确保你的机器安装了Composer,否则请自行安装,这是安装教程

 

2. 打开命令行,并切换目录到项目根目录,分别运行如下命令。

composer require "fxp/composer-asset-plugin:*"

composer require "codeception/codeception=*"

composer require "codeception/specify=*"

composer require "codeception/verify=*"

 

3. 依赖包安装好了过后,切换到tests目录下(以后的所有的命令都将在tests目录下运行),运行命令(博主所使用的是windows环境,linux同理)当然你也可以把该路径"C:\www\yii\vendor\bin\codecept"加到系统PATH里,这样你就可以直接输入"codecept build"而不用加上路径前缀了。

..\vendor\bin\codecept build

 

注:由于Yii2框架已经整合了Codeception,所以不需要运行"..\vendor\bin\codecept bootstrap"命令。

 

4. 配置tests/codeception/_bootstrap.php文件(在该文件末尾加上下面两行代码)

$config = require(__DIR__ . '/../../config/console.php');

$application = new yii\console\Application($config);

 

5. 博主在"task"数据库下,创建一个名为"department"的表,并插入如下数据。接下来,我们所有的测试都将围绕着这张表进行。

dept_name(varchar) building(varchar) budget(numeric)
Biology Watson 90000
Comp. Sci. Taylor 100000
Elec. Eng. Taylor 85000
Finance Painter 120000
History Painter 50000
Music Packard 80000
Physics Watson 70000

 

6. 配置tests/codeception/unit.suite.yml文件(博主该文件的配置如下)

# Codeception Test Suite Configuration

# suite for unit (internal) tests.
# RUN `build` COMMAND AFTER ADDING/REMOVING MODULES.

class_name: UnitTester
modules:
enabled:
- Asserts
- DB:
dsn: 'mysql:host=localhost;dbname=task'
user: 'root'
password: ''

 

7. 将tests/codeception/config/config.php文件中,"dbname"改成"department"表所在的数据库名

 

 

 

前期的准备工作完成了以后,我们现在把注意力集中在创建Unit Tests上来。

 

在Web应用中,最常见的操作也就是:验证用户输入、将用户输入保存到数据库、修改数据库中的数据。现在,我们对这三种常见的操作,分别创建一个单元测试的例子。

 

 

验证用户输入

 

首先创建测试文件,在tests目录下面运行如下命令

 

..\vendor\bin\codecept generate:test unit \models\ExampleValidation

 结果如下

 


 
 ExampleValidationTest.php源码如下

<?php
namespace tests\codeception\unit\models;

use Yii;
use app\models\DepartmentModel;
use yii\codeception\TestCase;

class ExampleTest extends TestCase
{
use \Codeception\Specify;

private $_dept;

/**
* @var \UnitTester
*/
protected $tester;

protected function _before()
{
$this->_dept = new DepartmentModel();
}

protected function _after()
{
}

public function testValidation()
{
$this->specify('Department validation fail', function() {

/* 给dept_name赋一个重复的值,然后assertFalse */
$this->_dept->dept_name = 'Biology';
$this->assertFalse($this->_dept->validate());
});

$this->specify('Department validation pass', function() {

/* 给dept_name赋一个尚未重复的值,然后assertTrue */
$this->_dept->dept_name = 'Math';
$this->assertTrue($this->_dept->validate());
});
}

}

 

 DepartmentModel.php的源码如下

<?php
namespace app\models;

use Yii;
use yii\db\ActiveRecord;

class DepartmentModel extends ActiveRecord
{

/**
* @return array the validation rules.
*/
public function rules()
{
return [
[['dept_name', 'building'], 'string'],
['budget', 'double'],
['dept_name', 'selfDefineValidation'],
];
}

/**
* @return string 返回与之关联的数据库表名
*/
public static function tableName()
{
return 'department';
}

/**
* 对输入的dept_name进行验证,不允许插入重复的dept_name
*/
public function selfDefineValidation($attribute, $params)
{
$result = self::find()
->where(['dept_name' => $this->$attribute])
->limit(1)
->one();
if (!empty($result)) {
$this->addError($attribute, 'The department name has been existed');
}
}
}

 

然后在命令行测试结果如下

 

验证通过。

 

 

 验证用户保存数据

 

首先创建测试文件,在tests目录下面运行创建命令

 
ExampleSavingTest.php源代码如下

<?php
namespace tests\codeception\unit\models;

use app\models\DepartmentModel;
use yii\codeception\TestCase;

class ExampleSavingTest extends TestCase
{
use \Codeception\Specify;

/**
* @var app\models\DepartmentModel
*/
private $_dept;

/**
* @var \UnitTester
*/
protected $tester;

protected function _before()
{
$this->_dept = new DepartmentModel();
}

protected function _after()
{
}

// tests
public function testSavingDept()
{
$this->_dept->dept_name = 'Math';
$this->_dept->building = 'Palmer';
$this->_dept->budget = 70000.00;
$this->_dept->save();

/* 查看数据库中是否保存了数据 */
$this->tester->seeInDatabase('department', [
'dept_name' => $this->_dept->dept_name,
'building' => $this->_dept->building,
'budget' => $this->_dept->budget,
]);

}
}

 

 

运行测试结果如下

 
测试通过,数据库中也确实保存了数据

 

 

验证用户修改数据

 

 首先创建单元测试文件

 

ExampleModifyingTest.php源码如下

<?php
namespace tests\codeception\unit\models;

use app\models\DepartmentModel;
use yii\codeception\TestCase;

class ExampleModifyingTest extends TestCase
{
use \Codeception\Specify;

/**
* @var app\models\DepartmentModel
*/
private $_dept;

/**
* @var \UnitTester
*/
protected $tester;

protected function _before()
{
}

protected function _after()
{
}

// tests
public function testModify()
{
$this->_dept = DepartmentModel::find()
->where(['dept_name' => 'History'])
->limit(1)
->one();

$old_dept_name = $this->_dept->dept_name;
$old_building = $this->_dept->building;
$old_budget = $this->_dept->budget;

$this->_dept->dept_name = 'English';
$this->_dept->building = 'Palmer';
$this->_dept->budget = 65000.00;
$this->_dept->save();

/* 校验数据库中的数据是否真的被修改了 */
$this->tester->seeInDatabase('department', [
'dept_name' => 'English',
'building' => 'Palmer',
'budget' => 65000.00,
]);

$this->tester->dontSeeInDatabase('department', [
'dept_name' => $old_dept_name,
'building' => $old_building,
'budget' => $old_budget,
]);
}
}

 

测试运行结果如下

 

  测试完毕,数据库中的数据也已经修改了。

 

 结束语:

对于任何一个软件从业人员来说,单元测试的重要性不言而喻。以上只是对Codeception这款全栈测试框架的单元测试部分,做一个简单的演示。有兴趣的朋友可以去Codepection官网查看更详细的内容。由于博主本人水平所限,如有错误,欢迎批评指正。

 

参考资料:

1. http://codeception.com/docs/05-UnitTests#.VwK7yPl97IV

2. http://pjokumsen.co.za/codeception-testing-with-yii-framework-2-0-wip/

 

版权声明:本文为博主原创文章,未经博主允许不得转载。

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: