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

Yii框架的单元测试中使用Fixtures详解

2013-05-16 15:31 253 查看
Yii框架提供了一些单元测试的支持,大家可以看看Yii提供的例子,然后,我们解析下最复杂的fixtures是怎么做的,因为企业级的单测,比如离不开数据库,这也是回报最优厚的地方。

单测的case如果要使用Fixtures就需要声明一个public
$fixtures的变量,比如:

public$fixtures=array(
'posts'=>'Post',
'comments'=>'Comment',
);


然后,调用fixtures的代码,实际上是在CDbTestCase里面。然后,里面有setup:
protected functionsetUp()
{
parent::setUp();
if(is_array($this->fixtures))
$this->getFixtureManager()->load($this->fixtures);
}

会执行$this->getFixtureManager()->load($this->fixtures);,接下去就会初始化fixture这个component了,而这个component在我们的main.php文件中,就是system.test.CDbFixtureManager了。

初始化的过程就是:init() ==> prepare() ==>checkIntegrity ==>
getFixtures ==> resetTable ==> loadFixtures ==>结束.
public functioninit()
{
parent::init();
if($this->basePath===null)
$this->basePath=Yii::getPathOfAlias('application.tests.fixtures');
$this->prepare();
}


public functiongetFixtures()
{
if($this->_fixtures===null)
{
$this->_fixtures=array();
$schema=$this->getDbConnection()->getSchema();
$folder=opendir($this->basePath);
$suffixLen=strlen($this->initScriptSuffix);
while($file=readdir($folder))
{
if($file==='.'|| $file==='..' || $file===$this->initScript)
continue;
$path=$this->basePath.DIRECTORY_SEPARATOR.$file;
if(substr($file,-4)==='.php'&& is_file($path) &&substr($file,-$suffixLen)!==$this->initScriptSuffix)
{
$tableName=substr($file,0,-4);
if($schema->getTable($tableName)!==null)
$this->_fixtures[$tableName]=$path;//在这里会获取到我们需要重新同步数据库的文件。也就是,如果数据有个叫 users的表,那么就一定要叫做users.php,大小写什么的都是敏感的。这就是坑的地方。
}
}
closedir($folder);
}
return$this->_fixtures;
}


然后,上面的只是初始化,我们看setup里面,还有一个load($this->fixtures);的操作,现在就来看看做了啥:
$schema=$this->getDbConnection()->getSchema();
$schema->checkIntegrity(false);

$this->_rows=array();
$this->_records=array();
foreach($fixtures as$fixtureName=>$tableName)
{
if($tableName[0]===':')
{
$tableName=substr($tableName,1);
unset($modelClass);
}
else
{
$modelClass=Yii::import($tableName,true);
$tableName=CActiveRecord::model($modelClass)->tableName();
if(($prefix=$this->getDbConnection()->tablePrefix)!==null)
$tableName=preg_replace('/{{(.*?)}}/',$prefix.'\1',$tableName);
}
$this->resetTable($tableName);
$rows=$this->loadFixture($tableName);
if(is_array($rows)&& is_string($fixtureName))
{
$this->_rows[$fixtureName]=$rows;
if(isset($modelClass))
{
foreach(array_keys($rows)as $alias)
$this->_records[$fixtureName][$alias]=$modelClass;
}
}
}

$schema->checkIntegrity(true);
}


到这里也就都完了,这就是加载的整个过程。然后,我们要注意的几个点,不然,就没法使用。

1.fixtures文件夹下面,一定要以数据库的表名称来命名,而且是大小写敏感的。

2.在单测的case里,我们的fixtures变量,后面的值,一定要是Model下面的类名称。不然就会报错的。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: