a grand renaming so that the most significant portion of the name comes first
This commit is contained in:
835
php-practice/web-cake/html/cake/tests/lib/cake_test_case.php
Normal file
835
php-practice/web-cake/html/cake/tests/lib/cake_test_case.php
Normal file
@@ -0,0 +1,835 @@
|
||||
<?php
|
||||
/**
|
||||
* CakeTestCase file
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.libs
|
||||
* @since CakePHP(tm) v 1.2.0.4667
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
if (!class_exists('dispatcher')) {
|
||||
require CAKE . 'dispatcher.php';
|
||||
}
|
||||
require_once CAKE_TESTS_LIB . 'cake_test_model.php';
|
||||
require_once CAKE_TESTS_LIB . 'cake_test_fixture.php';
|
||||
App::import('Vendor', 'simpletest' . DS . 'unit_tester');
|
||||
|
||||
/**
|
||||
* CakeTestDispatcher
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
*/
|
||||
class CakeTestDispatcher extends Dispatcher {
|
||||
|
||||
/**
|
||||
* controller property
|
||||
*
|
||||
* @var Controller
|
||||
* @access public
|
||||
*/
|
||||
var $controller;
|
||||
var $testCase;
|
||||
|
||||
/**
|
||||
* testCase method
|
||||
*
|
||||
* @param CakeTestCase $testCase
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function testCase(&$testCase) {
|
||||
$this->testCase =& $testCase;
|
||||
}
|
||||
|
||||
/**
|
||||
* invoke method
|
||||
*
|
||||
* @param Controller $controller
|
||||
* @param array $params
|
||||
* @param boolean $missingAction
|
||||
* @return Controller
|
||||
* @access protected
|
||||
*/
|
||||
function _invoke(&$controller, $params, $missingAction = false) {
|
||||
$this->controller =& $controller;
|
||||
|
||||
if (array_key_exists('layout', $params)) {
|
||||
$this->controller->layout = $params['layout'];
|
||||
}
|
||||
|
||||
if (isset($this->testCase) && method_exists($this->testCase, 'startController')) {
|
||||
$this->testCase->startController($this->controller, $params);
|
||||
}
|
||||
|
||||
$result = parent::_invoke($this->controller, $params, $missingAction);
|
||||
|
||||
if (isset($this->testCase) && method_exists($this->testCase, 'endController')) {
|
||||
$this->testCase->endController($this->controller, $params);
|
||||
}
|
||||
|
||||
return $result;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* CakeTestCase class
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
*/
|
||||
class CakeTestCase extends UnitTestCase {
|
||||
|
||||
/**
|
||||
* Methods used internally.
|
||||
*
|
||||
* @var array
|
||||
* @access public
|
||||
*/
|
||||
var $methods = array('start', 'end', 'startcase', 'endcase', 'starttest', 'endtest');
|
||||
|
||||
/**
|
||||
* By default, all fixtures attached to this class will be truncated and reloaded after each test.
|
||||
* Set this to false to handle manually
|
||||
*
|
||||
* @var array
|
||||
* @access public
|
||||
*/
|
||||
var $autoFixtures = true;
|
||||
|
||||
/**
|
||||
* Set this to false to avoid tables to be dropped if they already exist
|
||||
*
|
||||
* @var boolean
|
||||
* @access public
|
||||
*/
|
||||
var $dropTables = true;
|
||||
|
||||
/**
|
||||
* Maps fixture class names to fixture identifiers as included in CakeTestCase::$fixtures
|
||||
*
|
||||
* @var array
|
||||
* @access protected
|
||||
*/
|
||||
var $_fixtureClassMap = array();
|
||||
|
||||
/**
|
||||
* truncated property
|
||||
*
|
||||
* @var boolean
|
||||
* @access private
|
||||
*/
|
||||
var $__truncated = true;
|
||||
|
||||
/**
|
||||
* savedGetData property
|
||||
*
|
||||
* @var array
|
||||
* @access private
|
||||
*/
|
||||
var $__savedGetData = array();
|
||||
|
||||
/**
|
||||
* Called when a test case (group of methods) is about to start (to be overriden when needed.)
|
||||
*
|
||||
* @param string $method Test method about to get executed.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function startCase() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when a test case (group of methods) has been executed (to be overriden when needed.)
|
||||
*
|
||||
* @param string $method Test method about that was executed.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function endCase() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when a test case method is about to start (to be overriden when needed.)
|
||||
*
|
||||
* @param string $method Test method about to get executed.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function startTest($method) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Called when a test case method has been executed (to be overriden when needed.)
|
||||
*
|
||||
* @param string $method Test method about that was executed.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function endTest($method) {
|
||||
}
|
||||
|
||||
/**
|
||||
* Overrides SimpleTestCase::assert to enable calling of skipIf() from within tests
|
||||
*
|
||||
* @param Expectation $expectation
|
||||
* @param mixed $compare
|
||||
* @param string $message
|
||||
* @return boolean|null
|
||||
* @access public
|
||||
*/
|
||||
function assert(&$expectation, $compare, $message = '%s') {
|
||||
if ($this->_should_skip) {
|
||||
return;
|
||||
}
|
||||
return parent::assert($expectation, $compare, $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* Overrides SimpleTestCase::skipIf to provide a boolean return value
|
||||
*
|
||||
* @param boolean $shouldSkip
|
||||
* @param string $message
|
||||
* @return boolean
|
||||
* @access public
|
||||
*/
|
||||
function skipIf($shouldSkip, $message = '%s') {
|
||||
parent::skipIf($shouldSkip, $message);
|
||||
return $shouldSkip;
|
||||
}
|
||||
|
||||
/**
|
||||
* Callback issued when a controller's action is about to be invoked through testAction().
|
||||
*
|
||||
* @param Controller $controller Controller that's about to be invoked.
|
||||
* @param array $params Additional parameters as sent by testAction().
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function startController(&$controller, $params = array()) {
|
||||
if (isset($params['fixturize']) && ((is_array($params['fixturize']) && !empty($params['fixturize'])) || $params['fixturize'] === true)) {
|
||||
if (!isset($this->db)) {
|
||||
$this->_initDb();
|
||||
}
|
||||
|
||||
if ($controller->uses === false) {
|
||||
$list = array($controller->modelClass);
|
||||
} else {
|
||||
$list = is_array($controller->uses) ? $controller->uses : array($controller->uses);
|
||||
}
|
||||
|
||||
$models = array();
|
||||
ClassRegistry::config(array('ds' => $params['connection']));
|
||||
|
||||
foreach ($list as $name) {
|
||||
if ((is_array($params['fixturize']) && in_array($name, $params['fixturize'])) || $params['fixturize'] === true) {
|
||||
if (class_exists($name) || App::import('Model', $name)) {
|
||||
$object =& ClassRegistry::init($name);
|
||||
//switch back to specified datasource.
|
||||
$object->setDataSource($params['connection']);
|
||||
$db =& ConnectionManager::getDataSource($object->useDbConfig);
|
||||
$db->cacheSources = false;
|
||||
|
||||
$models[$object->alias] = array(
|
||||
'table' => $object->table,
|
||||
'model' => $object->alias,
|
||||
'key' => strtolower($name),
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
ClassRegistry::config(array('ds' => 'test_suite'));
|
||||
|
||||
if (!empty($models) && isset($this->db)) {
|
||||
$this->_actionFixtures = array();
|
||||
|
||||
foreach ($models as $model) {
|
||||
$fixture =& new CakeTestFixture($this->db);
|
||||
|
||||
$fixture->name = $model['model'] . 'Test';
|
||||
$fixture->table = $model['table'];
|
||||
$fixture->import = array('model' => $model['model'], 'records' => true);
|
||||
$fixture->init();
|
||||
|
||||
$fixture->create($this->db);
|
||||
$fixture->insert($this->db);
|
||||
$this->_actionFixtures[] =& $fixture;
|
||||
}
|
||||
|
||||
foreach ($models as $model) {
|
||||
$object =& ClassRegistry::getObject($model['key']);
|
||||
if ($object !== false) {
|
||||
$object->setDataSource('test_suite');
|
||||
$object->cacheSources = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Callback issued when a controller's action has been invoked through testAction().
|
||||
*
|
||||
* @param Controller $controller Controller that has been invoked.
|
||||
* @param array $params Additional parameters as sent by testAction().
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function endController(&$controller, $params = array()) {
|
||||
if (isset($this->db) && isset($this->_actionFixtures) && !empty($this->_actionFixtures) && $this->dropTables) {
|
||||
foreach ($this->_actionFixtures as $fixture) {
|
||||
$fixture->drop($this->db);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Executes a Cake URL, and can get (depending on the $params['return'] value):
|
||||
*
|
||||
* Params:
|
||||
* - 'return' has several possible values:
|
||||
* 1. 'result': Whatever the action returns (and also specifies $this->params['requested'] for controller)
|
||||
* 2. 'view': The rendered view, without the layout
|
||||
* 3. 'contents': The rendered view, within the layout.
|
||||
* 4. 'vars': the view vars
|
||||
*
|
||||
* - 'fixturize' - Set to true if you want to copy model data from 'connection' to the test_suite connection
|
||||
* - 'data' - The data you want to insert into $this->data in the controller.
|
||||
* - 'connection' - Which connection to use in conjunction with fixturize (defaults to 'default')
|
||||
* - 'method' - What type of HTTP method to simulate (defaults to post)
|
||||
*
|
||||
* @param string $url Cake URL to execute (e.g: /articles/view/455)
|
||||
* @param mixed $params Parameters (see above), or simply a string of what to return
|
||||
* @return mixed Whatever is returned depending of requested result
|
||||
* @access public
|
||||
*/
|
||||
function testAction($url, $params = array()) {
|
||||
$default = array(
|
||||
'return' => 'result',
|
||||
'fixturize' => false,
|
||||
'data' => array(),
|
||||
'method' => 'post',
|
||||
'connection' => 'default'
|
||||
);
|
||||
|
||||
if (is_string($params)) {
|
||||
$params = array('return' => $params);
|
||||
}
|
||||
$params = array_merge($default, $params);
|
||||
|
||||
$toSave = array(
|
||||
'case' => null,
|
||||
'group' => null,
|
||||
'app' => null,
|
||||
'output' => null,
|
||||
'show' => null,
|
||||
'plugin' => null
|
||||
);
|
||||
$this->__savedGetData = (empty($this->__savedGetData))
|
||||
? array_intersect_key($_GET, $toSave)
|
||||
: $this->__savedGetData;
|
||||
|
||||
$data = (!empty($params['data'])) ? $params['data'] : array();
|
||||
|
||||
if (strtolower($params['method']) == 'get') {
|
||||
$_GET = array_merge($this->__savedGetData, $data);
|
||||
$_POST = array();
|
||||
} else {
|
||||
$_POST = array('data' => $data);
|
||||
$_GET = $this->__savedGetData;
|
||||
}
|
||||
|
||||
$return = $params['return'];
|
||||
$params = array_diff_key($params, array('data' => null, 'method' => null, 'return' => null));
|
||||
|
||||
$dispatcher =& new CakeTestDispatcher();
|
||||
$dispatcher->testCase($this);
|
||||
|
||||
if ($return != 'result') {
|
||||
if ($return != 'contents') {
|
||||
$params['layout'] = false;
|
||||
}
|
||||
|
||||
ob_start();
|
||||
@$dispatcher->dispatch($url, $params);
|
||||
$result = ob_get_clean();
|
||||
|
||||
if ($return == 'vars') {
|
||||
$view =& ClassRegistry::getObject('view');
|
||||
$viewVars = $view->getVars();
|
||||
|
||||
$result = array();
|
||||
|
||||
foreach ($viewVars as $var) {
|
||||
$result[$var] = $view->getVar($var);
|
||||
}
|
||||
|
||||
if (!empty($view->pageTitle)) {
|
||||
$result = array_merge($result, array('title' => $view->pageTitle));
|
||||
}
|
||||
}
|
||||
} else {
|
||||
$params['return'] = 1;
|
||||
$params['bare'] = 1;
|
||||
$params['requested'] = 1;
|
||||
|
||||
$result = @$dispatcher->dispatch($url, $params);
|
||||
}
|
||||
|
||||
if (isset($this->_actionFixtures)) {
|
||||
unset($this->_actionFixtures);
|
||||
}
|
||||
ClassRegistry::flush();
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Announces the start of a test.
|
||||
*
|
||||
* @param string $method Test method just started.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function before($method) {
|
||||
parent::before($method);
|
||||
|
||||
if (isset($this->fixtures) && (!is_array($this->fixtures) || empty($this->fixtures))) {
|
||||
unset($this->fixtures);
|
||||
}
|
||||
|
||||
// Set up DB connection
|
||||
if (isset($this->fixtures) && strtolower($method) == 'start') {
|
||||
$this->_initDb();
|
||||
$this->_loadFixtures();
|
||||
}
|
||||
|
||||
// Create records
|
||||
if (isset($this->_fixtures) && isset($this->db) && !in_array(strtolower($method), array('start', 'end')) && $this->__truncated && $this->autoFixtures == true) {
|
||||
foreach ($this->_fixtures as $fixture) {
|
||||
$inserts = $fixture->insert($this->db);
|
||||
}
|
||||
}
|
||||
|
||||
if (!in_array(strtolower($method), $this->methods)) {
|
||||
$this->startTest($method);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs as first test to create tables.
|
||||
*
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function start() {
|
||||
if (isset($this->_fixtures) && isset($this->db)) {
|
||||
Configure::write('Cache.disable', true);
|
||||
$cacheSources = $this->db->cacheSources;
|
||||
$this->db->cacheSources = false;
|
||||
$sources = $this->db->listSources();
|
||||
$this->db->cacheSources = $cacheSources;
|
||||
|
||||
if (!$this->dropTables) {
|
||||
return;
|
||||
}
|
||||
foreach ($this->_fixtures as $fixture) {
|
||||
$table = $this->db->config['prefix'] . $fixture->table;
|
||||
if (in_array($table, $sources)) {
|
||||
$fixture->drop($this->db);
|
||||
$fixture->create($this->db);
|
||||
} elseif (!in_array($table, $sources)) {
|
||||
$fixture->create($this->db);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs as last test to drop tables.
|
||||
*
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function end() {
|
||||
if (isset($this->_fixtures) && isset($this->db)) {
|
||||
if ($this->dropTables) {
|
||||
foreach (array_reverse($this->_fixtures) as $fixture) {
|
||||
$fixture->drop($this->db);
|
||||
}
|
||||
}
|
||||
$this->db->sources(true);
|
||||
Configure::write('Cache.disable', false);
|
||||
}
|
||||
|
||||
if (class_exists('ClassRegistry')) {
|
||||
ClassRegistry::flush();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Announces the end of a test.
|
||||
*
|
||||
* @param string $method Test method just finished.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function after($method) {
|
||||
$isTestMethod = !in_array(strtolower($method), array('start', 'end'));
|
||||
|
||||
if (isset($this->_fixtures) && isset($this->db) && $isTestMethod) {
|
||||
foreach ($this->_fixtures as $fixture) {
|
||||
$fixture->truncate($this->db);
|
||||
}
|
||||
$this->__truncated = true;
|
||||
} else {
|
||||
$this->__truncated = false;
|
||||
}
|
||||
|
||||
if (!in_array(strtolower($method), $this->methods)) {
|
||||
$this->endTest($method);
|
||||
}
|
||||
$this->_should_skip = false;
|
||||
|
||||
parent::after($method);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets a list of test names. Normally that will be all internal methods that start with the
|
||||
* name "test". This method should be overridden if you want a different rule.
|
||||
*
|
||||
* @return array List of test names.
|
||||
* @access public
|
||||
*/
|
||||
function getTests() {
|
||||
return array_merge(
|
||||
array('start', 'startCase'),
|
||||
array_diff(parent::getTests(), array('testAction', 'testaction')),
|
||||
array('endCase', 'end')
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Chooses which fixtures to load for a given test
|
||||
*
|
||||
* @param string $fixture Each parameter is a model name that corresponds to a
|
||||
* fixture, i.e. 'Post', 'Author', etc.
|
||||
* @return void
|
||||
* @access public
|
||||
* @see CakeTestCase::$autoFixtures
|
||||
*/
|
||||
function loadFixtures() {
|
||||
$args = func_get_args();
|
||||
foreach ($args as $class) {
|
||||
if (isset($this->_fixtureClassMap[$class])) {
|
||||
$fixture = $this->_fixtures[$this->_fixtureClassMap[$class]];
|
||||
|
||||
$fixture->truncate($this->db);
|
||||
$fixture->insert($this->db);
|
||||
} else {
|
||||
trigger_error(sprintf(__('Referenced fixture class %s not found', true), $class), E_USER_WARNING);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Takes an array $expected and generates a regex from it to match the provided $string.
|
||||
* Samples for $expected:
|
||||
*
|
||||
* Checks for an input tag with a name attribute (contains any non-empty value) and an id
|
||||
* attribute that contains 'my-input':
|
||||
* array('input' => array('name', 'id' => 'my-input'))
|
||||
*
|
||||
* Checks for two p elements with some text in them:
|
||||
* array(
|
||||
* array('p' => true),
|
||||
* 'textA',
|
||||
* '/p',
|
||||
* array('p' => true),
|
||||
* 'textB',
|
||||
* '/p'
|
||||
* )
|
||||
*
|
||||
* You can also specify a pattern expression as part of the attribute values, or the tag
|
||||
* being defined, if you prepend the value with preg: and enclose it with slashes, like so:
|
||||
* array(
|
||||
* array('input' => array('name', 'id' => 'preg:/FieldName\d+/')),
|
||||
* 'preg:/My\s+field/'
|
||||
* )
|
||||
*
|
||||
* Important: This function is very forgiving about whitespace and also accepts any
|
||||
* permutation of attribute order. It will also allow whitespaces between specified tags.
|
||||
*
|
||||
* @param string $string An HTML/XHTML/XML string
|
||||
* @param array $expected An array, see above
|
||||
* @param string $message SimpleTest failure output string
|
||||
* @return boolean
|
||||
* @access public
|
||||
*/
|
||||
function assertTags($string, $expected, $fullDebug = false) {
|
||||
$regex = array();
|
||||
$normalized = array();
|
||||
foreach ((array) $expected as $key => $val) {
|
||||
if (!is_numeric($key)) {
|
||||
$normalized[] = array($key => $val);
|
||||
} else {
|
||||
$normalized[] = $val;
|
||||
}
|
||||
}
|
||||
$i = 0;
|
||||
foreach ($normalized as $tags) {
|
||||
if (!is_array($tags)) {
|
||||
$tags = (string)$tags;
|
||||
}
|
||||
$i++;
|
||||
if (is_string($tags) && $tags{0} == '<') {
|
||||
$tags = array(substr($tags, 1) => array());
|
||||
} elseif (is_string($tags)) {
|
||||
$tagsTrimmed = preg_replace('/\s+/m', '', $tags);
|
||||
|
||||
if (preg_match('/^\*?\//', $tags, $match) && $tagsTrimmed !== '//') {
|
||||
$prefix = array(null, null);
|
||||
|
||||
if ($match[0] == '*/') {
|
||||
$prefix = array('Anything, ', '.*?');
|
||||
}
|
||||
$regex[] = array(
|
||||
sprintf('%sClose %s tag', $prefix[0], substr($tags, strlen($match[0]))),
|
||||
sprintf('%s<[\s]*\/[\s]*%s[\s]*>[\n\r]*', $prefix[1], substr($tags, strlen($match[0]))),
|
||||
$i,
|
||||
);
|
||||
continue;
|
||||
}
|
||||
if (!empty($tags) && preg_match('/^preg\:\/(.+)\/$/i', $tags, $matches)) {
|
||||
$tags = $matches[1];
|
||||
$type = 'Regex matches';
|
||||
} else {
|
||||
$tags = preg_quote($tags, '/');
|
||||
$type = 'Text equals';
|
||||
}
|
||||
$regex[] = array(
|
||||
sprintf('%s "%s"', $type, $tags),
|
||||
$tags,
|
||||
$i,
|
||||
);
|
||||
continue;
|
||||
}
|
||||
foreach ($tags as $tag => $attributes) {
|
||||
$regex[] = array(
|
||||
sprintf('Open %s tag', $tag),
|
||||
sprintf('[\s]*<%s', preg_quote($tag, '/')),
|
||||
$i,
|
||||
);
|
||||
if ($attributes === true) {
|
||||
$attributes = array();
|
||||
}
|
||||
$attrs = array();
|
||||
$explanations = array();
|
||||
$i = 1;
|
||||
foreach ($attributes as $attr => $val) {
|
||||
if (is_numeric($attr) && preg_match('/^preg\:\/(.+)\/$/i', $val, $matches)) {
|
||||
$attrs[] = $matches[1];
|
||||
$explanations[] = sprintf('Regex "%s" matches', $matches[1]);
|
||||
continue;
|
||||
} else {
|
||||
$quotes = '["\']';
|
||||
if (is_numeric($attr)) {
|
||||
$attr = $val;
|
||||
$val = '.+?';
|
||||
$explanations[] = sprintf('Attribute "%s" present', $attr);
|
||||
} elseif (!empty($val) && preg_match('/^preg\:\/(.+)\/$/i', $val, $matches)) {
|
||||
$quotes = '["\']?';
|
||||
$val = $matches[1];
|
||||
$explanations[] = sprintf('Attribute "%s" matches "%s"', $attr, $val);
|
||||
} else {
|
||||
$explanations[] = sprintf('Attribute "%s" == "%s"', $attr, $val);
|
||||
$val = preg_quote($val, '/');
|
||||
}
|
||||
$attrs[] = '[\s]+' . preg_quote($attr, '/') . '=' . $quotes . $val . $quotes;
|
||||
}
|
||||
$i++;
|
||||
}
|
||||
if ($attrs) {
|
||||
$permutations = $this->__array_permute($attrs);
|
||||
|
||||
$permutationTokens = array();
|
||||
foreach ($permutations as $permutation) {
|
||||
$permutationTokens[] = implode('', $permutation);
|
||||
}
|
||||
$regex[] = array(
|
||||
sprintf('%s', implode(', ', $explanations)),
|
||||
$permutationTokens,
|
||||
$i,
|
||||
);
|
||||
}
|
||||
$regex[] = array(
|
||||
sprintf('End %s tag', $tag),
|
||||
'[\s]*\/?[\s]*>[\n\r]*',
|
||||
$i,
|
||||
);
|
||||
}
|
||||
}
|
||||
foreach ($regex as $i => $assertation) {
|
||||
list($description, $expressions, $itemNum) = $assertation;
|
||||
$matches = false;
|
||||
foreach ((array)$expressions as $expression) {
|
||||
if (preg_match(sprintf('/^%s/s', $expression), $string, $match)) {
|
||||
$matches = true;
|
||||
$string = substr($string, strlen($match[0]));
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!$matches) {
|
||||
$this->assert(new TrueExpectation(), false, sprintf('Item #%d / regex #%d failed: %s', $itemNum, $i, $description));
|
||||
if ($fullDebug) {
|
||||
debug($string, true);
|
||||
debug($regex, true);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return $this->assert(new TrueExpectation(), true, '%s');
|
||||
}
|
||||
|
||||
/**
|
||||
* Initialize DB connection.
|
||||
*
|
||||
* @return void
|
||||
* @access protected
|
||||
*/
|
||||
function _initDb() {
|
||||
$testDbAvailable = in_array('test', array_keys(ConnectionManager::enumConnectionObjects()));
|
||||
|
||||
$_prefix = null;
|
||||
|
||||
if ($testDbAvailable) {
|
||||
// Try for test DB
|
||||
restore_error_handler();
|
||||
@$db =& ConnectionManager::getDataSource('test');
|
||||
set_error_handler('simpleTestErrorHandler');
|
||||
$testDbAvailable = $db->isConnected();
|
||||
}
|
||||
|
||||
// Try for default DB
|
||||
if (!$testDbAvailable) {
|
||||
$db =& ConnectionManager::getDataSource('default');
|
||||
$_prefix = $db->config['prefix'];
|
||||
$db->config['prefix'] = 'test_suite_';
|
||||
}
|
||||
|
||||
ConnectionManager::create('test_suite', $db->config);
|
||||
$db->config['prefix'] = $_prefix;
|
||||
|
||||
// Get db connection
|
||||
$this->db =& ConnectionManager::getDataSource('test_suite');
|
||||
$this->db->cacheSources = false;
|
||||
|
||||
ClassRegistry::config(array('ds' => 'test_suite'));
|
||||
}
|
||||
|
||||
/**
|
||||
* Load fixtures specified in var $fixtures.
|
||||
*
|
||||
* @return void
|
||||
* @access protected
|
||||
*/
|
||||
function _loadFixtures() {
|
||||
if (!isset($this->fixtures) || empty($this->fixtures)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!is_array($this->fixtures)) {
|
||||
$this->fixtures = array_map('trim', explode(',', $this->fixtures));
|
||||
}
|
||||
|
||||
$this->_fixtures = array();
|
||||
|
||||
foreach ($this->fixtures as $index => $fixture) {
|
||||
$fixtureFile = null;
|
||||
|
||||
if (strpos($fixture, 'core.') === 0) {
|
||||
$fixture = substr($fixture, strlen('core.'));
|
||||
foreach (App::core('cake') as $key => $path) {
|
||||
$fixturePaths[] = $path . 'tests' . DS . 'fixtures';
|
||||
}
|
||||
} elseif (strpos($fixture, 'app.') === 0) {
|
||||
$fixture = substr($fixture, strlen('app.'));
|
||||
$fixturePaths = array(
|
||||
TESTS . 'fixtures',
|
||||
VENDORS . 'tests' . DS . 'fixtures'
|
||||
);
|
||||
} elseif (strpos($fixture, 'plugin.') === 0) {
|
||||
$parts = explode('.', $fixture, 3);
|
||||
$pluginName = $parts[1];
|
||||
$fixture = $parts[2];
|
||||
$fixturePaths = array(
|
||||
App::pluginPath($pluginName) . 'tests' . DS . 'fixtures',
|
||||
TESTS . 'fixtures',
|
||||
VENDORS . 'tests' . DS . 'fixtures'
|
||||
);
|
||||
} else {
|
||||
$fixturePaths = array(
|
||||
TESTS . 'fixtures',
|
||||
VENDORS . 'tests' . DS . 'fixtures',
|
||||
TEST_CAKE_CORE_INCLUDE_PATH . DS . 'cake' . DS . 'tests' . DS . 'fixtures'
|
||||
);
|
||||
}
|
||||
|
||||
foreach ($fixturePaths as $path) {
|
||||
if (is_readable($path . DS . $fixture . '_fixture.php')) {
|
||||
$fixtureFile = $path . DS . $fixture . '_fixture.php';
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (isset($fixtureFile)) {
|
||||
require_once($fixtureFile);
|
||||
$fixtureClass = Inflector::camelize($fixture) . 'Fixture';
|
||||
$this->_fixtures[$this->fixtures[$index]] =& new $fixtureClass($this->db);
|
||||
$this->_fixtureClassMap[Inflector::camelize($fixture)] = $this->fixtures[$index];
|
||||
}
|
||||
}
|
||||
|
||||
if (empty($this->_fixtures)) {
|
||||
unset($this->_fixtures);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates all permutation of an array $items and returns them in a new array.
|
||||
*
|
||||
* @param array $items An array of items
|
||||
* @return array
|
||||
* @access private
|
||||
*/
|
||||
function __array_permute($items, $perms = array()) {
|
||||
static $permuted;
|
||||
if (empty($perms)) {
|
||||
$permuted = array();
|
||||
}
|
||||
|
||||
if (empty($items)) {
|
||||
$permuted[] = $perms;
|
||||
} else {
|
||||
$numItems = count($items) - 1;
|
||||
for ($i = $numItems; $i >= 0; --$i) {
|
||||
$newItems = $items;
|
||||
$newPerms = $perms;
|
||||
list($tmp) = array_splice($newItems, $i, 1);
|
||||
array_unshift($newPerms, $tmp);
|
||||
$this->__array_permute($newItems, $newPerms);
|
||||
}
|
||||
return $permuted;
|
||||
}
|
||||
}
|
||||
}
|
200
php-practice/web-cake/html/cake/tests/lib/cake_test_fixture.php
Normal file
200
php-practice/web-cake/html/cake/tests/lib/cake_test_fixture.php
Normal file
@@ -0,0 +1,200 @@
|
||||
<?php
|
||||
/**
|
||||
* Short description for file.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.libs
|
||||
* @since CakePHP(tm) v 1.2.0.4667
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
|
||||
/**
|
||||
* Short description for class.
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
*/
|
||||
class CakeTestFixture extends Object {
|
||||
|
||||
/**
|
||||
* Name of the object
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $name = null;
|
||||
|
||||
/**
|
||||
* Cake's DBO driver (e.g: DboMysql).
|
||||
*
|
||||
* @access public
|
||||
*/
|
||||
var $db = null;
|
||||
|
||||
/**
|
||||
* Full Table Name
|
||||
*
|
||||
* @access public
|
||||
*/
|
||||
var $table = null;
|
||||
|
||||
/**
|
||||
* Instantiate the fixture.
|
||||
*
|
||||
* @access public
|
||||
*/
|
||||
function __construct() {
|
||||
App::import('Model', 'CakeSchema');
|
||||
$this->Schema = new CakeSchema(array('name' => 'TestSuite', 'connection' => 'test_suite'));
|
||||
|
||||
$this->init();
|
||||
}
|
||||
|
||||
/**
|
||||
* Initialize the fixture.
|
||||
*
|
||||
* @param object Cake's DBO driver (e.g: DboMysql).
|
||||
* @access public
|
||||
*
|
||||
*/
|
||||
function init() {
|
||||
if (isset($this->import) && (is_string($this->import) || is_array($this->import))) {
|
||||
$import = array_merge(
|
||||
array('connection' => 'default', 'records' => false),
|
||||
is_array($this->import) ? $this->import : array('model' => $this->import)
|
||||
);
|
||||
|
||||
if (isset($import['model']) && App::import('Model', $import['model'])) {
|
||||
ClassRegistry::config(array('ds' => $import['connection']));
|
||||
$model =& ClassRegistry::init($import['model']);
|
||||
$db =& ConnectionManager::getDataSource($model->useDbConfig);
|
||||
$db->cacheSources = false;
|
||||
$this->fields = $model->schema(true);
|
||||
$this->fields[$model->primaryKey]['key'] = 'primary';
|
||||
$this->table = $db->fullTableName($model, false);
|
||||
ClassRegistry::config(array('ds' => 'test_suite'));
|
||||
ClassRegistry::flush();
|
||||
} elseif (isset($import['table'])) {
|
||||
$model =& new Model(null, $import['table'], $import['connection']);
|
||||
$db =& ConnectionManager::getDataSource($import['connection']);
|
||||
$db->cacheSources = false;
|
||||
$model->useDbConfig = $import['connection'];
|
||||
$model->name = Inflector::camelize(Inflector::singularize($import['table']));
|
||||
$model->table = $import['table'];
|
||||
$model->tablePrefix = $db->config['prefix'];
|
||||
$this->fields = $model->schema(true);
|
||||
ClassRegistry::flush();
|
||||
}
|
||||
|
||||
if (!empty($db->config['prefix']) && strpos($this->table, $db->config['prefix']) === 0) {
|
||||
$this->table = str_replace($db->config['prefix'], '', $this->table);
|
||||
}
|
||||
|
||||
if (isset($import['records']) && $import['records'] !== false && isset($model) && isset($db)) {
|
||||
$this->records = array();
|
||||
$query = array(
|
||||
'fields' => $db->fields($model, null, array_keys($this->fields)),
|
||||
'table' => $db->fullTableName($model),
|
||||
'alias' => $model->alias,
|
||||
'conditions' => array(),
|
||||
'order' => null,
|
||||
'limit' => null,
|
||||
'group' => null
|
||||
);
|
||||
$records = $db->fetchAll($db->buildStatement($query, $model), false, $model->alias);
|
||||
|
||||
if ($records !== false && !empty($records)) {
|
||||
$this->records = Set::extract($records, '{n}.' . $model->alias);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!isset($this->table)) {
|
||||
$this->table = Inflector::underscore(Inflector::pluralize($this->name));
|
||||
}
|
||||
|
||||
if (!isset($this->primaryKey) && isset($this->fields['id'])) {
|
||||
$this->primaryKey = 'id';
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Run before all tests execute, should return SQL statement to create table for this fixture could be executed successfully.
|
||||
*
|
||||
* @param object $db An instance of the database object used to create the fixture table
|
||||
* @return boolean True on success, false on failure
|
||||
* @access public
|
||||
*/
|
||||
function create(&$db) {
|
||||
if (!isset($this->fields) || empty($this->fields)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
$this->Schema->_build(array($this->table => $this->fields));
|
||||
return (
|
||||
$db->execute($db->createSchema($this->Schema), array('log' => false)) !== false
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Run after all tests executed, should return SQL statement to drop table for this fixture.
|
||||
*
|
||||
* @param object $db An instance of the database object used to create the fixture table
|
||||
* @return boolean True on success, false on failure
|
||||
* @access public
|
||||
*/
|
||||
function drop(&$db) {
|
||||
$this->Schema->_build(array($this->table => $this->fields));
|
||||
return (
|
||||
$db->execute($db->dropSchema($this->Schema), array('log' => false)) !== false
|
||||
);
|
||||
}
|
||||
|
||||
/**
|
||||
* Run before each tests is executed, should return a set of SQL statements to insert records for the table
|
||||
* of this fixture could be executed successfully.
|
||||
*
|
||||
* @param object $db An instance of the database into which the records will be inserted
|
||||
* @return boolean on success or if there are no records to insert, or false on failure
|
||||
* @access public
|
||||
*/
|
||||
function insert(&$db) {
|
||||
if (!isset($this->_insert)) {
|
||||
$values = array();
|
||||
|
||||
if (isset($this->records) && !empty($this->records)) {
|
||||
foreach ($this->records as $record) {
|
||||
$fields = array_keys($record);
|
||||
$values[] = '(' . implode(', ', array_map(array(&$db, 'value'), array_values($record))) . ')';
|
||||
}
|
||||
return $db->insertMulti($this->table, $fields, $values);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Truncates the current fixture. Can be overwritten by classes extending CakeFixture to trigger other events before / after
|
||||
* truncate.
|
||||
*
|
||||
* @param object $db A reference to a db instance
|
||||
* @return boolean
|
||||
* @access public
|
||||
*/
|
||||
function truncate(&$db) {
|
||||
$fullDebug = $db->fullDebug;
|
||||
$db->fullDebug = false;
|
||||
$return = $db->truncate($this->table);
|
||||
$db->fullDebug = $fullDebug;
|
||||
return $return;
|
||||
}
|
||||
}
|
@@ -0,0 +1,31 @@
|
||||
<?php
|
||||
/**
|
||||
* Short description for file.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.libs
|
||||
* @since CakePHP(tm) v 1.2.0.4667
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
require_once LIBS.'model'.DS.'model.php';
|
||||
|
||||
/**
|
||||
* Short description for class.
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
*/
|
||||
class CakeTestModel extends Model {
|
||||
var $useDbConfig = 'test_suite';
|
||||
var $cacheSources = false;
|
||||
}
|
@@ -0,0 +1,249 @@
|
||||
<?php
|
||||
/**
|
||||
* CakeTestSuiteDispatcher controls dispatching TestSuite web based requests.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://cakephp.org CakePHP(tm) Project
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
* @since CakePHP(tm) v 1.3
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
require_once CAKE_TESTS_LIB . 'test_manager.php';
|
||||
|
||||
/**
|
||||
* CakeTestSuiteDispatcher handles web requests to the test suite and runs the correct action.
|
||||
*
|
||||
* @package cake.tests.libs
|
||||
*/
|
||||
class CakeTestSuiteDispatcher {
|
||||
/**
|
||||
* 'Request' parameters
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
var $params = array(
|
||||
'codeCoverage' => false,
|
||||
'group' => null,
|
||||
'case' => null,
|
||||
'app' => false,
|
||||
'plugin' => null,
|
||||
'output' => 'html',
|
||||
'show' => 'groups',
|
||||
'show_passes' => false
|
||||
);
|
||||
|
||||
/**
|
||||
* The classname for the TestManager being used
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $_managerClass = 'TestManager';
|
||||
|
||||
/**
|
||||
* The Instance of the Manager being used.
|
||||
*
|
||||
* @var TestManager subclass
|
||||
*/
|
||||
var $Manager;
|
||||
|
||||
/**
|
||||
* Baseurl for the request
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $_baseUrl;
|
||||
|
||||
/**
|
||||
* Base dir of the request. Used for accessing assets.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $_baseDir;
|
||||
|
||||
/**
|
||||
* constructor
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function CakeTestSuiteDispatcher() {
|
||||
$this->_baseUrl = $_SERVER['PHP_SELF'];
|
||||
$dir = rtrim(dirname($this->_baseUrl), '\\');
|
||||
$this->_baseDir = ($dir === '/') ? $dir : $dir . '/';
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs the actions required by the URL parameters.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function dispatch() {
|
||||
$this->_checkSimpleTest();
|
||||
$this->_parseParams();
|
||||
|
||||
if ($this->params['group']) {
|
||||
$this->_runGroupTest();
|
||||
} elseif ($this->params['case']) {
|
||||
$this->_runTestCase();
|
||||
} elseif (isset($_GET['show']) && $_GET['show'] == 'cases') {
|
||||
$this->_testCaseList();
|
||||
} else {
|
||||
$this->_groupTestList();
|
||||
}
|
||||
|
||||
$output = ob_get_clean();
|
||||
echo $output;
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks that simpleTest is installed. Will exit if it doesn't
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function _checkSimpleTest() {
|
||||
if (!App::import('Vendor', 'simpletest' . DS . 'reporter')) {
|
||||
$baseDir = $this->_baseDir;
|
||||
include CAKE_TESTS_LIB . 'templates' . DS . 'simpletest.php';
|
||||
exit();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks for the xdebug extension required to do code coverage. Displays an error
|
||||
* if xdebug isn't installed.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function _checkXdebug() {
|
||||
if (!extension_loaded('xdebug')) {
|
||||
$baseDir = $this->_baseDir;
|
||||
include CAKE_TESTS_LIB . 'templates' . DS . 'xdebug.php';
|
||||
exit();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates a page containing the a list of test cases that could be run.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function _testCaseList() {
|
||||
$Reporter =& $this->getReporter();
|
||||
$Reporter->paintDocumentStart();
|
||||
$Reporter->paintTestMenu();
|
||||
$Reporter->testCaseList();
|
||||
$Reporter->paintDocumentEnd();
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates a page containing a list of group tests that could be run.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function _groupTestList() {
|
||||
$Reporter =& $this->getReporter();
|
||||
$Reporter->paintDocumentStart();
|
||||
$Reporter->paintTestMenu();
|
||||
$Reporter->groupTestList();
|
||||
$Reporter->paintDocumentEnd();
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the Manager to use for the request.
|
||||
*
|
||||
* @return string The manager class name
|
||||
* @static
|
||||
*/
|
||||
function &getManager() {
|
||||
if (empty($this->Manager)) {
|
||||
$this->Manager = new $this->_managerClass();
|
||||
}
|
||||
return $this->Manager;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the reporter based on the request parameters
|
||||
*
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function &getReporter() {
|
||||
static $Reporter = NULL;
|
||||
if (!$Reporter) {
|
||||
$type = strtolower($this->params['output']);
|
||||
$coreClass = 'Cake' . ucwords($this->params['output']) . 'Reporter';
|
||||
$coreFile = CAKE_TESTS_LIB . 'reporter' . DS . 'cake_' . $type . '_reporter.php';
|
||||
|
||||
$appClass = $this->params['output'] . 'Reporter';
|
||||
$appFile = APPLIBS . 'test_suite' . DS . 'reporter' . DS . $type . '_reporter.php';
|
||||
if (include_once $coreFile) {
|
||||
$Reporter =& new $coreClass(null, $this->params);
|
||||
} elseif (include_once $appFile) {
|
||||
$Reporter =& new $appClass(null, $this->params);
|
||||
}
|
||||
}
|
||||
return $Reporter;
|
||||
}
|
||||
|
||||
/**
|
||||
* Parse url params into a 'request'
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function _parseParams() {
|
||||
if (!isset($_SERVER['SERVER_NAME'])) {
|
||||
$_SERVER['SERVER_NAME'] = '';
|
||||
}
|
||||
foreach ($this->params as $key => $value) {
|
||||
if (isset($_GET[$key])) {
|
||||
$this->params[$key] = $_GET[$key];
|
||||
}
|
||||
}
|
||||
if (isset($_GET['code_coverage'])) {
|
||||
$this->params['codeCoverage'] = true;
|
||||
require_once CAKE_TESTS_LIB . 'code_coverage_manager.php';
|
||||
$this->_checkXdebug();
|
||||
}
|
||||
$this->params['baseUrl'] = $this->_baseUrl;
|
||||
$this->params['baseDir'] = $this->_baseDir;
|
||||
$this->getManager();
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs the group test case.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function _runGroupTest() {
|
||||
$Reporter =& CakeTestSuiteDispatcher::getReporter();
|
||||
if ($this->params['codeCoverage']) {
|
||||
CodeCoverageManager::init($this->params['group'], $Reporter);
|
||||
}
|
||||
if ('all' == $this->params['group']) {
|
||||
$this->Manager->runAllTests($Reporter);
|
||||
} else {
|
||||
$this->Manager->runGroupTest(ucfirst($this->params['group']), $Reporter);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs a test case file.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function _runTestCase() {
|
||||
$Reporter =& CakeTestSuiteDispatcher::getReporter();
|
||||
if ($this->params['codeCoverage']) {
|
||||
CodeCoverageManager::init($this->params['case'], $Reporter);
|
||||
}
|
||||
$this->Manager->runTestCase($this->params['case'], $Reporter);
|
||||
}
|
||||
}
|
@@ -0,0 +1,33 @@
|
||||
<?php
|
||||
/**
|
||||
* CakeWebTestCase a simple wrapper around WebTestCase
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
|
||||
/**
|
||||
* Ignore base class.
|
||||
*/
|
||||
SimpleTest::ignore('CakeWebTestCase');
|
||||
|
||||
/**
|
||||
* Simple wrapper for the WebTestCase provided by SimpleTest
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
*/
|
||||
class CakeWebTestCase extends WebTestCase {
|
||||
}
|
@@ -0,0 +1,804 @@
|
||||
<?php
|
||||
/**
|
||||
* A class to manage all aspects for Code Coverage Analysis
|
||||
*
|
||||
* This class
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
App::import('Core', 'Folder');
|
||||
|
||||
/**
|
||||
* Short description for class.
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
*/
|
||||
class CodeCoverageManager {
|
||||
|
||||
/**
|
||||
* Is this an app test case?
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $appTest = false;
|
||||
|
||||
/**
|
||||
* Is this an app test case?
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $pluginTest = false;
|
||||
|
||||
/**
|
||||
* Is this a grouptest?
|
||||
*
|
||||
* @var string
|
||||
* @access public
|
||||
*/
|
||||
var $groupTest = false;
|
||||
|
||||
/**
|
||||
* The test case file to analyze
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $testCaseFile = '';
|
||||
|
||||
/**
|
||||
* The currently used CakeTestReporter
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $reporter = '';
|
||||
|
||||
/**
|
||||
* undocumented variable
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $numDiffContextLines = 7;
|
||||
|
||||
/**
|
||||
* Returns a singleton instance
|
||||
*
|
||||
* @return object
|
||||
* @access public
|
||||
*/
|
||||
function &getInstance() {
|
||||
static $instance = array();
|
||||
if (!$instance) {
|
||||
$instance[0] =& new CodeCoverageManager();
|
||||
}
|
||||
return $instance[0];
|
||||
}
|
||||
|
||||
/**
|
||||
* Initializes a new Coverage Analyzation for a given test case file
|
||||
*
|
||||
* @param string $testCaseFile The test case file being covered.
|
||||
* @param object $reporter Instance of the reporter running.
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function init($testCaseFile, &$reporter) {
|
||||
$manager =& CodeCoverageManager::getInstance();
|
||||
$manager->reporter =& $reporter;
|
||||
$testCaseFile = str_replace(DS . DS, DS, $testCaseFile);
|
||||
$thisFile = str_replace('.php', '.test.php', basename(__FILE__));
|
||||
|
||||
if (strpos($testCaseFile, $thisFile) !== false) {
|
||||
trigger_error(__('Xdebug supports no parallel coverage analysis - so this is not possible.', true), E_USER_ERROR);
|
||||
}
|
||||
$manager->setParams($reporter);
|
||||
$manager->testCaseFile = $testCaseFile;
|
||||
}
|
||||
|
||||
/**
|
||||
* Start/resume Code coverage collection.
|
||||
*
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function start() {
|
||||
xdebug_start_code_coverage(XDEBUG_CC_UNUSED | XDEBUG_CC_DEAD_CODE);
|
||||
}
|
||||
|
||||
/**
|
||||
* Stops/pauses code coverage collection. Does not clean the
|
||||
* code coverage memory. Use clean() to clear code coverage memory
|
||||
*
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function stop() {
|
||||
xdebug_stop_code_coverage(false);
|
||||
}
|
||||
|
||||
/**
|
||||
* Clears the existing code coverage information. Also stops any
|
||||
* running collection.
|
||||
*
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function clear() {
|
||||
xdebug_stop_code_coverage();
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the parameters from a reporter to the CodeCoverageManager
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function setParams(&$reporter) {
|
||||
if ($reporter->params['app']) {
|
||||
$this->appTest = true;
|
||||
}
|
||||
|
||||
if ($reporter->params['group']) {
|
||||
$this->groupTest = true;
|
||||
}
|
||||
|
||||
if ($reporter->params['plugin']) {
|
||||
$this->pluginTest = Inflector::underscore($reporter->params['plugin']);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Stops the current code coverage analyzation and dumps a nice report
|
||||
* depending on the reporter that was passed to start()
|
||||
*
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function report($output = true) {
|
||||
$manager =& CodeCoverageManager::getInstance();
|
||||
|
||||
CodeCoverageManager::stop();
|
||||
CodeCoverageManager::clear();
|
||||
|
||||
list($coverageData, $testObjectFile) = $manager->_getCoverageData();
|
||||
|
||||
if (empty($coverageData) && $output) {
|
||||
echo "The test object file is never loaded.\n";
|
||||
}
|
||||
|
||||
if (!$manager->groupTest) {
|
||||
$execCodeLines = $manager->__getExecutableLines(file_get_contents($testObjectFile));
|
||||
$result = '';
|
||||
|
||||
switch (get_class($manager->reporter)) {
|
||||
case 'CakeHtmlReporter':
|
||||
$result = $manager->reportCaseHtmlDiff(@file($testObjectFile), $coverageData, $execCodeLines, $manager->numDiffContextLines);
|
||||
break;
|
||||
case 'CakeCliReporter':
|
||||
default:
|
||||
$result = $manager->reportCaseCli(@file($testObjectFile), $coverageData, $execCodeLines, $manager->numDiffContextLines);
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
$execCodeLines = $manager->__getExecutableLines($testObjectFile);
|
||||
$result = '';
|
||||
|
||||
switch (get_class($manager->reporter)) {
|
||||
case 'CakeHtmlReporter':
|
||||
$result = $manager->reportGroupHtml($testObjectFile, $coverageData, $execCodeLines, $manager->numDiffContextLines);
|
||||
break;
|
||||
case 'CakeCliReporter':
|
||||
default:
|
||||
$result = $manager->reportGroupCli($testObjectFile, $coverageData, $execCodeLines, $manager->numDiffContextLines);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if ($output) {
|
||||
echo $result;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the coverage data for the test case or group test that is being run.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function _getCoverageData() {
|
||||
$coverageData = array();
|
||||
$dump = xdebug_get_code_coverage();
|
||||
|
||||
if ($this->groupTest) {
|
||||
$testObjectFile = $this->__testObjectFilesFromGroupFile($this->testCaseFile, $this->appTest);
|
||||
foreach ($testObjectFile as $file) {
|
||||
if (!file_exists($file)) {
|
||||
trigger_error(sprintf(__('This test object file is invalid: %s', true), $file));
|
||||
return ;
|
||||
}
|
||||
}
|
||||
foreach ($testObjectFile as $file) {
|
||||
if (isset($dump[$file])) {
|
||||
$coverageData[$file] = $dump[$file];
|
||||
}
|
||||
}
|
||||
} else {
|
||||
$testObjectFile = $this->__testObjectFileFromCaseFile($this->testCaseFile, $this->appTest);
|
||||
|
||||
if (!file_exists($testObjectFile)) {
|
||||
trigger_error(sprintf(__('This test object file is invalid: %s', true), $testObjectFile));
|
||||
return ;
|
||||
}
|
||||
|
||||
if (isset($dump[$testObjectFile])) {
|
||||
$coverageData = $dump[$testObjectFile];
|
||||
}
|
||||
}
|
||||
return array($coverageData, $testObjectFile);
|
||||
}
|
||||
|
||||
/**
|
||||
* Diff reporting
|
||||
*
|
||||
* @param string $testObjectFile
|
||||
* @param string $coverageData
|
||||
* @param string $execCodeLines
|
||||
* @param string $output
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function reportCaseHtmlDiff($testObjectFile, $coverageData, $execCodeLines, $numContextLines) {
|
||||
$manager = CodeCoverageManager::getInstance();
|
||||
$total = count($testObjectFile);
|
||||
$lines = array();
|
||||
|
||||
for ($i = 1; $i < $total + 1; $i++) {
|
||||
$foundByManualFinder = isset($execCodeLines[$i]) && trim($execCodeLines[$i]) != '';
|
||||
$foundByXdebug = isset($coverageData[$i]);
|
||||
|
||||
if (!$foundByManualFinder || !$foundByXdebug || $coverageData[$i] === -2) {
|
||||
if (isset($lines[$i])) {
|
||||
$lines[$i] = 'ignored ' . $lines[$i];
|
||||
} else {
|
||||
$lines[$i] = 'ignored';
|
||||
}
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($coverageData[$i] !== -1) {
|
||||
if (isset($lines[$i])) {
|
||||
$lines[$i] = 'covered ' . $lines[$i];
|
||||
} else {
|
||||
$lines[$i] = 'covered';
|
||||
}
|
||||
continue;
|
||||
}
|
||||
$lines[$i] = 'uncovered show';
|
||||
$foundEndBlockInContextSearch = false;
|
||||
|
||||
for ($j = 1; $j <= $numContextLines; $j++) {
|
||||
$key = $i - $j;
|
||||
|
||||
if ($key > 0 && isset($lines[$key])) {
|
||||
if (strpos($lines[$key], 'end') !== false) {
|
||||
$foundEndBlockInContextSearch = true;
|
||||
if ($j < $numContextLines) {
|
||||
$lines[$key] = str_replace('end', '', $lines[$key-1]);
|
||||
}
|
||||
}
|
||||
|
||||
if (strpos($lines[$key], 'uncovered') === false) {
|
||||
if (strpos($lines[$key], 'covered') !== false) {
|
||||
$lines[$key] .= ' show';
|
||||
} else {
|
||||
$lines[$key] = 'ignored show';
|
||||
}
|
||||
}
|
||||
|
||||
if ($j == $numContextLines) {
|
||||
$lineBeforeIsEndBlock = strpos($lines[$key-1], 'end') !== false;
|
||||
$lineBeforeIsShown = strpos($lines[$key-1], 'show') !== false;
|
||||
$lineBeforeIsUncovered = strpos($lines[$key-1], 'uncovered') !== false;
|
||||
|
||||
if (!$foundEndBlockInContextSearch && !$lineBeforeIsUncovered && ($lineBeforeIsEndBlock)) {
|
||||
$lines[$key-1] = str_replace('end', '', $lines[$key-1]);
|
||||
}
|
||||
|
||||
if (!$lineBeforeIsShown && !$lineBeforeIsUncovered) {
|
||||
$lines[$key] .= ' start';
|
||||
}
|
||||
}
|
||||
}
|
||||
$key = $i + $j;
|
||||
|
||||
if ($key < $total) {
|
||||
$lines[$key] = 'show';
|
||||
|
||||
if ($j == $numContextLines) {
|
||||
$lines[$key] .= ' end';
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// find the last "uncovered" or "show"n line and "end" its block
|
||||
$lastShownLine = $manager->__array_strpos($lines, 'show', true);
|
||||
if (isset($lines[$lastShownLine])) {
|
||||
$lines[$lastShownLine] .= ' end';
|
||||
}
|
||||
|
||||
// give the first start line another class so we can control the top padding of the entire results
|
||||
$firstShownLine = $manager->__array_strpos($lines, 'show');
|
||||
if (isset($lines[$firstShownLine])) {
|
||||
$lines[$firstShownLine] .= ' realstart';
|
||||
}
|
||||
|
||||
// get the output
|
||||
$lineCount = $coveredCount = 0;
|
||||
$report = '';
|
||||
foreach ($testObjectFile as $num => $line) {
|
||||
// start line count at 1
|
||||
$num++;
|
||||
$class = $lines[$num];
|
||||
|
||||
if (strpos($class, 'ignored') === false) {
|
||||
$lineCount++;
|
||||
|
||||
if (strpos($class, 'covered') !== false && strpos($class, 'uncovered') === false) {
|
||||
$coveredCount++;
|
||||
}
|
||||
}
|
||||
|
||||
if (strpos($class, 'show') !== false) {
|
||||
$report .= $manager->__paintCodeline($class, $num, $line);
|
||||
}
|
||||
}
|
||||
return $manager->__paintHeader($lineCount, $coveredCount, $report);
|
||||
}
|
||||
|
||||
/**
|
||||
* CLI reporting
|
||||
*
|
||||
* @param string $testObjectFile
|
||||
* @param string $coverageData
|
||||
* @param string $execCodeLines
|
||||
* @param string $output
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function reportCaseCli($testObjectFile, $coverageData, $execCodeLines) {
|
||||
$manager = CodeCoverageManager::getInstance();
|
||||
$lineCount = $coveredCount = 0;
|
||||
$report = '';
|
||||
|
||||
foreach ($testObjectFile as $num => $line) {
|
||||
$num++;
|
||||
$foundByManualFinder = isset($execCodeLines[$num]) && trim($execCodeLines[$num]) != '';
|
||||
$foundByXdebug = isset($coverageData[$num]) && $coverageData[$num] !== -2;
|
||||
|
||||
if ($foundByManualFinder && $foundByXdebug) {
|
||||
$lineCount++;
|
||||
|
||||
if ($coverageData[$num] > 0) {
|
||||
$coveredCount++;
|
||||
}
|
||||
}
|
||||
}
|
||||
return $manager->__paintHeaderCli($lineCount, $coveredCount, $report);
|
||||
}
|
||||
|
||||
/**
|
||||
* Diff reporting
|
||||
*
|
||||
* @param string $testObjectFile
|
||||
* @param string $coverageData
|
||||
* @param string $execCodeLines
|
||||
* @param string $output
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function reportGroupHtml($testObjectFiles, $coverageData, $execCodeLines, $numContextLines) {
|
||||
$manager = CodeCoverageManager::getInstance();
|
||||
$report = '';
|
||||
|
||||
foreach ($testObjectFiles as $testObjectFile) {
|
||||
$lineCount = $coveredCount = 0;
|
||||
$objFilename = $testObjectFile;
|
||||
$testObjectFile = file($testObjectFile);
|
||||
|
||||
foreach ($testObjectFile as $num => $line) {
|
||||
$num++;
|
||||
$foundByManualFinder = isset($execCodeLines[$objFilename][$num]) && trim($execCodeLines[$objFilename][$num]) != '';
|
||||
$foundByXdebug = isset($coverageData[$objFilename][$num]) && $coverageData[$objFilename][$num] !== -2;
|
||||
|
||||
if ($foundByManualFinder && $foundByXdebug) {
|
||||
$class = 'uncovered';
|
||||
$lineCount++;
|
||||
|
||||
if ($coverageData[$objFilename][$num] > 0) {
|
||||
$class = 'covered';
|
||||
$coveredCount++;
|
||||
}
|
||||
} else {
|
||||
$class = 'ignored';
|
||||
}
|
||||
}
|
||||
$report .= $manager->__paintGroupResultLine($objFilename, $lineCount, $coveredCount);
|
||||
}
|
||||
return $manager->__paintGroupResultHeader($report);
|
||||
}
|
||||
|
||||
/**
|
||||
* CLI reporting
|
||||
*
|
||||
* @param string $testObjectFile
|
||||
* @param string $coverageData
|
||||
* @param string $execCodeLines
|
||||
* @param string $output
|
||||
* @return void
|
||||
* @static
|
||||
*/
|
||||
function reportGroupCli($testObjectFiles, $coverageData, $execCodeLines) {
|
||||
$manager = CodeCoverageManager::getInstance();
|
||||
$report = '';
|
||||
|
||||
foreach ($testObjectFiles as $testObjectFile) {
|
||||
$lineCount = $coveredCount = 0;
|
||||
$objFilename = $testObjectFile;
|
||||
$testObjectFile = file($testObjectFile);
|
||||
|
||||
foreach ($testObjectFile as $num => $line) {
|
||||
$num++;
|
||||
$foundByManualFinder = isset($execCodeLines[$objFilename][$num]) && trim($execCodeLines[$objFilename][$num]) != '';
|
||||
$foundByXdebug = isset($coverageData[$objFilename][$num]) && $coverageData[$objFilename][$num] !== -2;
|
||||
|
||||
if ($foundByManualFinder && $foundByXdebug) {
|
||||
$lineCount++;
|
||||
|
||||
if ($coverageData[$objFilename][$num] > 0) {
|
||||
$coveredCount++;
|
||||
}
|
||||
}
|
||||
}
|
||||
$report .= $manager->__paintGroupResultLineCli($objFilename, $lineCount, $coveredCount);
|
||||
}
|
||||
return $report;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the name of the test object file based on a given test case file name
|
||||
*
|
||||
* @param string $file
|
||||
* @param string $isApp
|
||||
* @return string name of the test object file
|
||||
* @access private
|
||||
*/
|
||||
function __testObjectFileFromCaseFile($file, $isApp = true) {
|
||||
$manager = CodeCoverageManager::getInstance();
|
||||
$path = $manager->__getTestFilesPath($isApp);
|
||||
$folderPrefixMap = array(
|
||||
'behaviors' => 'models',
|
||||
'components' => 'controllers',
|
||||
'helpers' => 'views'
|
||||
);
|
||||
|
||||
foreach ($folderPrefixMap as $dir => $prefix) {
|
||||
if (strpos($file, $dir) === 0) {
|
||||
$path .= $prefix . DS;
|
||||
break;
|
||||
}
|
||||
}
|
||||
$testManager =& new TestManager();
|
||||
$testFile = str_replace(array('/', $testManager->_testExtension), array(DS, '.php'), $file);
|
||||
|
||||
$folder =& new Folder();
|
||||
$folder->cd(ROOT . DS . CAKE_TESTS_LIB);
|
||||
$contents = $folder->read();
|
||||
|
||||
if (in_array(basename($testFile), $contents[1])) {
|
||||
$testFile = basename($testFile);
|
||||
$path = ROOT . DS . CAKE_TESTS_LIB;
|
||||
}
|
||||
$path .= $testFile;
|
||||
$realpath = realpath($path);
|
||||
|
||||
if ($realpath) {
|
||||
return $realpath;
|
||||
}
|
||||
return $path;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns an array of names of the test object files based on a given test group file name
|
||||
*
|
||||
* @param array $files
|
||||
* @param string $isApp
|
||||
* @return array names of the test object files
|
||||
* @access private
|
||||
*/
|
||||
function __testObjectFilesFromGroupFile($groupFile, $isApp = true) {
|
||||
$manager = CodeCoverageManager::getInstance();
|
||||
$testManager =& new TestManager();
|
||||
|
||||
$path = TESTS;
|
||||
if (!$isApp) {
|
||||
$path = ROOT . DS . 'cake' . DS . 'tests';
|
||||
}
|
||||
if (!!$manager->pluginTest) {
|
||||
$path = App::pluginPath($manager->pluginTest) . DS . 'tests';
|
||||
}
|
||||
|
||||
$result = array();
|
||||
if ($groupFile == 'all') {
|
||||
$files = array_keys($testManager->getTestCaseList());
|
||||
foreach ($files as $file) {
|
||||
$file = str_replace(DS . 'tests' . DS . 'cases' . DS, DS, $file);
|
||||
$file = str_replace('.test.php', '.php', $file);
|
||||
$file = str_replace(DS . DS, DS, $file);
|
||||
$result[] = $file;
|
||||
}
|
||||
} else {
|
||||
$path .= DS . 'groups' . DS . $groupFile . $testManager->_groupExtension;
|
||||
if (!file_exists($path)) {
|
||||
trigger_error(__('This group file does not exist!', true));
|
||||
return array();
|
||||
}
|
||||
|
||||
$result = array();
|
||||
$groupContent = file_get_contents($path);
|
||||
$ds = '\s*\.\s*DS\s*\.\s*';
|
||||
$pluginTest = 'APP\.\'plugins\'' . $ds . '\'' . $manager->pluginTest . '\'' . $ds . '\'tests\'' . $ds . '\'cases\'';
|
||||
$pluginTest .= '|App::pluginPath\(\'' . $manager->pluginTest . '\'\)' . $ds . '\'tests\'' . $ds . '\'cases\'';
|
||||
$pattern = '/\s*TestManager::addTestFile\(\s*\$this,\s*(' . $pluginTest . '|APP_TEST_CASES|CORE_TEST_CASES)' . $ds . '(.*?)\)/i';
|
||||
preg_match_all($pattern, $groupContent, $matches);
|
||||
|
||||
foreach ($matches[2] as $file) {
|
||||
$patterns = array(
|
||||
'/\s*\.\s*DS\s*\.\s*/',
|
||||
'/\s*APP_TEST_CASES\s*/',
|
||||
'/\s*CORE_TEST_CASES\s*/',
|
||||
);
|
||||
|
||||
$replacements = array(DS, '', '');
|
||||
$file = preg_replace($patterns, $replacements, $file);
|
||||
$file = str_replace("'", '', $file);
|
||||
$result[] = $manager->__testObjectFileFromCaseFile($file, $isApp) . '.php';
|
||||
}
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses a given code string into an array of lines and replaces some non-executable code lines with the needed
|
||||
* amount of new lines in order for the code line numbers to stay in sync
|
||||
*
|
||||
* @param string $content
|
||||
* @return array array of lines
|
||||
* @access private
|
||||
*/
|
||||
function __getExecutableLines($content) {
|
||||
if (is_array($content)) {
|
||||
$manager =& CodeCoverageManager::getInstance();
|
||||
$result = array();
|
||||
foreach ($content as $file) {
|
||||
$result[$file] = $manager->__getExecutableLines(file_get_contents($file));
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
$content = h($content);
|
||||
// arrays are 0-indexed, but we want 1-indexed stuff now as we are talking code lines mind you (**)
|
||||
$content = "\n" . $content;
|
||||
// // strip unwanted lines
|
||||
$content = preg_replace_callback("/(@codeCoverageIgnoreStart.*?@codeCoverageIgnoreEnd)/is", array('CodeCoverageManager', '__replaceWithNewlines'), $content);
|
||||
// strip php | ?\> tag only lines
|
||||
$content = preg_replace('/[ |\t]*[<\?php|\?>]+[ |\t]*/', '', $content);
|
||||
|
||||
// strip lines that contain only braces and parenthesis
|
||||
$content = preg_replace('/[ |\t]*[{|}|\(|\)]+[ |\t]*/', '', $content);
|
||||
$result = explode("\n", $content);
|
||||
// unset the zero line again to get the original line numbers, but starting at 1, see (**)
|
||||
unset($result[0]);
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Replaces a given arg with the number of newlines in it
|
||||
*
|
||||
* @return string the number of newlines in a given arg
|
||||
* @access private
|
||||
*/
|
||||
function __replaceWithNewlines() {
|
||||
$args = func_get_args();
|
||||
$numLineBreaks = count(explode("\n", $args[0][0]));
|
||||
return str_pad('', $numLineBreaks - 1, "\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the headline for code coverage analysis
|
||||
*
|
||||
* @param string $codeCoverage
|
||||
* @param string $report
|
||||
* @return void
|
||||
* @access private
|
||||
*/
|
||||
function __paintHeader($lineCount, $coveredCount, $report) {
|
||||
$manager =& CodeCoverageManager::getInstance();
|
||||
$codeCoverage = $manager->__calcCoverage($lineCount, $coveredCount);
|
||||
return $report = '<h2>Code Coverage: ' . $codeCoverage . '%</h2>
|
||||
<div class="code-coverage-results"><pre>' . $report . '</pre></div>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Displays a notification concerning group test results
|
||||
*
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function __paintGroupResultHeader($report) {
|
||||
return '<div class="code-coverage-results"><p class="note">Please keep in mind that the coverage can vary a little bit depending on how much the different tests in the group interfere. If for example, TEST A calls a line from TEST OBJECT B, the coverage for TEST OBJECT B will be a little greater than if you were running the corresponding test case for TEST OBJECT B alone.</p><pre>' . $report . '</pre></div>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the headline for code coverage analysis
|
||||
*
|
||||
* @param string $codeCoverage
|
||||
* @param string $report
|
||||
* @return void
|
||||
* @access private
|
||||
*/
|
||||
function __paintGroupResultLine($file, $lineCount, $coveredCount) {
|
||||
$manager =& CodeCoverageManager::getInstance();
|
||||
$codeCoverage = $manager->__calcCoverage($lineCount, $coveredCount);
|
||||
$class = 'result-bad';
|
||||
|
||||
if ($codeCoverage > 50) {
|
||||
$class = 'result-ok';
|
||||
}
|
||||
if ($codeCoverage > 80) {
|
||||
$class = 'result-good';
|
||||
}
|
||||
return '<p>Code Coverage for ' . $file . ': <span class="' . $class . '">' . $codeCoverage . '%</span></p>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the headline for code coverage analysis
|
||||
*
|
||||
* @param string $codeCoverage
|
||||
* @param string $report
|
||||
* @return void
|
||||
* @access private
|
||||
*/
|
||||
function __paintGroupResultLineCli($file, $lineCount, $coveredCount) {
|
||||
$manager =& CodeCoverageManager::getInstance();
|
||||
$codeCoverage = $manager->__calcCoverage($lineCount, $coveredCount);
|
||||
$class = 'bad';
|
||||
if ($codeCoverage > 50) {
|
||||
$class = 'ok';
|
||||
}
|
||||
if ($codeCoverage > 80) {
|
||||
$class = 'good';
|
||||
}
|
||||
return "\n" . 'Code Coverage for ' . $file . ': ' . $codeCoverage . '% (' . $class . ')' . "\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the headline for code coverage analysis in the CLI
|
||||
*
|
||||
* @param string $codeCoverage
|
||||
* @param string $report
|
||||
* @return void
|
||||
* @access private
|
||||
*/
|
||||
function __paintHeaderCli($lineCount, $coveredCount, $report) {
|
||||
$manager =& CodeCoverageManager::getInstance();
|
||||
$codeCoverage = $manager->__calcCoverage($lineCount, $coveredCount);
|
||||
$class = 'bad';
|
||||
if ($codeCoverage > 50) {
|
||||
$class = 'ok';
|
||||
}
|
||||
if ($codeCoverage > 80) {
|
||||
$class = 'good';
|
||||
}
|
||||
return $report = "Code Coverage: $codeCoverage% ($class)\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints a code line for html output
|
||||
*
|
||||
* @package default
|
||||
* @access private
|
||||
*/
|
||||
function __paintCodeline($class, $num, $line) {
|
||||
$line = h($line);
|
||||
|
||||
if (trim($line) == '') {
|
||||
$line = ' '; // Win IE fix
|
||||
}
|
||||
return '<div class="code-line ' . trim($class) . '"><span class="line-num">' . $num . '</span><span class="content">' . $line . '</span></div>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Calculates the coverage percentage based on a line count and a covered line count
|
||||
*
|
||||
* @param string $lineCount
|
||||
* @param string $coveredCount
|
||||
* @return void
|
||||
* @access private
|
||||
*/
|
||||
function __calcCoverage($lineCount, $coveredCount) {
|
||||
if ($coveredCount > $lineCount) {
|
||||
trigger_error(__('Sorry, you cannot have more covered lines than total lines!', true));
|
||||
}
|
||||
return ($lineCount != 0)
|
||||
? round(100 * $coveredCount / $lineCount, 2)
|
||||
: '0.00';
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets us the base path to look for the test files
|
||||
*
|
||||
* @param string $isApp
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function __getTestFilesPath($isApp = true) {
|
||||
$manager = CodeCoverageManager::getInstance();
|
||||
$path = ROOT . DS;
|
||||
|
||||
if ($isApp) {
|
||||
$path .= APP_DIR . DS;
|
||||
} elseif (!!$manager->pluginTest) {
|
||||
$pluginPath = APP . 'plugins' . DS . $manager->pluginTest . DS;
|
||||
|
||||
$pluginPaths = App::path('plugins');
|
||||
foreach ($pluginPaths as $tmpPath) {
|
||||
$tmpPath = $tmpPath . $manager->pluginTest . DS;
|
||||
if (file_exists($tmpPath)) {
|
||||
$pluginPath = $tmpPath;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
$path = $pluginPath;
|
||||
} else {
|
||||
$path = TEST_CAKE_CORE_INCLUDE_PATH;
|
||||
}
|
||||
|
||||
return $path;
|
||||
}
|
||||
|
||||
/**
|
||||
* Finds the last element of an array that contains $needle in a strpos computation
|
||||
*
|
||||
* @param array $arr
|
||||
* @param string $needle
|
||||
* @return void
|
||||
* @access private
|
||||
*/
|
||||
function __array_strpos($arr, $needle, $reverse = false) {
|
||||
if (!is_array($arr) || empty($arr)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if ($reverse) {
|
||||
$arr = array_reverse($arr, true);
|
||||
}
|
||||
|
||||
foreach ($arr as $key => $val) {
|
||||
if (strpos($val, $needle) !== false) {
|
||||
return $key;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
@@ -0,0 +1,225 @@
|
||||
<?php
|
||||
/**
|
||||
* CakeBaseReporter contains common functionality to all cake test suite reporters.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://cakephp.org CakePHP(tm) Project
|
||||
* @package cake
|
||||
* @subpackage cake.tests.libs.reporter
|
||||
* @since CakePHP(tm) v 1.3
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
|
||||
/**
|
||||
* CakeBaseReporter contains common reporting features used in the CakePHP Test suite
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.tests.lib
|
||||
*/
|
||||
class CakeBaseReporter extends SimpleReporter {
|
||||
|
||||
/**
|
||||
* Time the test runs started.
|
||||
*
|
||||
* @var integer
|
||||
* @access protected
|
||||
*/
|
||||
var $_timeStart = 0;
|
||||
|
||||
/**
|
||||
* Time the test runs ended
|
||||
*
|
||||
* @var integer
|
||||
* @access protected
|
||||
*/
|
||||
var $_timeEnd = 0;
|
||||
|
||||
/**
|
||||
* Duration of all test methods.
|
||||
*
|
||||
* @var integer
|
||||
* @access protected
|
||||
*/
|
||||
var $_timeDuration = 0;
|
||||
|
||||
/**
|
||||
* Array of request parameters. Usually parsed GET params.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
var $params = array();
|
||||
|
||||
/**
|
||||
* Character set for the output of test reporting.
|
||||
*
|
||||
* @var string
|
||||
* @access protected
|
||||
*/
|
||||
var $_characterSet;
|
||||
|
||||
/**
|
||||
* Does nothing yet. The first output will
|
||||
* be sent on the first test start.
|
||||
*
|
||||
* ### Params
|
||||
*
|
||||
* - show_passes - Should passes be shown
|
||||
* - plugin - Plugin test being run?
|
||||
* - app - App test being run.
|
||||
* - case - The case being run
|
||||
* - codeCoverage - Whether the case/group being run is being code covered.
|
||||
*
|
||||
* @param string $charset The character set to output with. Defaults to UTF-8
|
||||
* @param array $params Array of request parameters the reporter should use. See above.
|
||||
* @access public
|
||||
*/
|
||||
function CakeBaseReporter($charset = 'utf-8', $params = array()) {
|
||||
$this->SimpleReporter();
|
||||
if (!$charset) {
|
||||
$charset = 'utf-8';
|
||||
}
|
||||
$this->_characterSet = $charset;
|
||||
$this->params = $params;
|
||||
}
|
||||
|
||||
/**
|
||||
* Signals / Paints the beginning of a TestSuite executing.
|
||||
* Starts the timer for the TestSuite execution time.
|
||||
*
|
||||
* @param string $test_name Name of the test that is being run.
|
||||
* @param integer $size
|
||||
* @return void
|
||||
*/
|
||||
function paintGroupStart($test_name, $size) {
|
||||
if (empty($this->_timeStart)) {
|
||||
$this->_timeStart = $this->_getTime();
|
||||
}
|
||||
parent::paintGroupStart($test_name, $size);
|
||||
}
|
||||
|
||||
/**
|
||||
* Signals/Paints the end of a TestSuite. All test cases have run
|
||||
* and timers are stopped.
|
||||
*
|
||||
* @param string $test_name Name of the test that is being run.
|
||||
* @return void
|
||||
*/
|
||||
function paintGroupEnd($test_name) {
|
||||
$this->_timeEnd = $this->_getTime();
|
||||
$this->_timeDuration = $this->_timeEnd - $this->_timeStart;
|
||||
parent::paintGroupEnd($test_name);
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the beginning of a test method being run. This is used
|
||||
* to start/resume the code coverage tool.
|
||||
*
|
||||
* @param string $method The method name being run.
|
||||
* @return void
|
||||
*/
|
||||
function paintMethodStart($method) {
|
||||
parent::paintMethodStart($method);
|
||||
if (!empty($this->params['codeCoverage'])) {
|
||||
CodeCoverageManager::start();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the end of a test method being run. This is used
|
||||
* to pause the collection of code coverage if its being used.
|
||||
*
|
||||
* @param string $method The name of the method being run.
|
||||
* @return void
|
||||
*/
|
||||
function paintMethodEnd($method) {
|
||||
parent::paintMethodEnd($method);
|
||||
if (!empty($this->params['codeCoverage'])) {
|
||||
CodeCoverageManager::stop();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the current time in microseconds. Similar to getMicrotime in basics.php
|
||||
* but in a separate function to reduce dependancies.
|
||||
*
|
||||
* @return float Time in microseconds
|
||||
* @access protected
|
||||
*/
|
||||
function _getTime() {
|
||||
list($usec, $sec) = explode(' ', microtime());
|
||||
return ((float)$sec + (float)$usec);
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves a list of test cases from the active Manager class,
|
||||
* displaying it in the correct format for the reporter subclass
|
||||
*
|
||||
* @return mixed
|
||||
*/
|
||||
function testCaseList() {
|
||||
$testList = TestManager::getTestCaseList();
|
||||
return $testList;
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves a list of group test cases from the active Manager class
|
||||
* displaying it in the correct format for the reporter subclass.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function groupTestList() {
|
||||
$testList = TestManager::getGroupTestList();
|
||||
return $testList;
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the start of the response from the test suite.
|
||||
* Used to paint things like head elements in an html page.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function paintDocumentStart() {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the end of the response from the test suite.
|
||||
* Used to paint things like </body> in an html page.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function paintDocumentEnd() {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Paint a list of test sets, core, app, and plugin test sets
|
||||
* available.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function paintTestMenu() {
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the baseUrl if one is available.
|
||||
*
|
||||
* @return string The base url for the request.
|
||||
*/
|
||||
function baseUrl() {
|
||||
if (!empty($_SERVER['PHP_SELF'])) {
|
||||
return $_SERVER['PHP_SELF'];
|
||||
}
|
||||
return '';
|
||||
}
|
||||
|
||||
}
|
@@ -0,0 +1,178 @@
|
||||
<?php
|
||||
/**
|
||||
* Cake CLI test reporter.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.libs
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
if (version_compare(PHP_VERSION, '4.4.4', '<=') ||
|
||||
PHP_SAPI == 'cgi') {
|
||||
define('STDOUT', fopen('php://stdout', 'w'));
|
||||
define('STDERR', fopen('php://stderr', 'w'));
|
||||
register_shutdown_function(create_function('', 'fclose(STDOUT); fclose(STDERR); return true;'));
|
||||
}
|
||||
|
||||
include_once dirname(__FILE__) . DS . 'cake_base_reporter.php';
|
||||
|
||||
/**
|
||||
* Minimal command line test displayer. Writes fail details to STDERR. Returns 0
|
||||
* to the shell if all tests pass, ST_FAILS_RETURN_CODE if any test fails.
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.tests.libs.reporter
|
||||
*/
|
||||
class CakeCliReporter extends CakeBaseReporter {
|
||||
/**
|
||||
* separator string for fail, error, exception, and skip messages.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $separator = '->';
|
||||
|
||||
/**
|
||||
* array of 'request' parameters
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
var $params = array();
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param string $separator
|
||||
* @param array $params
|
||||
* @return void
|
||||
*/
|
||||
function CakeCLIReporter($charset = 'utf-8', $params = array()) {
|
||||
$this->CakeBaseReporter($charset, $params);
|
||||
}
|
||||
|
||||
function setFailDetailSeparator($separator) {
|
||||
$this->separator = $separator;
|
||||
}
|
||||
|
||||
/**
|
||||
* Paint fail faildetail to STDERR.
|
||||
*
|
||||
* @param string $message Message of the fail.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintFail($message) {
|
||||
parent::paintFail($message);
|
||||
$message .= $this->_getBreadcrumb();
|
||||
fwrite(STDERR, 'FAIL' . $this->separator . $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* Paint PHP errors to STDERR.
|
||||
*
|
||||
* @param string $message Message of the Error
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintError($message) {
|
||||
parent::paintError($message);
|
||||
$message .= $this->_getBreadcrumb();
|
||||
fwrite(STDERR, 'ERROR' . $this->separator . $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* Paint exception faildetail to STDERR.
|
||||
*
|
||||
* @param string $message Message of the Error
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintException($exception) {
|
||||
parent::paintException($exception);
|
||||
$message .= sprintf('Unexpected exception of type [%s] with message [%s] in [%s] line [%s]',
|
||||
get_class($exception),
|
||||
$exception->getMessage(),
|
||||
$exception->getFile(),
|
||||
$exception->getLine()
|
||||
);
|
||||
$message .= $this->_getBreadcrumb();
|
||||
fwrite(STDERR, 'EXCEPTION' . $this->separator . $message);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the breadcrumb trail for the current test method/case
|
||||
*
|
||||
* @return string The string for the breadcrumb
|
||||
*/
|
||||
function _getBreadcrumb() {
|
||||
$breadcrumb = $this->getTestList();
|
||||
array_shift($breadcrumb);
|
||||
$out = "\n\tin " . implode("\n\tin ", array_reverse($breadcrumb));
|
||||
$out .= "\n\n";
|
||||
return $out;
|
||||
}
|
||||
|
||||
/**
|
||||
* Paint a test skip message
|
||||
*
|
||||
* @param string $message The message of the skip
|
||||
* @return void
|
||||
*/
|
||||
function paintSkip($message) {
|
||||
parent::paintSkip($message);
|
||||
fwrite(STDOUT, 'SKIP' . $this->separator . $message . "\n\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* Paint a footer with test case name, timestamp, counts of fails and exceptions.
|
||||
*/
|
||||
function paintFooter($test_name) {
|
||||
$buffer = $this->getTestCaseProgress() . '/' . $this->getTestCaseCount() . ' test cases complete: ';
|
||||
|
||||
if (0 < ($this->getFailCount() + $this->getExceptionCount())) {
|
||||
$buffer .= $this->getPassCount() . " passes";
|
||||
if (0 < $this->getFailCount()) {
|
||||
$buffer .= ", " . $this->getFailCount() . " fails";
|
||||
}
|
||||
if (0 < $this->getExceptionCount()) {
|
||||
$buffer .= ", " . $this->getExceptionCount() . " exceptions";
|
||||
}
|
||||
$buffer .= ".\n";
|
||||
$buffer .= $this->_timeStats();
|
||||
fwrite(STDOUT, $buffer);
|
||||
} else {
|
||||
fwrite(STDOUT, $buffer . $this->getPassCount() . " passes.\n" . $this->_timeStats());
|
||||
}
|
||||
|
||||
if (
|
||||
isset($this->params['codeCoverage']) &&
|
||||
$this->params['codeCoverage'] &&
|
||||
class_exists('CodeCoverageManager')
|
||||
) {
|
||||
CodeCoverageManager::report();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the time and memory stats for this test case/group
|
||||
*
|
||||
* @return string String content to display
|
||||
* @access protected
|
||||
*/
|
||||
function _timeStats() {
|
||||
$out = 'Time taken by tests (in seconds): ' . $this->_timeDuration . "\n";
|
||||
if (function_exists('memory_get_peak_usage')) {
|
||||
$out .= 'Peak memory use: (in bytes): ' . number_format(memory_get_peak_usage()) . "\n";
|
||||
}
|
||||
return $out;
|
||||
}
|
||||
}
|
378
php-practice/web-cake/html/cake/tests/lib/reporter/cake_html_reporter.php
Executable file
378
php-practice/web-cake/html/cake/tests/lib/reporter/cake_html_reporter.php
Executable file
@@ -0,0 +1,378 @@
|
||||
<?php
|
||||
/**
|
||||
* CakeHtmlReporter
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://cakephp.org CakePHP(tm) Project
|
||||
* @package cake
|
||||
* @subpackage cake.tests.libs.reporter
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
include_once dirname(__FILE__) . DS . 'cake_base_reporter.php';
|
||||
|
||||
/**
|
||||
* CakeHtmlReporter Reports Results of TestSuites and Test Cases
|
||||
* in an HTML format / context.
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.tests.lib
|
||||
*/
|
||||
class CakeHtmlReporter extends CakeBaseReporter {
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param string $charset
|
||||
* @param string $params
|
||||
* @return void
|
||||
*/
|
||||
function CakeHtmlReporter($charset = 'utf-8', $params = array()) {
|
||||
$params = array_map(array($this, '_htmlEntities'), $params);
|
||||
$this->CakeBaseReporter($charset, $params);
|
||||
}
|
||||
/**
|
||||
* Paints the top of the web page setting the
|
||||
* title to the name of the starting test.
|
||||
*
|
||||
* @param string $test_name Name class of test.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintHeader($testName) {
|
||||
$this->sendNoCacheHeaders();
|
||||
$this->paintDocumentStart();
|
||||
$this->paintTestMenu();
|
||||
printf("<h2>%s</h2>\n", $this->_htmlEntities($testName));
|
||||
echo "<ul class='tests'>\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the document start content contained in header.php
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function paintDocumentStart() {
|
||||
ob_start();
|
||||
$baseDir = $this->params['baseDir'];
|
||||
include CAKE_TESTS_LIB . 'templates' . DS . 'header.php';
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the menu on the left side of the test suite interface.
|
||||
* Contains all of the various plugin, core, and app buttons.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function paintTestMenu() {
|
||||
$groups = $this->baseUrl() . '?show=groups';
|
||||
$cases = $this->baseUrl() . '?show=cases';
|
||||
$plugins = App::objects('plugin');
|
||||
sort($plugins);
|
||||
include CAKE_TESTS_LIB . 'templates' . DS . 'menu.php';
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves and paints the list of tests cases in an HTML format.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function testCaseList() {
|
||||
$testCases = parent::testCaseList();
|
||||
$app = $this->params['app'];
|
||||
$plugin = $this->params['plugin'];
|
||||
|
||||
$buffer = "<h3>Core Test Cases:</h3>\n<ul>";
|
||||
$urlExtra = null;
|
||||
if ($app) {
|
||||
$buffer = "<h3>App Test Cases:</h3>\n<ul>";
|
||||
$urlExtra = '&app=true';
|
||||
} elseif ($plugin) {
|
||||
$buffer = "<h3>" . Inflector::humanize($plugin) . " Test Cases:</h3>\n<ul>";
|
||||
$urlExtra = '&plugin=' . $plugin;
|
||||
}
|
||||
|
||||
if (1 > count($testCases)) {
|
||||
$buffer .= "<strong>EMPTY</strong>";
|
||||
}
|
||||
|
||||
foreach ($testCases as $testCaseFile => $testCase) {
|
||||
$title = explode(strpos($testCase, '\\') ? '\\' : '/', str_replace('.test.php', '', $testCase));
|
||||
$title[count($title) - 1] = Inflector::camelize($title[count($title) - 1]);
|
||||
$title = implode(' / ', $title);
|
||||
$buffer .= "<li><a href='" . $this->baseUrl() . "?case=" . urlencode($testCase) . $urlExtra ."'>" . $title . "</a></li>\n";
|
||||
}
|
||||
$buffer .= "</ul>\n";
|
||||
echo $buffer;
|
||||
}
|
||||
|
||||
/**
|
||||
* Retrieves and paints the list of group tests in an HTML format.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function groupTestList() {
|
||||
$groupTests = parent::groupTestList();
|
||||
$app = $this->params['app'];
|
||||
$plugin = $this->params['plugin'];
|
||||
|
||||
$buffer = "<h3>Core Test Groups:</h3>\n<ul>";
|
||||
$urlExtra = null;
|
||||
if ($app) {
|
||||
$buffer = "<h3>App Test Groups:</h3>\n<ul>";
|
||||
$urlExtra = '&app=true';
|
||||
} else if ($plugin) {
|
||||
$buffer = "<h3>" . Inflector::humanize($plugin) . " Test Groups:</h3>\n<ul>";
|
||||
$urlExtra = '&plugin=' . $plugin;
|
||||
}
|
||||
|
||||
$buffer .= "<li><a href='" . $this->baseURL() . "?group=all$urlExtra'>All tests</a></li>\n";
|
||||
|
||||
foreach ($groupTests as $groupTest) {
|
||||
$buffer .= "<li><a href='" . $this->baseURL() . "?group={$groupTest}" . "{$urlExtra}'>" . $groupTest . "</a></li>\n";
|
||||
}
|
||||
$buffer .= "</ul>\n";
|
||||
echo $buffer;
|
||||
}
|
||||
|
||||
/**
|
||||
* Send the headers necessary to ensure the page is
|
||||
* reloaded on every request. Otherwise you could be
|
||||
* scratching your head over out of date test data.
|
||||
*
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function sendNoCacheHeaders() {
|
||||
if (!headers_sent()) {
|
||||
header("Expires: Mon, 26 Jul 1997 05:00:00 GMT");
|
||||
header("Last-Modified: " . gmdate("D, d M Y H:i:s") . " GMT");
|
||||
header("Cache-Control: no-store, no-cache, must-revalidate");
|
||||
header("Cache-Control: post-check=0, pre-check=0", false);
|
||||
header("Pragma: no-cache");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the end of the test with a summary of
|
||||
* the passes and failures.
|
||||
*
|
||||
* @param string $test_name Name class of test.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintFooter($test_name) {
|
||||
$colour = ($this->getFailCount() + $this->getExceptionCount() > 0 ? "red" : "green");
|
||||
echo "</ul>\n";
|
||||
echo "<div style=\"";
|
||||
echo "padding: 8px; margin: 1em 0; background-color: $colour; color: white;";
|
||||
echo "\">";
|
||||
echo $this->getTestCaseProgress() . "/" . $this->getTestCaseCount();
|
||||
echo " test cases complete:\n";
|
||||
echo "<strong>" . $this->getPassCount() . "</strong> passes, ";
|
||||
echo "<strong>" . $this->getFailCount() . "</strong> fails and ";
|
||||
echo "<strong>" . $this->getExceptionCount() . "</strong> exceptions.";
|
||||
echo "</div>\n";
|
||||
echo '<div style="padding:0 0 5px;">';
|
||||
echo '<p><strong>Time taken by tests (in seconds):</strong> ' . $this->_timeDuration . '</p>';
|
||||
if (function_exists('memory_get_peak_usage')) {
|
||||
echo '<p><strong>Peak memory use: (in bytes):</strong> ' . number_format(memory_get_peak_usage()) . '</p>';
|
||||
}
|
||||
echo $this->_paintLinks();
|
||||
echo '</div>';
|
||||
if (
|
||||
isset($this->params['codeCoverage']) &&
|
||||
$this->params['codeCoverage'] &&
|
||||
class_exists('CodeCoverageManager')
|
||||
) {
|
||||
CodeCoverageManager::report();
|
||||
}
|
||||
$this->paintDocumentEnd();
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders the links that for accessing things in the test suite.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function _paintLinks() {
|
||||
$show = $query = array();
|
||||
if (!empty($this->params['group'])) {
|
||||
$show['show'] = 'groups';
|
||||
} elseif (!empty($this->params['case'])) {
|
||||
$show['show'] = 'cases';
|
||||
}
|
||||
|
||||
if (!empty($this->params['app'])) {
|
||||
$show['app'] = $query['app'] = 'true';
|
||||
}
|
||||
if (!empty($this->params['plugin'])) {
|
||||
$show['plugin'] = $query['plugin'] = $this->params['plugin'];
|
||||
}
|
||||
if (!empty($this->params['case'])) {
|
||||
$query['case'] = $this->params['case'];
|
||||
} elseif (!empty($this->params['group'])) {
|
||||
$query['group'] = $this->params['group'];
|
||||
}
|
||||
$show = $this->_queryString($show);
|
||||
$query = $this->_queryString($query);
|
||||
|
||||
echo "<p><a href='" . $this->baseUrl() . $show . "'>Run more tests</a> | <a href='" . $this->baseUrl() . $query . "&show_passes=1'>Show Passes</a> | \n";
|
||||
echo " <a href='" . $this->baseUrl() . $query . "&code_coverage=true'>Analyze Code Coverage</a></p>\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert an array of parameters into a query string url
|
||||
*
|
||||
* @param array $url Url hash to be converted
|
||||
* @return string Converted url query string
|
||||
*/
|
||||
function _queryString($url) {
|
||||
$out = '?';
|
||||
$params = array();
|
||||
foreach ($url as $key => $value) {
|
||||
$params[] = "$key=$value";
|
||||
}
|
||||
$out .= implode('&', $params);
|
||||
return $out;
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the end of the document html.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function paintDocumentEnd() {
|
||||
$baseDir = $this->params['baseDir'];
|
||||
include CAKE_TESTS_LIB . 'templates' . DS . 'footer.php';
|
||||
ob_end_flush();
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the test failure with a breadcrumbs
|
||||
* trail of the nesting test suites below the
|
||||
* top level test.
|
||||
*
|
||||
* @param string $message Failure message displayed in
|
||||
* the context of the other tests.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintFail($message) {
|
||||
parent::paintFail($message);
|
||||
echo "<li class='fail'>\n";
|
||||
echo "<span>Failed</span>";
|
||||
echo "<div class='msg'>" . $this->_htmlEntities($message) . "</div>\n";
|
||||
$breadcrumb = $this->getTestList();
|
||||
array_shift($breadcrumb);
|
||||
echo "<div>" . implode(" -> ", $breadcrumb) . "</div>\n";
|
||||
echo "</li>\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the test pass with a breadcrumbs
|
||||
* trail of the nesting test suites below the
|
||||
* top level test.
|
||||
*
|
||||
* @param string $message Pass message displayed in the context of the other tests.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintPass($message) {
|
||||
parent::paintPass($message);
|
||||
|
||||
if (isset($this->params['show_passes']) && $this->params['show_passes']) {
|
||||
echo "<li class='pass'>\n";
|
||||
echo "<span>Passed</span> ";
|
||||
$breadcrumb = $this->getTestList();
|
||||
array_shift($breadcrumb);
|
||||
echo implode(" -> ", $breadcrumb);
|
||||
echo "<br />" . $this->_htmlEntities($message) . "\n";
|
||||
echo "</li>\n";
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints a PHP error.
|
||||
*
|
||||
* @param string $message Message is ignored.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintError($message) {
|
||||
parent::paintError($message);
|
||||
echo "<li class='error'>\n";
|
||||
echo "<span>Error</span>";
|
||||
echo "<div class='msg'>" . $this->_htmlEntities($message) . "</div>\n";
|
||||
$breadcrumb = $this->getTestList();
|
||||
array_shift($breadcrumb);
|
||||
echo "<div>" . implode(" -> ", $breadcrumb) . "</div>\n";
|
||||
echo "</li>\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints a PHP exception.
|
||||
*
|
||||
* @param Exception $exception Exception to display.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintException($exception) {
|
||||
parent::paintException($exception);
|
||||
echo "<li class='fail'>\n";
|
||||
echo "<span>Exception</span>";
|
||||
$message = 'Unexpected exception of type [' . get_class($exception) .
|
||||
'] with message ['. $exception->getMessage() .
|
||||
'] in ['. $exception->getFile() .
|
||||
' line ' . $exception->getLine() . ']';
|
||||
echo "<div class='msg'>" . $this->_htmlEntities($message) . "</div>\n";
|
||||
$breadcrumb = $this->getTestList();
|
||||
array_shift($breadcrumb);
|
||||
echo "<div>" . implode(" -> ", $breadcrumb) . "</div>\n";
|
||||
echo "</li>\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Prints the message for skipping tests.
|
||||
*
|
||||
* @param string $message Text of skip condition.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintSkip($message) {
|
||||
parent::paintSkip($message);
|
||||
echo "<li class='skipped'>\n";
|
||||
echo "<span>Skipped</span> ";
|
||||
echo $this->_htmlEntities($message);
|
||||
echo "</li>\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints formatted text such as dumped variables.
|
||||
*
|
||||
* @param string $message Text to show.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintFormattedMessage($message) {
|
||||
echo '<pre>' . $this->_htmlEntities($message) . '</pre>';
|
||||
}
|
||||
|
||||
/**
|
||||
* Character set adjusted entity conversion.
|
||||
*
|
||||
* @param string $message Plain text or Unicode message.
|
||||
* @return string Browser readable message.
|
||||
* @access protected
|
||||
*/
|
||||
function _htmlEntities($message) {
|
||||
return htmlentities($message, ENT_COMPAT, $this->_characterSet);
|
||||
}
|
||||
}
|
@@ -0,0 +1,198 @@
|
||||
<?php
|
||||
/**
|
||||
* CakeTextReporter contains reporting features used for plain text based output
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://cakephp.org CakePHP(tm) Project
|
||||
* @package cake
|
||||
* @subpackage cake.tests.libs.reporter
|
||||
* @since CakePHP(tm) v 1.3
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
include_once dirname(__FILE__) . DS . 'cake_base_reporter.php';
|
||||
|
||||
/**
|
||||
* CakeTextReporter contains reporting features used for plain text based output
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.tests.lib
|
||||
*/
|
||||
class CakeTextReporter extends CakeBaseReporter {
|
||||
|
||||
/**
|
||||
* Sets the text/plain header if the test is not a CLI test.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function paintDocumentStart() {
|
||||
if (!SimpleReporter::inCli()) {
|
||||
header('Content-type: text/plain');
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the end of the test with a summary of
|
||||
* the passes and failures.
|
||||
*
|
||||
* @param string $test_name Name class of test.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintFooter($test_name) {
|
||||
if ($this->getFailCount() + $this->getExceptionCount() == 0) {
|
||||
echo "OK\n";
|
||||
} else {
|
||||
echo "FAILURES!!!\n";
|
||||
}
|
||||
echo "Test cases run: " . $this->getTestCaseProgress() .
|
||||
"/" . $this->getTestCaseCount() .
|
||||
", Passes: " . $this->getPassCount() .
|
||||
", Failures: " . $this->getFailCount() .
|
||||
", Exceptions: " . $this->getExceptionCount() . "\n";
|
||||
|
||||
echo 'Time taken by tests (in seconds): ' . $this->_timeDuration . "\n";
|
||||
if (function_exists('memory_get_peak_usage')) {
|
||||
echo 'Peak memory use: (in bytes): ' . number_format(memory_get_peak_usage()) . "\n";
|
||||
}
|
||||
if (
|
||||
isset($this->params['codeCoverage']) &&
|
||||
$this->params['codeCoverage'] &&
|
||||
class_exists('CodeCoverageManager')
|
||||
) {
|
||||
CodeCoverageManager::report();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the title only.
|
||||
*
|
||||
* @param string $test_name Name class of test.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintHeader($test_name) {
|
||||
$this->paintDocumentStart();
|
||||
echo "$test_name\n";
|
||||
flush();
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints the test failure as a stack trace.
|
||||
*
|
||||
* @param string $message Failure message displayed in
|
||||
* the context of the other tests.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintFail($message) {
|
||||
parent::paintFail($message);
|
||||
echo $this->getFailCount() . ") $message\n";
|
||||
$breadcrumb = $this->getTestList();
|
||||
array_shift($breadcrumb);
|
||||
echo "\tin " . implode("\n\tin ", array_reverse($breadcrumb));
|
||||
echo "\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints a PHP error.
|
||||
*
|
||||
* @param string $message Message to be shown.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintError($message) {
|
||||
parent::paintError($message);
|
||||
echo "Exception " . $this->getExceptionCount() . "!\n$message\n";
|
||||
$breadcrumb = $this->getTestList();
|
||||
array_shift($breadcrumb);
|
||||
echo "\tin " . implode("\n\tin ", array_reverse($breadcrumb));
|
||||
echo "\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints a PHP exception.
|
||||
*
|
||||
* @param Exception $exception Exception to describe.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintException($exception) {
|
||||
parent::paintException($exception);
|
||||
$message = 'Unexpected exception of type [' . get_class($exception) .
|
||||
'] with message ['. $exception->getMessage() .
|
||||
'] in ['. $exception->getFile() .
|
||||
' line ' . $exception->getLine() . ']';
|
||||
echo "Exception " . $this->getExceptionCount() . "!\n$message\n";
|
||||
$breadcrumb = $this->getTestList();
|
||||
array_shift($breadcrumb);
|
||||
echo "\tin " . implode("\n\tin ", array_reverse($breadcrumb));
|
||||
echo "\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Prints the message for skipping tests.
|
||||
*
|
||||
* @param string $message Text of skip condition.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintSkip($message) {
|
||||
parent::paintSkip($message);
|
||||
echo "Skip: $message\n";
|
||||
}
|
||||
|
||||
/**
|
||||
* Paints formatted text such as dumped variables.
|
||||
*
|
||||
* @param string $message Text to show.
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function paintFormattedMessage($message) {
|
||||
echo "$message\n";
|
||||
flush();
|
||||
}
|
||||
|
||||
/**
|
||||
* Generate a test case list in plain text.
|
||||
* Creates as series of url's for tests that can be run.
|
||||
* One case per line.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
function testCaseList() {
|
||||
$testCases = parent::testCaseList();
|
||||
$app = $this->params['app'];
|
||||
$plugin = $this->params['plugin'];
|
||||
|
||||
$buffer = "Core Test Cases:\n";
|
||||
$urlExtra = '';
|
||||
if ($app) {
|
||||
$buffer = "App Test Cases:\n";
|
||||
$urlExtra = '&app=true';
|
||||
} elseif ($plugin) {
|
||||
$buffer = Inflector::humanize($plugin) . " Test Cases:\n";
|
||||
$urlExtra = '&plugin=' . $plugin;
|
||||
}
|
||||
|
||||
if (1 > count($testCases)) {
|
||||
$buffer .= "EMPTY";
|
||||
echo $buffer;
|
||||
}
|
||||
|
||||
foreach ($testCases as $testCaseFile => $testCase) {
|
||||
$buffer .= $_SERVER['SERVER_NAME'] . $this->baseUrl() ."?case=" . $testCase . "&output=text"."\n";
|
||||
}
|
||||
|
||||
$buffer .= "\n";
|
||||
echo $buffer;
|
||||
}
|
||||
}
|
@@ -0,0 +1,37 @@
|
||||
<?php
|
||||
/**
|
||||
* Short description for file.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
?> </div>
|
||||
</div>
|
||||
<div id="footer">
|
||||
<p>
|
||||
<!--PLEASE USE ONE OF THE POWERED BY CAKEPHP LOGO-->
|
||||
<a href="http://www.cakephp.org/" target="_blank">
|
||||
<img src="<?php echo $baseDir; ?>img/cake.power.gif" alt="CakePHP(tm) :: Rapid Development Framework" /></a>
|
||||
</p>
|
||||
</div>
|
||||
<?php
|
||||
App::import('Core', 'View');
|
||||
$null = null;
|
||||
$View =& new View($null, false);
|
||||
echo $View->element('sql_dump');
|
||||
?>
|
||||
</div>
|
||||
</body>
|
||||
</html>
|
125
php-practice/web-cake/html/cake/tests/lib/templates/header.php
Normal file
125
php-practice/web-cake/html/cake/tests/lib/templates/header.php
Normal file
@@ -0,0 +1,125 @@
|
||||
<?php
|
||||
/**
|
||||
* Short description for file.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
?>
|
||||
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
||||
<html xmlns="http://www.w3.org/1999/xhtml">
|
||||
<head>
|
||||
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
|
||||
<title>CakePHP Test Suite 1.3</title>
|
||||
<style type="text/css">
|
||||
h3 {font-size: 170%; padding-top: 1em}
|
||||
a {font-size: 120%}
|
||||
li {line-height: 140%}
|
||||
.test-menu {float:left; margin-right: 24px;}
|
||||
.test-results {float:left; width: 67%;}
|
||||
ul.tests {margin: 0; font-size:12px;}
|
||||
ul.tests li {
|
||||
list-style: none;
|
||||
margin: 14px 0;
|
||||
padding-left: 20px;
|
||||
}
|
||||
ul.tests li span {
|
||||
font-size:14px;
|
||||
text-transform: uppercase;
|
||||
font-weight: bold;
|
||||
}
|
||||
ul.tests li.pass span, ul.tests li.skipped span { display:inline;}
|
||||
ul.tests li.fail span { color: red; }
|
||||
ul.tests li.pass span { color: green; }
|
||||
ul.tests li.skipped span { color: navy; }
|
||||
ul.tests li.error span { color : #d15d00; }
|
||||
|
||||
ul.tests li.pass,
|
||||
ul.tests li.error,
|
||||
ul.tests li.skipped,
|
||||
ul.tests li.fail {
|
||||
background: #fff2f2 url(http://cakephp.org/img/test-fail-icon.png) 5px 5px no-repeat;
|
||||
border-top: 1px dotted red;
|
||||
border-bottom: 1px dotted red;
|
||||
padding:5px 10px 2px 25px;
|
||||
}
|
||||
ul.tests li.pass {
|
||||
background-color: #f2fff2;
|
||||
background-image: url(http://cakephp.org/img/test-pass-icon.png);
|
||||
border-color:green;
|
||||
}
|
||||
ul.tests li.skipped {
|
||||
background-color: #edf1ff;
|
||||
background-image: url(http://cakephp.org/img/test-skip-icon.png);
|
||||
border-color:navy;
|
||||
}
|
||||
ul.tests li.error {
|
||||
background-color: #ffffe5;
|
||||
background-image: url(http://cakephp.org/img/test-error-icon.png);
|
||||
border-color: #DF6300;
|
||||
}
|
||||
ul.tests li div { margin: 5px 0 8px 0; }
|
||||
ul.tests li div.msg { font-weight: bold; }
|
||||
table caption { color:#fff; }
|
||||
|
||||
div.code-coverage-results div.code-line {
|
||||
padding-left:5px;
|
||||
display:block;
|
||||
margin-left:10px;
|
||||
}
|
||||
div.code-coverage-results div.uncovered span.content { background:#ecc; }
|
||||
div.code-coverage-results div.covered span.content { background:#cec; }
|
||||
div.code-coverage-results div.ignored span.content { color:#aaa; }
|
||||
div.code-coverage-results span.line-num {
|
||||
color:#666;
|
||||
display:block;
|
||||
float:left;
|
||||
width:20px;
|
||||
text-align:right;
|
||||
margin-right:5px;
|
||||
}
|
||||
div.code-coverage-results span.line-num strong { color:#666; }
|
||||
div.code-coverage-results div.start {
|
||||
border:1px solid #aaa;
|
||||
border-width:1px 1px 0px 1px;
|
||||
margin-top:30px;
|
||||
padding-top:5px;
|
||||
}
|
||||
div.code-coverage-results div.end {
|
||||
border:1px solid #aaa;
|
||||
border-width:0px 1px 1px 1px;
|
||||
margin-bottom:30px;
|
||||
padding-bottom:5px;
|
||||
}
|
||||
div.code-coverage-results div.realstart { margin-top:0px; }
|
||||
div.code-coverage-results p.note {
|
||||
color:#bbb;
|
||||
padding:5px;
|
||||
margin:5px 0 10px;
|
||||
font-size:10px;
|
||||
}
|
||||
div.code-coverage-results span.result-bad { color: #a00; }
|
||||
div.code-coverage-results span.result-ok { color: #fa0; }
|
||||
div.code-coverage-results span.result-good { color: #0a0; }
|
||||
</style>
|
||||
<link rel="stylesheet" type="text/css" href="<?php echo $baseDir; ?>css/cake.generic.css" />
|
||||
</head>
|
||||
<body>
|
||||
<div id="container">
|
||||
<div id="header">
|
||||
<h1>CakePHP: the rapid development php framework</h1>
|
||||
</div>
|
||||
<div id="content">
|
||||
<h2>CakePHP Test Suite 1.3</h2>
|
58
php-practice/web-cake/html/cake/tests/lib/templates/menu.php
Normal file
58
php-practice/web-cake/html/cake/tests/lib/templates/menu.php
Normal file
@@ -0,0 +1,58 @@
|
||||
<?php
|
||||
/**
|
||||
* Short description for file.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
?>
|
||||
<div class="test-menu">
|
||||
<ul>
|
||||
<li>
|
||||
<span style="font-size: 18px">App</span>
|
||||
<ul>
|
||||
<li><a href='<?php echo $groups;?>&app=true'>Test Groups</a></li>
|
||||
<li><a href='<?php echo $cases;?>&app=true'>Test Cases</a></li>
|
||||
</ul>
|
||||
</li>
|
||||
<?php
|
||||
if (!empty($plugins)):
|
||||
?>
|
||||
<li style="padding-top: 10px">
|
||||
<span style="font-size: 18px">Plugins</span>
|
||||
<?php foreach($plugins as $plugin):
|
||||
$pluginPath = Inflector::underscore($plugin);
|
||||
?>
|
||||
<ul>
|
||||
<li style="padding-top: 10px">
|
||||
<span style="font-size: 18px"><?php echo $plugin;?></span>
|
||||
<ul>
|
||||
<li><a href='<?php echo $groups;?>&plugin=<?php echo $pluginPath; ?>'>Test Groups</a></li>
|
||||
<li><a href='<?php echo $cases;?>&plugin=<?php echo $pluginPath; ?>'>Test Cases</a></li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
<?php endforeach; ?>
|
||||
<?php endif;?>
|
||||
<li style="padding-top: 10px">
|
||||
<span style="font-size: 18px">Core</span>
|
||||
<ul>
|
||||
<li><a href='<?php echo $groups;?>'>Test Groups</a></li>
|
||||
<li><a href='<?php echo $cases;?>'>Test Cases</a></li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
<div class="test-results">
|
@@ -0,0 +1,32 @@
|
||||
<?php
|
||||
/**
|
||||
* Missing SimpleTest error page.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.libs
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
?>
|
||||
<?php include dirname(__FILE__) . DS . 'header.php'; ?>
|
||||
<div id="content">
|
||||
<h2>SimpleTest is not installed</h2>
|
||||
<p>You must install SimpleTest to use the CakePHP(tm) Test Suite.</p>
|
||||
<p>SimpleTest can be placed in one of the following directories.</p>
|
||||
<ul>
|
||||
<li><?php echo CAKE; ?>vendors </li>
|
||||
<li><?php echo APP_DIR . DS; ?>vendors</li>
|
||||
</ul>
|
||||
<p><a href="http://simpletest.org/en/download.html" target="_blank">Download SimpleTest</a></p>
|
||||
</div>
|
||||
<?php include dirname(__FILE__) . DS . 'footer.php'; ?>
|
@@ -0,0 +1,27 @@
|
||||
<?php
|
||||
/**
|
||||
* Xdebug error page
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.libs
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
?>
|
||||
<?php include dirname(__FILE__) . DS . 'header.php'; ?>
|
||||
<div id="content">
|
||||
<h2>Xdebug is not installed</h2>
|
||||
<p>You must install Xdebug to use the CakePHP(tm) Code Coverage Analyzation.</p>
|
||||
<p><a href="http://www.xdebug.org/docs/install" target="_blank">Learn How To Install Xdebug</a></p>
|
||||
</div>
|
||||
<?php include dirname(__FILE__) . DS . 'footer.php'; ?>
|
421
php-practice/web-cake/html/cake/tests/lib/test_manager.php
Normal file
421
php-practice/web-cake/html/cake/tests/lib/test_manager.php
Normal file
@@ -0,0 +1,421 @@
|
||||
<?php
|
||||
/**
|
||||
* TestManager for CakePHP Test suite.
|
||||
*
|
||||
* PHP versions 4 and 5
|
||||
*
|
||||
* CakePHP(tm) Tests <http://book.cakephp.org/view/1196/Testing>
|
||||
* Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
*
|
||||
* Licensed under The Open Group Test Suite License
|
||||
* Redistributions of files must retain the above copyright notice.
|
||||
*
|
||||
* @copyright Copyright 2005-2010, Cake Software Foundation, Inc. (http://cakefoundation.org)
|
||||
* @link http://book.cakephp.org/view/1196/Testing CakePHP(tm) Tests
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
* @since CakePHP(tm) v 1.2.0.4433
|
||||
* @license http://www.opensource.org/licenses/opengroup.php The Open Group Test Suite License
|
||||
*/
|
||||
define('CORE_TEST_CASES', TEST_CAKE_CORE_INCLUDE_PATH . 'tests' . DS . 'cases');
|
||||
define('CORE_TEST_GROUPS', TEST_CAKE_CORE_INCLUDE_PATH . 'tests' . DS . 'groups');
|
||||
define('APP_TEST_CASES', TESTS . 'cases');
|
||||
define('APP_TEST_GROUPS', TESTS . 'groups');
|
||||
|
||||
/**
|
||||
* TestManager is the base class that handles loading and initiating the running
|
||||
* of TestCase and TestSuite classes that the user has selected.
|
||||
*
|
||||
* @package cake
|
||||
* @subpackage cake.cake.tests.lib
|
||||
*/
|
||||
class TestManager {
|
||||
/**
|
||||
* Extension suffix for test case files.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $_testExtension = '.test.php';
|
||||
|
||||
/**
|
||||
* Extension suffix for group test case files.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
var $_groupExtension = '.group.php';
|
||||
|
||||
/**
|
||||
* Is this test an AppTest?
|
||||
*
|
||||
* @var boolean
|
||||
*/
|
||||
var $appTest = false;
|
||||
|
||||
/**
|
||||
* Is this test a plugin test?
|
||||
*
|
||||
* @var mixed boolean false or string name of the plugin being used.
|
||||
*/
|
||||
var $pluginTest = false;
|
||||
|
||||
/**
|
||||
* Constructor for the TestManager class
|
||||
*
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function TestManager() {
|
||||
$this->_installSimpleTest();
|
||||
if (isset($_GET['app'])) {
|
||||
$this->appTest = true;
|
||||
}
|
||||
if (isset($_GET['plugin'])) {
|
||||
$this->pluginTest = htmlentities($_GET['plugin']);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Includes the required simpletest files in order for the testsuite to run
|
||||
*
|
||||
* @return void
|
||||
* @access public
|
||||
*/
|
||||
function _installSimpleTest() {
|
||||
App::import('Vendor', array(
|
||||
'simpletest' . DS . 'unit_tester',
|
||||
'simpletest' . DS . 'mock_objects',
|
||||
'simpletest' . DS . 'web_tester'
|
||||
));
|
||||
require_once(CAKE_TESTS_LIB . 'cake_web_test_case.php');
|
||||
require_once(CAKE_TESTS_LIB . 'cake_test_case.php');
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs all tests in the Application depending on the current appTest setting
|
||||
*
|
||||
* @param Object $reporter Reporter object for the tests being run.
|
||||
* @param boolean $testing Are tests supposed to be auto run. Set to true to return testcase list.
|
||||
* @return mixed
|
||||
* @access public
|
||||
*/
|
||||
function runAllTests(&$reporter, $testing = false) {
|
||||
$testCases =& $this->_getTestFileList($this->_getTestsPath());
|
||||
if ($this->appTest) {
|
||||
$test =& new TestSuite(__('All App Tests', true));
|
||||
} else if ($this->pluginTest) {
|
||||
$test =& new TestSuite(sprintf(__('All %s Plugin Tests', true), Inflector::humanize($this->pluginTest)));
|
||||
} else {
|
||||
$test =& new TestSuite(__('All Core Tests', true));
|
||||
}
|
||||
|
||||
if ($testing) {
|
||||
return $testCases;
|
||||
}
|
||||
|
||||
foreach ($testCases as $testCase) {
|
||||
$test->addTestFile($testCase);
|
||||
}
|
||||
|
||||
return $test->run($reporter);
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs a specific test case file
|
||||
*
|
||||
* @param string $testCaseFile Filename of the test to be run.
|
||||
* @param Object $reporter Reporter instance to attach to the test case.
|
||||
* @param boolean $testing Set to true if testing, otherwise test case will be run.
|
||||
* @return mixed Result of test case being run.
|
||||
* @access public
|
||||
*/
|
||||
function runTestCase($testCaseFile, &$reporter, $testing = false) {
|
||||
$testCaseFileWithPath = $this->_getTestsPath() . DS . $testCaseFile;
|
||||
|
||||
if (!file_exists($testCaseFileWithPath) || strpos($testCaseFileWithPath, '..')) {
|
||||
trigger_error(
|
||||
sprintf(__("Test case %s cannot be found", true), htmlentities($testCaseFile)),
|
||||
E_USER_ERROR
|
||||
);
|
||||
return false;
|
||||
}
|
||||
|
||||
if ($testing) {
|
||||
return true;
|
||||
}
|
||||
|
||||
$test =& new TestSuite(sprintf(__('Individual test case: %s', true), $testCaseFile));
|
||||
$test->addTestFile($testCaseFileWithPath);
|
||||
return $test->run($reporter);
|
||||
}
|
||||
|
||||
/**
|
||||
* Runs a specific group test file
|
||||
*
|
||||
* @param string $groupTestName GroupTest that you want to run.
|
||||
* @param Object $reporter Reporter instance to use with the group test being run.
|
||||
* @return mixed Results of group test being run.
|
||||
* @access public
|
||||
*/
|
||||
function runGroupTest($groupTestName, &$reporter) {
|
||||
$filePath = $this->_getTestsPath('groups') . DS . strtolower($groupTestName) . $this->_groupExtension;
|
||||
|
||||
if (!file_exists($filePath) || strpos($filePath, '..')) {
|
||||
trigger_error(sprintf(
|
||||
__("Group test %s cannot be found at %s", true),
|
||||
htmlentities($groupTestName),
|
||||
htmlentities($filePath)
|
||||
),
|
||||
E_USER_ERROR
|
||||
);
|
||||
}
|
||||
|
||||
require_once $filePath;
|
||||
$test =& new TestSuite(sprintf(__('%s group test', true), $groupTestName));
|
||||
foreach ($this->_getGroupTestClassNames($filePath) as $groupTest) {
|
||||
$testCase = new $groupTest();
|
||||
$test->addTestCase($testCase);
|
||||
if (isset($testCase->label)) {
|
||||
$test->_label = $testCase->label;
|
||||
}
|
||||
}
|
||||
return $test->run($reporter);
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds all testcases in a given directory to a given GroupTest object
|
||||
*
|
||||
* @param object $groupTest Instance of TestSuite/GroupTest that files are to be added to.
|
||||
* @param string $directory The directory to add tests from.
|
||||
* @return void
|
||||
* @access public
|
||||
* @static
|
||||
*/
|
||||
function addTestCasesFromDirectory(&$groupTest, $directory = '.') {
|
||||
$manager =& new TestManager();
|
||||
$testCases =& $manager->_getTestFileList($directory);
|
||||
foreach ($testCases as $testCase) {
|
||||
$groupTest->addTestFile($testCase);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a specific test file and thereby all of its test cases and group tests to a given group test file
|
||||
*
|
||||
* @param object $groupTest Instance of TestSuite/GroupTest that a file should be added to.
|
||||
* @param string $file The file name, minus the suffix to add.
|
||||
* @return void
|
||||
* @access public
|
||||
* @static
|
||||
*/
|
||||
function addTestFile(&$groupTest, $file) {
|
||||
$manager =& new TestManager();
|
||||
|
||||
if (file_exists($file . $manager->_testExtension)) {
|
||||
$file .= $manager->_testExtension;
|
||||
} elseif (file_exists($file . $manager->_groupExtension)) {
|
||||
$file .= $manager->_groupExtension;
|
||||
}
|
||||
$groupTest->addTestFile($file);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a list of test cases found in the current valid test case path
|
||||
*
|
||||
* @access public
|
||||
* @static
|
||||
*/
|
||||
function &getTestCaseList() {
|
||||
$manager =& new TestManager();
|
||||
$return = $manager->_getTestCaseList($manager->_getTestsPath());
|
||||
return $return;
|
||||
}
|
||||
|
||||
/**
|
||||
* Builds the list of test cases from a given directory
|
||||
*
|
||||
* @param string $directory Directory to get test case list from.
|
||||
* @access protected
|
||||
*/
|
||||
function &_getTestCaseList($directory = '.') {
|
||||
$fileList =& $this->_getTestFileList($directory);
|
||||
$testCases = array();
|
||||
foreach ($fileList as $testCaseFile) {
|
||||
$testCases[$testCaseFile] = str_replace($directory . DS, '', $testCaseFile);
|
||||
}
|
||||
return $testCases;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a list of test files from a given directory
|
||||
*
|
||||
* @param string $directory Directory to get test case files from.
|
||||
* @access protected
|
||||
*/
|
||||
function &_getTestFileList($directory = '.') {
|
||||
$return = $this->_getRecursiveFileList($directory, array(&$this, '_isTestCaseFile'));
|
||||
return $return;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a list of group tests found in the current valid test case path
|
||||
*
|
||||
* @access public
|
||||
* @static
|
||||
*/
|
||||
function &getGroupTestList() {
|
||||
$manager =& new TestManager();
|
||||
$return = $manager->_getTestGroupList($manager->_getTestsPath('groups'));
|
||||
return $return;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a list of group test files from a given directory
|
||||
*
|
||||
* @param string $directory The directory to get group test files from.
|
||||
* @access protected
|
||||
*/
|
||||
function &_getTestGroupFileList($directory = '.') {
|
||||
$return = $this->_getRecursiveFileList($directory, array(&$this, '_isTestGroupFile'));
|
||||
return $return;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a list of group test files from a given directory
|
||||
*
|
||||
* @param string $directory The directory to get group tests from.
|
||||
* @access protected
|
||||
*/
|
||||
function &_getTestGroupList($directory = '.') {
|
||||
$fileList =& $this->_getTestGroupFileList($directory);
|
||||
$groupTests = array();
|
||||
|
||||
foreach ($fileList as $groupTestFile) {
|
||||
$groupTests[$groupTestFile] = str_replace($this->_groupExtension, '', basename($groupTestFile));
|
||||
}
|
||||
sort($groupTests);
|
||||
return $groupTests;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a list of class names from a group test file
|
||||
*
|
||||
* @param string $groupTestFile The groupTest file to scan for TestSuite classnames.
|
||||
* @access protected
|
||||
*/
|
||||
function &_getGroupTestClassNames($groupTestFile) {
|
||||
$file = implode("\n", file($groupTestFile));
|
||||
preg_match("~lass\s+?(.*)\s+?extends TestSuite~", $file, $matches);
|
||||
if (!empty($matches)) {
|
||||
unset($matches[0]);
|
||||
return $matches;
|
||||
}
|
||||
$matches = array();
|
||||
return $matches;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets a recursive list of files from a given directory and matches then against
|
||||
* a given fileTestFunction, like isTestCaseFile()
|
||||
*
|
||||
* @param string $directory The directory to scan for files.
|
||||
* @param mixed $fileTestFunction
|
||||
* @access protected
|
||||
*/
|
||||
function &_getRecursiveFileList($directory = '.', $fileTestFunction) {
|
||||
$fileList = array();
|
||||
if (!is_dir($directory)) {
|
||||
return $fileList;
|
||||
}
|
||||
|
||||
$files = glob($directory . DS . '*');
|
||||
$files = $files ? $files : array();
|
||||
|
||||
foreach ($files as $file) {
|
||||
if (is_dir($file)) {
|
||||
$fileList = array_merge($fileList, $this->_getRecursiveFileList($file, $fileTestFunction));
|
||||
} elseif ($fileTestFunction[0]->$fileTestFunction[1]($file)) {
|
||||
$fileList[] = $file;
|
||||
}
|
||||
}
|
||||
return $fileList;
|
||||
}
|
||||
|
||||
/**
|
||||
* Tests if a file has the correct test case extension
|
||||
*
|
||||
* @param string $file
|
||||
* @return boolean Whether $file is a test case.
|
||||
* @access protected
|
||||
*/
|
||||
function _isTestCaseFile($file) {
|
||||
return $this->_hasExpectedExtension($file, $this->_testExtension);
|
||||
}
|
||||
|
||||
/**
|
||||
* Tests if a file has the correct group test extension
|
||||
*
|
||||
* @param string $file
|
||||
* @return boolean Whether $file is a group
|
||||
* @access protected
|
||||
*/
|
||||
function _isTestGroupFile($file) {
|
||||
return $this->_hasExpectedExtension($file, $this->_groupExtension);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if a file has a specific extension
|
||||
*
|
||||
* @param string $file
|
||||
* @param string $extension
|
||||
* @return void
|
||||
* @access protected
|
||||
*/
|
||||
function _hasExpectedExtension($file, $extension) {
|
||||
return $extension == strtolower(substr($file, (0 - strlen($extension))));
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the given path to the test files depending on a given type of tests (cases, group, ..)
|
||||
*
|
||||
* @param string $type either 'cases' or 'groups'
|
||||
* @return string The path tests are located on
|
||||
* @access protected
|
||||
*/
|
||||
function _getTestsPath($type = 'cases') {
|
||||
if (!empty($this->appTest)) {
|
||||
if ($type == 'cases') {
|
||||
$result = APP_TEST_CASES;
|
||||
} else if ($type == 'groups') {
|
||||
$result = APP_TEST_GROUPS;
|
||||
}
|
||||
} else if (!empty($this->pluginTest)) {
|
||||
$_pluginBasePath = APP . 'plugins' . DS . $this->pluginTest . DS . 'tests';
|
||||
$pluginPath = App::pluginPath($this->pluginTest);
|
||||
if (file_exists($pluginPath . DS . 'tests')) {
|
||||
$_pluginBasePath = $pluginPath . DS . 'tests';
|
||||
}
|
||||
$result = $_pluginBasePath . DS . $type;
|
||||
} else {
|
||||
if ($type == 'cases') {
|
||||
$result = CORE_TEST_CASES;
|
||||
} else if ($type == 'groups') {
|
||||
$result = CORE_TEST_GROUPS;
|
||||
}
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the extension for either 'group' or 'test' types.
|
||||
*
|
||||
* @param string $type Type of test to get, either 'test' or 'group'
|
||||
* @return string Extension suffix for test.
|
||||
* @access public
|
||||
*/
|
||||
function getExtension($type = 'test') {
|
||||
if ($type == 'test' || $type == 'case') {
|
||||
return $this->_testExtension;
|
||||
}
|
||||
return $this->_groupExtension;
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user