我有一个运行产品组件测试的测试环境。我发现最近很难测试并成功模拟 php 的 is_uploaded_file()
和 move_uploaded_file()
但经过大量搜索和研究后,我找到了 PHPT。这真的对我测试这些方法和文件上传的期望有很大帮助。这不是关于文件上传的问题,而是如何将 phpt 测试用例集成到基本的 phpunit 测试用例中,以便代码覆盖率也将针对正在测试的方法运行。下面是一些代码摘录:
文件.php
class prFiles
{
// Instance methods here not needed for the purpose of this question
// ......
public function transfer(array $files, $target_directory,
$new_filename, $old_filename = '')
{
if ( (isset($files['file']['tmp_name']) === true)
&& (is_uploaded_file($files['file']['tmp_name']) === true) )
{
// Only check if old filename exists
if ( (file_exists($target_directory . '/' . $old_filename) === true)
&& (empty($old_filename) === false) )
{
unlink($target_directory . $old_filename);
}
$upload = move_uploaded_file(
$files['file']['tmp_name'],
$target_directory . '/' . $new_filename
);
if ( $upload === true )
{
return true;
}
else
{
return false;
}
}
return false;
}
}
file_upload_test.phpt
--TEST--
Test the prFiles::transfer() the actual testing of the file uploading.
--POST_RAW--
Content-Type: multipart/form-data; boundary=----WebKitFormBoundaryfywL8UCjFtqUBTQn
------WebKitFormBoundaryfywL8UCjFtqUBTQn
Content-Disposition: form-data; name="file"; filename="test.txt"
Content-Type: text/plain
This is some test text
------WebKitFormBoundaryfywL8UCjFtqUBTQn
Content-Disposition: form-data; name="submit"
Upload
------WebKitFormBoundaryfywL8UCjFtqUBTQn--
--FILE--
<?php
require_once dirname(__FILE__) . '/../../../src/lib/utilities/files.php';
$prFiles = prFiles::getInstance()->transfer(
$_FILES,
dirname(__FILE__) . '/../_data/',
'test.txt'
);
var_dump($prFiles);
?>
--EXPECT--
bool(true)
UtilitiesFilesTransferTest.php
class UtilitiesFilesTransferTest extends PHPUnit_Extensions_PhptTestCase
{
/**
* Constructs a new UtilitiesFilesTransferTest.
*
*/
public function __construct()
{
parent::__construct(dirname(__FILE__) . '/_phpt/file_upload_test.phpt');
}
}
所以一切正常。但我似乎无法了解我正在测试的传输方法。请问有人能帮帮我吗?
编辑:我的覆盖命令如下所示:
@echo off
echo.
if not "%1"=="" goto location
goto default
:location
set EXEC=phpunit --coverage-html %1 TestSuite
goto execute
:default
set EXEC=phpunit --coverage-html c:\xampp\htdocs\workspace\coverage\project TestSuite
:execute
%EXEC%
最佳答案
由于 PhpUnit 具有运行在单独进程中发生的 PHPT 文件的自定义实现,因此将代码覆盖率集成到 PhpUnit 可能确实非常困难。
但是,如果您所需要的只是覆盖范围(或者您愿意自己进行一些后期处理),它就变得非常微不足道了。
在最简单的形式中,您需要做的就是从 PHPT 文件调用 xDebug。使用 PHP_CodeCoverage (以及用于类自动加载的 Composer)您的 --FILE--
部分可能如下所示:
--FILE--
<?php
/* autoload classes */
require __DIR__ . '/../../../vendor/autoload.php';
/* Setup and start code coverage */
$coverage = new \PHP_CodeCoverage;
$coverage->start('test');
/* run logic */
$prFiles = prFiles::getInstance()->transfer(
$_FILES,
__DIR__ . '/../_data/',
'test.txt'
);
var_dump($prFiles);
/* stop and output coverage data */
$coverage->stop();
$writer = new \PHP_CodeCoverage_Report_PHP;
$writer->process($coverage, __DIR__ . '/../../../build/log/coverage-data.php');
?>
所有收集到的覆盖率数据将被放入coverage-data.php
文件中。
您可以加载此信息并将其与其他覆盖率信息(例如来自 PhpUnit)相结合,以创建您想要的任何格式的输出。
覆盖逻辑可以放在一个单独的类中,让您只需添加两行代码即可添加到您想要覆盖的每个测试中:
--FILE--
<?php
/* autoload classes */
require __DIR__ . '/../../../vendor/autoload.php';
cover::start;
/* run logic */
$prFiles = prFiles::getInstance()->transfer(
$_FILES,
__DIR__ . '/../_data/',
'test.txt'
);
var_dump($prFiles);
cover::stop;
?>
还有一个cover
类:
<?php
class cover
{
private static $coverage;
/* Setup and start code coverage */
public static function start()
{
self::$coverage = new \PHP_CodeCoverage;
/* Make sure this file is not added to the coverage data */
$filter = self::$coverage->filter();
$filter->addFileToBlacklist(__FILE__);
self::$coverage->start('test');
}
/* stop and output coverage data */
public static function stop()
{
self::$coverage->stop();
$writer = new \PHP_CodeCoverage_Report_PHP;
$writer->process(self::$coverage, __DIR__ . '/../build/log/coverage-data.php');
}
}
由于覆盖逻辑位于 PHPT 文件之外,您可以轻松访问配置文件或添加其他逻辑。
关于php - 我如何获得 php 代码覆盖率来运行 phpt 测试用例?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5622437/