Add pear modules, mail and net_smtp via composer (#93)

Add pear modules, mail and net_smtp via composer, remove php 5.6 build due to phpunit 6
This commit is contained in:
Thilina Hasantha
2018-01-08 23:13:43 +01:00
committed by GitHub
parent 359e3f8382
commit e7792e7d79
2349 changed files with 117270 additions and 83170 deletions

View File

@@ -0,0 +1,18 @@
| Q | A
| --------------------------| ---------------
| php-code-coverage version | x.y.z
| PHP version | x.y.z
| Driver | Xdebug / PHPDBG
| Xdebug version (if used) | x.y.z
| Installation Method | Composer / PHPUnit PHAR
| Usage Method | PHPUnit / other
| PHPUnit version (if used) | x.y.z
<!--
- Please fill in this template according to your issue.
- Please keep the table shown above at the top of your issue.
- Please post code as text (using proper markup). Do not post screenshots of code.
- For support request or how-tos, visit https://phpunit.de/support.html
- Otherwise, replace this comment by the description of your issue.
-->

View File

@@ -1,12 +1,6 @@
build/api
build/code-browser
build/coverage
build/logs
build/pdepend
cache.properties
/tests/_files/tmp
/vendor
/composer.lock
/composer.phar
/.idea
/.php_cs.cache

View File

@@ -1,69 +1,87 @@
<?php
$finder = Symfony\CS\Finder\DefaultFinder::create()
->files()
->in('src')
->in('tests')
->exclude('_files')
->name('*.php');
$header = <<<'EOF'
This file is part of the php-code-coverage package.
return Symfony\CS\Config\Config::create()
->setUsingCache(true)
->level(\Symfony\CS\FixerInterface::NONE_LEVEL)
->fixers(
array(
'align_double_arrow',
'align_equals',
'braces',
'concat_with_spaces',
'duplicate_semicolon',
'elseif',
'empty_return',
'encoding',
'eof_ending',
'extra_empty_lines',
'function_call_space',
'function_declaration',
'indentation',
'join_function',
'line_after_namespace',
'linefeed',
'list_commas',
'lowercase_constants',
'lowercase_keywords',
'method_argument_space',
'multiple_use',
'namespace_no_leading_whitespace',
'no_blank_lines_after_class_opening',
'no_empty_lines_after_phpdocs',
'parenthesis',
'php_closing_tag',
'phpdoc_indent',
'phpdoc_no_access',
'phpdoc_no_empty_return',
'phpdoc_no_package',
'phpdoc_params',
'phpdoc_scalar',
'phpdoc_separation',
'phpdoc_to_comment',
'phpdoc_trim',
'phpdoc_types',
'phpdoc_var_without_name',
'remove_lines_between_uses',
'return',
'self_accessor',
'short_array_syntax',
'short_tag',
'single_line_after_imports',
'single_quote',
'spaces_before_semicolon',
'spaces_cast',
'ternary_spaces',
'trailing_spaces',
'trim_array_spaces',
'unused_use',
'visibility',
'whitespacy_lines'
)
(c) Sebastian Bergmann <sebastian@phpunit.de>
For the full copyright and license information, please view the LICENSE
file that was distributed with this source code.
EOF;
return PhpCsFixer\Config::create()
->setRiskyAllowed(true)
->setRules(
[
'array_syntax' => ['syntax' => 'short'],
'binary_operator_spaces' => [
'align_double_arrow' => true,
'align_equals' => true
],
'blank_line_after_namespace' => true,
'blank_line_before_statement' => [
'statements' => [
'break',
'continue',
'return',
'throw',
'try',
],
],
'braces' => true,
'cast_spaces' => true,
'concat_space' => ['spacing' => 'one'],
'elseif' => true,
'encoding' => true,
'full_opening_tag' => true,
'function_declaration' => true,
'header_comment' => ['header' => $header, 'separate' => 'none'],
'indentation_type' => true,
'line_ending' => true,
'lowercase_constants' => true,
'lowercase_keywords' => true,
'method_argument_space' => true,
'native_function_invocation' => true,
'no_alias_functions' => true,
'no_blank_lines_after_class_opening' => true,
'no_blank_lines_after_phpdoc' => true,
'no_closing_tag' => true,
'no_empty_phpdoc' => true,
'no_empty_statement' => true,
'no_extra_consecutive_blank_lines' => true,
'no_leading_namespace_whitespace' => true,
'no_singleline_whitespace_before_semicolons' => true,
'no_spaces_after_function_name' => true,
'no_spaces_inside_parenthesis' => true,
'no_trailing_comma_in_list_call' => true,
'no_trailing_whitespace' => true,
'no_unused_imports' => true,
'no_whitespace_in_blank_line' => true,
'ordered_imports' => true,
'phpdoc_align' => true,
'phpdoc_indent' => true,
'phpdoc_no_access' => true,
'phpdoc_no_empty_return' => true,
'phpdoc_no_package' => true,
'phpdoc_scalar' => true,
'phpdoc_separation' => true,
'phpdoc_to_comment' => true,
'phpdoc_trim' => true,
'phpdoc_types' => true,
'phpdoc_var_without_name' => true,
'self_accessor' => true,
'simplified_null_return' => true,
'single_blank_line_at_eof' => true,
'single_import_per_statement' => true,
'single_line_after_imports' => true,
'single_quote' => true,
'ternary_operator_spaces' => true,
'trim_array_spaces' => true,
'visibility_required' => true,
]
)
->finder($finder);
->setFinder(
PhpCsFixer\Finder::create()
->files()
->in(__DIR__ . '/src')
->name('*.php')
);

View File

@@ -1,21 +1,39 @@
language: php
php:
- 5.6
- 7.0
- nightly
sudo: false
php:
- 7.0
- 7.1
- 7.2
- master
matrix:
allow_failures:
- php: master
fast_finish: true
env:
matrix:
- DEPENDENCIES="high"
- DEPENDENCIES="low"
global:
- DEFAULT_COMPOSER_FLAGS="--no-interaction --no-ansi --no-progress --no-suggest"
before_install:
- composer self-update
- composer self-update
- composer clear-cache
install:
- travis_retry composer install --no-interaction --prefer-source
- if [[ "$DEPENDENCIES" = 'high' ]]; then travis_retry composer update $DEFAULT_COMPOSER_FLAGS; fi
- if [[ "$DEPENDENCIES" = 'low' ]]; then travis_retry composer update $DEFAULT_COMPOSER_FLAGS --prefer-lowest; fi
script:
- if [[ "$DRIVER" = 'phpdbg' ]]; then phpdbg -qrr vendor/bin/phpunit --coverage-clover=coverage.xml; fi
- if [[ "$DRIVER" = 'xdebug' ]]; then vendor/bin/phpunit --coverage-clover=coverage.xml; fi
- vendor/bin/phpunit --configuration build
after_success:
- bash <(curl -s https://codecov.io/bash)
notifications:
email: false

View File

@@ -2,6 +2,41 @@
All notable changes of the PHP_CodeCoverage 4.0 release series are documented in this file using the [Keep a CHANGELOG](http://keepachangelog.com/) principles.
## [4.0.8] - 2017-04-02
* Fixed [#515](https://github.com/sebastianbergmann/php-code-coverage/pull/515): Wrong use of recursive iterator causing duplicate entries in XML coverage report
## [4.0.7] - 2017-03-01
### Changed
* Cleaned up requirements in `composer.json`
## [4.0.6] - 2017-02-23
### Changed
* Added support for `phpunit/php-token-stream` 2.0
* Updated HTML report assets
## [4.0.5] - 2017-01-20
### Fixed
* Fixed formatting of executed lines percentage for classes in file view
## [4.0.4] - 2016-12-20
### Changed
* Implemented [#432](https://github.com/sebastianbergmann/php-code-coverage/issues/432): Change how files with no executable lines are displayed in the HTML report
## [4.0.3] - 2016-11-28
### Changed
* The check for unintentionally covered code is no longer performed for `@medium` and `@large` tests
## [4.0.2] - 2016-11-01
### Fixed
@@ -20,6 +55,12 @@ All notable changes of the PHP_CodeCoverage 4.0 release series are documented in
* This component now uses namespaces
[4.0.8]: https://github.com/sebastianbergmann/php-code-coverage/compare/4.0.7...4.0.8
[4.0.7]: https://github.com/sebastianbergmann/php-code-coverage/compare/4.0.6...4.0.7
[4.0.6]: https://github.com/sebastianbergmann/php-code-coverage/compare/4.0.5...4.0.6
[4.0.5]: https://github.com/sebastianbergmann/php-code-coverage/compare/4.0.4...4.0.5
[4.0.4]: https://github.com/sebastianbergmann/php-code-coverage/compare/4.0.3...4.0.4
[4.0.3]: https://github.com/sebastianbergmann/php-code-coverage/compare/4.0.2...4.0.3
[4.0.2]: https://github.com/sebastianbergmann/php-code-coverage/compare/4.0.1...4.0.2
[4.0.1]: https://github.com/sebastianbergmann/php-code-coverage/compare/4.0.0...4.0.1
[4.0.0]: https://github.com/sebastianbergmann/php-code-coverage/compare/3.3...4.0.0

View File

@@ -0,0 +1,45 @@
# Changes in PHP_CodeCoverage 5.0
All notable changes of the PHP_CodeCoverage 5.0 release series are documented in this file using the [Keep a CHANGELOG](http://keepachangelog.com/) principles.
## [5.0.4] - 2017-04-02
### Added
* Added `SebastianBergmann\CodeCoverage\Version::id()` method
### Fixed
* Fixed [#515](https://github.com/sebastianbergmann/php-code-coverage/pull/515): Wrong use of recursive iterator causing duplicate entries in XML coverage report
## [5.0.3] - 2017-03-06
### Fixed
* Fixed [#451](https://github.com/sebastianbergmann/php-code-coverage/pull/451): Conflict between HTML report assets and directories named `css`, `fonts`, or `js`
* Fixed [#485](https://github.com/sebastianbergmann/php-code-coverage/issues/485): Large popover contents cannot be viewed
## [5.0.2] - 2017-03-01
### Changed
* Cleaned up requirements in `composer.json`
## [5.0.1] - 2017-02-23
### Added
* Implemented [#508](https://github.com/sebastianbergmann/php-code-coverage/pull/508): Support for HackLang's `ENUM` declaration
## [5.0.0] - 2017-02-03
### Removed
* This component is no longer supported on PHP 5
[5.0.4]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.0.3...5.0.4
[5.0.3]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.0.2...5.0.3
[5.0.2]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.0.1...5.0.2
[5.0.1]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.0.0...5.0.1
[5.0.0]: https://github.com/sebastianbergmann/php-code-coverage/compare/4.0...5.0.0

View File

@@ -0,0 +1,19 @@
# Changes in PHP_CodeCoverage 5.1
All notable changes of the PHP_CodeCoverage 5.1 release series are documented in this file using the [Keep a CHANGELOG](http://keepachangelog.com/) principles.
## [5.1.1] - 2017-04-12
## Fixed
* Fixed [#420](https://github.com/sebastianbergmann/php-code-coverage/issues/420): Check for unexecuted covered or used code is too strict
## [5.1.0] - 2017-04-07
## Changed
* Implemented [#516](https://github.com/sebastianbergmann/php-code-coverage/pull/516): Add more information to XML code coverage report
[5.1.1]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.1.0...5.1.1
[5.1.0]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.0...5.1.0

View File

@@ -0,0 +1,44 @@
# Changes in PHP_CodeCoverage 5.2
All notable changes of the PHP_CodeCoverage 5.2 release series are documented in this file using the [Keep a CHANGELOG](http://keepachangelog.com/) principles.
## [5.2.4] - 2017-11-27
### Fixed
* Fixed [#424](https://github.com/sebastianbergmann/php-code-coverage/issues/424): Rest of a function or method is ignored after an anonymous function
* Fixed [#455](https://github.com/sebastianbergmann/php-code-coverage/issues/455): Dashboard does not handle namespaced classes properly
* Fixed [#468](https://github.com/sebastianbergmann/php-code-coverage/issues/468): Global functions are not properly counted
* Fixed [#560](https://github.com/sebastianbergmann/php-code-coverage/issues/560): Uncovered whitelisted files are missing from the report
## [5.2.3] - 2017-11-03
### Fixed
* Fixed [#540](https://github.com/sebastianbergmann/php-code-coverage/issues/540): Missing attribute `type` in the CSS `<link>` elements
* Fixed [#554](https://github.com/sebastianbergmann/php-code-coverage/pull/554): `Parameter must be an array or an object that implements Countable`
## [5.2.2] - 2017-08-03
## Changed
* Bumped required versions of dependencies
## [5.2.1] - 2017-04-21
## Changed
* Version 3 of `sebastian/environment` is now required
## [5.2.0] - 2017-04-20
## Changed
* Implemented [#518](https://github.com/sebastianbergmann/php-code-coverage/pull/518): Add more information to XML code coverage report
[5.2.4]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.2.3...5.2.4
[5.2.3]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.2.2...5.2.3
[5.2.2]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.2.1...5.2.2
[5.2.1]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.2.0...5.2.1
[5.2.0]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.1...5.2.0

View File

@@ -0,0 +1,16 @@
# Changes in PHP_CodeCoverage 5.3
All notable changes of the PHP_CodeCoverage 5.3 release series are documented in this file using the [Keep a CHANGELOG](http://keepachangelog.com/) principles.
## [5.3.0] - 2017-12-06
### Added
* Added option to ignore the `forceCoversAnnotation="true"` setting for a single test
### Fixed
* Fixed [#564](https://github.com/sebastianbergmann/php-code-coverage/issues/564): `setDisableIgnoredLines(true)` disables more than it should
[5.3.0]: https://github.com/sebastianbergmann/php-code-coverage/compare/5.2...5.3.0

View File

@@ -1,6 +1,6 @@
PHP_CodeCoverage
Copyright (c) 2009-2015, Sebastian Bergmann <sebastian@phpunit.de>.
Copyright (c) 2009-2017, Sebastian Bergmann <sebastian@phpunit.de>.
All rights reserved.
Redistribution and use in source and binary forms, with or without

View File

@@ -1,25 +1,9 @@
[![Latest Stable Version](https://poser.pugx.org/phpunit/php-code-coverage/v/stable.png)](https://packagist.org/packages/phpunit/php-code-coverage)
[![Build Status](https://travis-ci.org/sebastianbergmann/php-code-coverage.svg?branch=master)](https://travis-ci.org/sebastianbergmann/php-code-coverage)
[![Build Status](https://travis-ci.org/sebastianbergmann/php-code-coverage.svg?branch=5.3)](https://travis-ci.org/sebastianbergmann/php-code-coverage)
# PHP_CodeCoverage
# SebastianBergmann\CodeCoverage
**PHP_CodeCoverage** is a library that provides collection, processing, and rendering functionality for PHP code coverage information.
## Requirements
PHP 5.6 is required but using the latest version of PHP is highly recommended.
### PHP 5
[Xdebug](http://xdebug.org/) is the only source of raw code coverage data supported for PHP 5. Version 2.2.1 of Xdebug is required but using the latest version is highly recommended.
### PHP 7
Version 2.4.0 (or later) of [Xdebug](http://xdebug.org/) as well as [phpdbg](http://phpdbg.com/docs) are supported sources of raw code coverage data for PHP 7.
### HHVM
A version of HHVM that implements the Xdebug API for code coverage (`xdebug_*_code_coverage()`) is required.
**SebastianBergmann\CodeCoverage** is a library that provides collection, processing, and rendering functionality for PHP code coverage information.
## Installation
@@ -31,11 +15,16 @@ If you only need this library during development, for instance to run your proje
composer require --dev phpunit/php-code-coverage
## Using the PHP_CodeCoverage API
## Using the SebastianBergmann\CodeCoverage API
```php
<?php
$coverage = new \SebastianBergmann\CodeCoverage\CodeCoverage;
use SebastianBergmann\CodeCoverage\CodeCoverage;
$coverage = new CodeCoverage;
$coverage->filter()->addDirectoryToWhitelist('/path/to/src');
$coverage->start('<name of test>');
// ...

View File

@@ -1,41 +1,19 @@
<?xml version="1.0" encoding="UTF-8"?>
<project name="PHP_CodeCoverage">
<target name="clean" description="Cleanup build artifacts">
<delete dir="${basedir}/vendor"/>
<delete file="${basedir}/composer.lock"/>
<project name="php-code-coverage" default="setup">
<target name="setup" depends="clean,composer"/>
<delete>
<fileset dir="${basedir}/build">
<include name="**/*.phar" />
</fileset>
</delete>
</target>
<target name="clean" description="Cleanup build artifacts">
<delete dir="${basedir}/vendor"/>
<delete file="${basedir}/composer.lock"/>
</target>
<target name="composer" depends="clean" description="Install dependencies with Composer">
<tstamp>
<format property="thirty.days.ago" pattern="MM/dd/yyyy hh:mm aa" offset="-30" unit="day"/>
</tstamp>
<delete>
<fileset dir="${basedir}">
<include name="composer.phar" />
<date datetime="${thirty.days.ago}" when="before"/>
</fileset>
</delete>
<get src="https://getcomposer.org/composer.phar" dest="${basedir}/composer.phar" skipexisting="true"/>
<exec executable="php">
<arg value="composer.phar"/>
<arg value="install"/>
</exec>
</target>
<target name="phpcs" description="Find coding standard violations using PHP_CodeSniffer">
<exec executable="phpcs">
<arg value="--standard=PSR2" />
<arg value="--extensions=php" />
<arg path="${basedir}/src" />
<arg path="${basedir}/tests" />
</exec>
</target>
<target name="composer" depends="clean" description="Install dependencies with Composer">
<exec executable="composer" taskname="composer">
<arg value="update"/>
<arg value="--no-interaction"/>
<arg value="--no-progress"/>
<arg value="--no-ansi"/>
<arg value="--no-suggest"/>
</exec>
</target>
</project>

View File

@@ -12,31 +12,35 @@
"authors": [
{
"name": "Sebastian Bergmann",
"email": "sb@sebastian-bergmann.de",
"email": "sebastian@phpunit.de",
"role": "lead"
}
],
"support": {
"issues": "https://github.com/sebastianbergmann/php-code-coverage/issues",
"irc": "irc://irc.freenode.net/phpunit"
"issues": "https://github.com/sebastianbergmann/php-code-coverage/issues"
},
"config": {
"optimize-autoloader": true,
"sort-packages": true
},
"prefer-stable": true,
"require": {
"php": "^5.6 || ^7.0",
"phpunit/php-file-iterator": "~1.3",
"phpunit/php-token-stream": "^1.4.2",
"phpunit/php-text-template": "~1.2",
"sebastian/code-unit-reverse-lookup": "~1.0",
"sebastian/environment": "^1.3.2 || ^2.0",
"sebastian/version": "~1.0|~2.0"
"php": "^7.0",
"ext-dom": "*",
"ext-xmlwriter": "*",
"phpunit/php-file-iterator": "^1.4.2",
"phpunit/php-token-stream": "^2.0.1",
"phpunit/php-text-template": "^1.2.1",
"sebastian/code-unit-reverse-lookup": "^1.0.1",
"sebastian/environment": "^3.0",
"sebastian/version": "^2.0.1",
"theseer/tokenizer": "^1.1"
},
"require-dev": {
"phpunit/phpunit": "^5.4",
"ext-xdebug": ">=2.1.4"
"phpunit/phpunit": "^6.0"
},
"suggest": {
"ext-dom": "*",
"ext-xdebug": ">=2.4.0",
"ext-xmlwriter": "*"
"ext-xdebug": "^2.5.5"
},
"autoload": {
"classmap": [
@@ -45,7 +49,7 @@
},
"extra": {
"branch-alias": {
"dev-master": "4.0.x-dev"
"dev-master": "5.3.x-dev"
}
}
}

View File

@@ -1,16 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/5.3/phpunit.xsd"
bootstrap="../tests/bootstrap.php"
xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/6.0/phpunit.xsd"
bootstrap="tests/bootstrap.php"
backupGlobals="false"
verbose="true">
<testsuite>
<directory suffix="Test.php">../tests/tests</directory>
<testsuite name="default">
<directory suffix="Test.php">tests/tests</directory>
</testsuite>
<filter>
<whitelist processUncoveredFilesFromWhitelist="true">
<directory suffix=".php">../src</directory>
<directory suffix=".php">src</directory>
</whitelist>
</filter>
<php>
<ini name="serialize_precision" value="14"/>
</php>
</phpunit>

View File

@@ -10,10 +10,12 @@
namespace SebastianBergmann\CodeCoverage;
use PHPUnit\Framework\TestCase;
use PHPUnit\Runner\PhptTestCase;
use SebastianBergmann\CodeCoverage\Driver\Driver;
use SebastianBergmann\CodeCoverage\Driver\Xdebug;
use SebastianBergmann\CodeCoverage\Driver\HHVM;
use SebastianBergmann\CodeCoverage\Driver\PHPDBG;
use SebastianBergmann\CodeCoverage\Driver\Xdebug;
use SebastianBergmann\CodeCoverage\Node\Builder;
use SebastianBergmann\CodeCoverage\Node\Directory;
use SebastianBergmann\CodeUnitReverseLookup\Wizard;
@@ -127,6 +129,11 @@ class CodeCoverage
*/
private $shouldCheckForDeadAndUnused = true;
/**
* @var Directory
*/
private $report;
/**
* Constructor.
*
@@ -158,9 +165,13 @@ class CodeCoverage
*/
public function getReport()
{
$builder = new Builder;
if ($this->report === null) {
$builder = new Builder;
return $builder->build($this);
$this->report = $builder->build($this);
}
return $this->report;
}
/**
@@ -172,6 +183,7 @@ class CodeCoverage
$this->currentId = null;
$this->data = [];
$this->tests = [];
$this->report = null;
}
/**
@@ -208,7 +220,8 @@ class CodeCoverage
*/
public function setData(array $data)
{
$this->data = $data;
$this->data = $data;
$this->report = null;
}
/**
@@ -241,7 +254,7 @@ class CodeCoverage
*/
public function start($id, $clear = false)
{
if (!is_bool($clear)) {
if (!\is_bool($clear)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -267,21 +280,23 @@ class CodeCoverage
* @param bool $append
* @param mixed $linesToBeCovered
* @param array $linesToBeUsed
* @param bool $ignoreForceCoversAnnotation
*
* @return array
*
* @throws \SebastianBergmann\CodeCoverage\RuntimeException
* @throws InvalidArgumentException
*/
public function stop($append = true, $linesToBeCovered = [], array $linesToBeUsed = [])
public function stop($append = true, $linesToBeCovered = [], array $linesToBeUsed = [], $ignoreForceCoversAnnotation = false)
{
if (!is_bool($append)) {
if (!\is_bool($append)) {
throw InvalidArgumentException::create(
1,
'boolean'
);
}
if (!is_array($linesToBeCovered) && $linesToBeCovered !== false) {
if (!\is_array($linesToBeCovered) && $linesToBeCovered !== false) {
throw InvalidArgumentException::create(
2,
'array or false'
@@ -289,7 +304,7 @@ class CodeCoverage
}
$data = $this->driver->stop();
$this->append($data, null, $append, $linesToBeCovered, $linesToBeUsed);
$this->append($data, null, $append, $linesToBeCovered, $linesToBeUsed, $ignoreForceCoversAnnotation);
$this->currentId = null;
@@ -304,10 +319,16 @@ class CodeCoverage
* @param bool $append
* @param mixed $linesToBeCovered
* @param array $linesToBeUsed
* @param bool $ignoreForceCoversAnnotation
*
* @throws \SebastianBergmann\CodeCoverage\UnintentionallyCoveredCodeException
* @throws \SebastianBergmann\CodeCoverage\MissingCoversAnnotationException
* @throws \SebastianBergmann\CodeCoverage\CoveredCodeNotExecutedException
* @throws \ReflectionException
* @throws \SebastianBergmann\CodeCoverage\InvalidArgumentException
* @throws RuntimeException
*/
public function append(array $data, $id = null, $append = true, $linesToBeCovered = [], array $linesToBeUsed = [])
public function append(array $data, $id = null, $append = true, $linesToBeCovered = [], array $linesToBeUsed = [], $ignoreForceCoversAnnotation = false)
{
if ($id === null) {
$id = $this->currentId;
@@ -325,11 +346,12 @@ class CodeCoverage
return;
}
if ($id != 'UNCOVERED_FILES_FROM_WHITELIST') {
if ($id !== 'UNCOVERED_FILES_FROM_WHITELIST') {
$this->applyCoversAnnotationFilter(
$data,
$linesToBeCovered,
$linesToBeUsed
$linesToBeUsed,
$ignoreForceCoversAnnotation
);
}
@@ -340,20 +362,20 @@ class CodeCoverage
$size = 'unknown';
$status = null;
if ($id instanceof \PHPUnit_Framework_TestCase) {
if ($id instanceof TestCase) {
$_size = $id->getSize();
if ($_size == \PHPUnit_Util_Test::SMALL) {
if ($_size === \PHPUnit\Util\Test::SMALL) {
$size = 'small';
} elseif ($_size == \PHPUnit_Util_Test::MEDIUM) {
} elseif ($_size === \PHPUnit\Util\Test::MEDIUM) {
$size = 'medium';
} elseif ($_size == \PHPUnit_Util_Test::LARGE) {
} elseif ($_size === \PHPUnit\Util\Test::LARGE) {
$size = 'large';
}
$status = $id->getStatus();
$id = get_class($id) . '::' . $id->getName();
} elseif ($id instanceof \PHPUnit_Extensions_PhptTestCase) {
$id = \get_class($id) . '::' . $id->getName();
} elseif ($id instanceof PhptTestCase) {
$size = 'large';
$id = $id->getName();
}
@@ -366,13 +388,15 @@ class CodeCoverage
}
foreach ($lines as $k => $v) {
if ($v == Driver::LINE_EXECUTED) {
if (empty($this->data[$file][$k]) || !in_array($id, $this->data[$file][$k])) {
if ($v === Driver::LINE_EXECUTED) {
if (empty($this->data[$file][$k]) || !\in_array($id, $this->data[$file][$k])) {
$this->data[$file][$k][] = $id;
}
}
}
}
$this->report = null;
}
/**
@@ -380,10 +404,10 @@ class CodeCoverage
*
* @param CodeCoverage $that
*/
public function merge(CodeCoverage $that)
public function merge(self $that)
{
$this->filter->setWhitelistedFiles(
array_merge($this->filter->getWhitelistedFiles(), $that->filter()->getWhitelistedFiles())
\array_merge($this->filter->getWhitelistedFiles(), $that->filter()->getWhitelistedFiles())
);
foreach ($that->data as $file => $lines) {
@@ -400,15 +424,16 @@ class CodeCoverage
if (!isset($this->data[$file][$line])) {
$this->data[$file][$line] = $data;
} else {
$this->data[$file][$line] = array_unique(
array_merge($this->data[$file][$line], $data)
$this->data[$file][$line] = \array_unique(
\array_merge($this->data[$file][$line], $data)
);
}
}
}
}
$this->tests = array_merge($this->tests, $that->getTests());
$this->tests = \array_merge($this->tests, $that->getTests());
$this->report = null;
}
/**
@@ -418,7 +443,7 @@ class CodeCoverage
*/
public function setCacheTokens($flag)
{
if (!is_bool($flag)) {
if (!\is_bool($flag)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -443,7 +468,7 @@ class CodeCoverage
*/
public function setCheckForUnintentionallyCoveredCode($flag)
{
if (!is_bool($flag)) {
if (!\is_bool($flag)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -460,7 +485,7 @@ class CodeCoverage
*/
public function setForceCoversAnnotation($flag)
{
if (!is_bool($flag)) {
if (!\is_bool($flag)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -477,7 +502,7 @@ class CodeCoverage
*/
public function setCheckForMissingCoversAnnotation($flag)
{
if (!is_bool($flag)) {
if (!\is_bool($flag)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -494,7 +519,7 @@ class CodeCoverage
*/
public function setCheckForUnexecutedCoveredCode($flag)
{
if (!is_bool($flag)) {
if (!\is_bool($flag)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -522,7 +547,7 @@ class CodeCoverage
*/
public function setAddUncoveredFilesFromWhitelist($flag)
{
if (!is_bool($flag)) {
if (!\is_bool($flag)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -539,7 +564,7 @@ class CodeCoverage
*/
public function setProcessUncoveredFilesFromWhitelist($flag)
{
if (!is_bool($flag)) {
if (!\is_bool($flag)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -556,7 +581,7 @@ class CodeCoverage
*/
public function setDisableIgnoredLines($flag)
{
if (!is_bool($flag)) {
if (!\is_bool($flag)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -573,7 +598,7 @@ class CodeCoverage
*/
public function setIgnoreDeprecatedCode($flag)
{
if (!is_bool($flag)) {
if (!\is_bool($flag)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -597,14 +622,17 @@ class CodeCoverage
* @param array $data
* @param mixed $linesToBeCovered
* @param array $linesToBeUsed
* @param bool $ignoreForceCoversAnnotation
*
* @throws \SebastianBergmann\CodeCoverage\CoveredCodeNotExecutedException
* @throws \ReflectionException
* @throws MissingCoversAnnotationException
* @throws UnintentionallyCoveredCodeException
*/
private function applyCoversAnnotationFilter(array &$data, $linesToBeCovered, array $linesToBeUsed)
private function applyCoversAnnotationFilter(array &$data, $linesToBeCovered, array $linesToBeUsed, $ignoreForceCoversAnnotation)
{
if ($linesToBeCovered === false ||
($this->forceCoversAnnotation && empty($linesToBeCovered))) {
($this->forceCoversAnnotation && empty($linesToBeCovered) && !$ignoreForceCoversAnnotation)) {
if ($this->checkForMissingCoversAnnotation) {
throw new MissingCoversAnnotationException;
}
@@ -618,27 +646,21 @@ class CodeCoverage
return;
}
if ($this->checkForUnintentionallyCoveredCode) {
$this->performUnintentionallyCoveredCodeCheck(
$data,
$linesToBeCovered,
$linesToBeUsed
);
if ($this->checkForUnintentionallyCoveredCode &&
(!$this->currentId instanceof TestCase ||
(!$this->currentId->isMedium() && !$this->currentId->isLarge()))) {
$this->performUnintentionallyCoveredCodeCheck($data, $linesToBeCovered, $linesToBeUsed);
}
if ($this->checkForUnexecutedCoveredCode) {
$this->performUnexecutedCoveredCodeCheck($data, $linesToBeCovered, $linesToBeUsed);
}
$data = array_intersect_key($data, $linesToBeCovered);
$data = \array_intersect_key($data, $linesToBeCovered);
foreach (array_keys($data) as $filename) {
$_linesToBeCovered = array_flip($linesToBeCovered[$filename]);
$data[$filename] = array_intersect_key(
$data[$filename],
$_linesToBeCovered
);
foreach (\array_keys($data) as $filename) {
$_linesToBeCovered = \array_flip($linesToBeCovered[$filename]);
$data[$filename] = \array_intersect_key($data[$filename], $_linesToBeCovered);
}
}
@@ -649,7 +671,7 @@ class CodeCoverage
*/
private function applyListsFilter(array &$data)
{
foreach (array_keys($data) as $filename) {
foreach (\array_keys($data) as $filename) {
if ($this->filter->isFiltered($filename)) {
unset($data[$filename]);
}
@@ -660,10 +682,12 @@ class CodeCoverage
* Applies the "ignored lines" filtering.
*
* @param array $data
*
* @throws \SebastianBergmann\CodeCoverage\InvalidArgumentException
*/
private function applyIgnoredLinesFilter(array &$data)
{
foreach (array_keys($data) as $filename) {
foreach (\array_keys($data) as $filename) {
if (!$this->filter->isFile($filename)) {
continue;
}
@@ -680,11 +704,11 @@ class CodeCoverage
private function initializeFilesThatAreSeenTheFirstTime(array $data)
{
foreach ($data as $file => $lines) {
if ($this->filter->isFile($file) && !isset($this->data[$file])) {
if (!isset($this->data[$file]) && $this->filter->isFile($file)) {
$this->data[$file] = [];
foreach ($lines as $k => $v) {
$this->data[$file][$k] = $v == -2 ? null : [];
$this->data[$file][$k] = $v === -2 ? null : [];
}
}
}
@@ -696,24 +720,22 @@ class CodeCoverage
private function addUncoveredFilesFromWhitelist()
{
$data = [];
$uncoveredFiles = array_diff(
$uncoveredFiles = \array_diff(
$this->filter->getWhitelist(),
array_keys($this->data)
\array_keys($this->data)
);
foreach ($uncoveredFiles as $uncoveredFile) {
if (!file_exists($uncoveredFile)) {
if (!\file_exists($uncoveredFile)) {
continue;
}
if (!$this->processUncoveredFilesFromWhitelist) {
$data[$uncoveredFile] = [];
$data[$uncoveredFile] = [];
$lines = count(file($uncoveredFile));
$lines = \count(\file($uncoveredFile));
for ($i = 1; $i <= $lines; $i++) {
$data[$uncoveredFile][$i] = Driver::LINE_NOT_EXECUTED;
}
for ($i = 1; $i <= $lines; $i++) {
$data[$uncoveredFile][$i] = Driver::LINE_NOT_EXECUTED;
}
}
@@ -731,168 +753,185 @@ class CodeCoverage
*/
private function getLinesToBeIgnored($filename)
{
if (!is_string($filename)) {
if (!\is_string($filename)) {
throw InvalidArgumentException::create(
1,
'string'
);
}
if (!isset($this->ignoredLines[$filename])) {
$this->ignoredLines[$filename] = [];
if (isset($this->ignoredLines[$filename])) {
return $this->ignoredLines[$filename];
}
if ($this->disableIgnoredLines) {
return $this->ignoredLines[$filename];
$this->ignoredLines[$filename] = [];
$lines = \file($filename);
foreach ($lines as $index => $line) {
if (!\trim($line)) {
$this->ignoredLines[$filename][] = $index + 1;
}
}
$ignore = false;
$stop = false;
$lines = file($filename);
$numLines = count($lines);
if ($this->cacheTokens) {
$tokens = \PHP_Token_Stream_CachingFactory::get($filename);
} else {
$tokens = new \PHP_Token_Stream($filename);
}
foreach ($lines as $index => $line) {
if (!trim($line)) {
$this->ignoredLines[$filename][] = $index + 1;
}
foreach ($tokens->getInterfaces() as $interface) {
$interfaceStartLine = $interface['startLine'];
$interfaceEndLine = $interface['endLine'];
foreach (\range($interfaceStartLine, $interfaceEndLine) as $line) {
$this->ignoredLines[$filename][] = $line;
}
}
if ($this->cacheTokens) {
$tokens = \PHP_Token_Stream_CachingFactory::get($filename);
} else {
$tokens = new \PHP_Token_Stream($filename);
}
foreach (\array_merge($tokens->getClasses(), $tokens->getTraits()) as $classOrTrait) {
$classOrTraitStartLine = $classOrTrait['startLine'];
$classOrTraitEndLine = $classOrTrait['endLine'];
$classes = array_merge($tokens->getClasses(), $tokens->getTraits());
$tokens = $tokens->tokens();
foreach ($tokens as $token) {
switch (get_class($token)) {
case 'PHP_Token_COMMENT':
case 'PHP_Token_DOC_COMMENT':
$_token = trim($token);
$_line = trim($lines[$token->getLine() - 1]);
if ($_token == '// @codeCoverageIgnore' ||
$_token == '//@codeCoverageIgnore') {
$ignore = true;
$stop = true;
} elseif ($_token == '// @codeCoverageIgnoreStart' ||
$_token == '//@codeCoverageIgnoreStart') {
$ignore = true;
} elseif ($_token == '// @codeCoverageIgnoreEnd' ||
$_token == '//@codeCoverageIgnoreEnd') {
$stop = true;
}
if (!$ignore) {
$start = $token->getLine();
$end = $start + substr_count($token, "\n");
// Do not ignore the first line when there is a token
// before the comment
if (0 !== strpos($_token, $_line)) {
$start++;
}
for ($i = $start; $i < $end; $i++) {
$this->ignoredLines[$filename][] = $i;
}
// A DOC_COMMENT token or a COMMENT token starting with "/*"
// does not contain the final \n character in its text
if (isset($lines[$i-1]) && 0 === strpos($_token, '/*') && '*/' === substr(trim($lines[$i-1]), -2)) {
$this->ignoredLines[$filename][] = $i;
}
}
break;
case 'PHP_Token_INTERFACE':
case 'PHP_Token_TRAIT':
case 'PHP_Token_CLASS':
case 'PHP_Token_FUNCTION':
/* @var \PHP_Token_Interface $token */
$docblock = $token->getDocblock();
$this->ignoredLines[$filename][] = $token->getLine();
if (strpos($docblock, '@codeCoverageIgnore') || ($this->ignoreDeprecatedCode && strpos($docblock, '@deprecated'))) {
$endLine = $token->getEndLine();
for ($i = $token->getLine(); $i <= $endLine; $i++) {
$this->ignoredLines[$filename][] = $i;
}
} elseif ($token instanceof \PHP_Token_INTERFACE ||
$token instanceof \PHP_Token_TRAIT ||
$token instanceof \PHP_Token_CLASS) {
if (empty($classes[$token->getName()]['methods'])) {
for ($i = $token->getLine();
$i <= $token->getEndLine();
$i++) {
$this->ignoredLines[$filename][] = $i;
}
} else {
$firstMethod = array_shift(
$classes[$token->getName()]['methods']
);
do {
$lastMethod = array_pop(
$classes[$token->getName()]['methods']
);
} while ($lastMethod !== null &&
substr($lastMethod['signature'], 0, 18) == 'anonymous function');
if ($lastMethod === null) {
$lastMethod = $firstMethod;
}
for ($i = $token->getLine();
$i < $firstMethod['startLine'];
$i++) {
$this->ignoredLines[$filename][] = $i;
}
for ($i = $token->getEndLine();
$i > $lastMethod['endLine'];
$i--) {
$this->ignoredLines[$filename][] = $i;
}
}
}
break;
case 'PHP_Token_NAMESPACE':
$this->ignoredLines[$filename][] = $token->getEndLine();
// Intentional fallthrough
case 'PHP_Token_DECLARE':
case 'PHP_Token_OPEN_TAG':
case 'PHP_Token_CLOSE_TAG':
case 'PHP_Token_USE':
$this->ignoredLines[$filename][] = $token->getLine();
break;
if (empty($classOrTrait['methods'])) {
foreach (\range($classOrTraitStartLine, $classOrTraitEndLine) as $line) {
$this->ignoredLines[$filename][] = $line;
}
if ($ignore) {
continue;
}
$firstMethod = \array_shift($classOrTrait['methods']);
$firstMethodStartLine = $firstMethod['startLine'];
$firstMethodEndLine = $firstMethod['endLine'];
$lastMethodEndLine = $firstMethodEndLine;
do {
$lastMethod = \array_pop($classOrTrait['methods']);
} while ($lastMethod !== null && 0 === \strpos($lastMethod['signature'], 'anonymousFunction'));
if ($lastMethod !== null) {
$lastMethodEndLine = $lastMethod['endLine'];
}
foreach (\range($classOrTraitStartLine, $firstMethodStartLine) as $line) {
$this->ignoredLines[$filename][] = $line;
}
foreach (\range($lastMethodEndLine + 1, $classOrTraitEndLine) as $line) {
$this->ignoredLines[$filename][] = $line;
}
}
if ($this->disableIgnoredLines) {
$this->ignoredLines[$filename] = array_unique($this->ignoredLines[$filename]);
\sort($this->ignoredLines[$filename]);
return $this->ignoredLines[$filename];
}
$ignore = false;
$stop = false;
foreach ($tokens->tokens() as $token) {
switch (\get_class($token)) {
case \PHP_Token_COMMENT::class:
case \PHP_Token_DOC_COMMENT::class:
$_token = \trim($token);
$_line = \trim($lines[$token->getLine() - 1]);
if ($_token === '// @codeCoverageIgnore' ||
$_token === '//@codeCoverageIgnore') {
$ignore = true;
$stop = true;
} elseif ($_token === '// @codeCoverageIgnoreStart' ||
$_token === '//@codeCoverageIgnoreStart') {
$ignore = true;
} elseif ($_token === '// @codeCoverageIgnoreEnd' ||
$_token === '//@codeCoverageIgnoreEnd') {
$stop = true;
}
if (!$ignore) {
$start = $token->getLine();
$end = $start + \substr_count($token, "\n");
// Do not ignore the first line when there is a token
// before the comment
if (0 !== \strpos($_token, $_line)) {
$start++;
}
for ($i = $start; $i < $end; $i++) {
$this->ignoredLines[$filename][] = $i;
}
// A DOC_COMMENT token or a COMMENT token starting with "/*"
// does not contain the final \n character in its text
if (isset($lines[$i - 1]) && 0 === \strpos($_token, '/*') && '*/' === \substr(\trim($lines[$i - 1]), -2)) {
$this->ignoredLines[$filename][] = $i;
}
}
break;
case \PHP_Token_INTERFACE::class:
case \PHP_Token_TRAIT::class:
case \PHP_Token_CLASS::class:
case \PHP_Token_FUNCTION::class:
/* @var \PHP_Token_Interface $token */
$docblock = $token->getDocblock();
$this->ignoredLines[$filename][] = $token->getLine();
if ($stop) {
$ignore = false;
$stop = false;
if (\strpos($docblock, '@codeCoverageIgnore') || ($this->ignoreDeprecatedCode && \strpos($docblock, '@deprecated'))) {
$endLine = $token->getEndLine();
for ($i = $token->getLine(); $i <= $endLine; $i++) {
$this->ignoredLines[$filename][] = $i;
}
}
}
break;
case \PHP_Token_ENUM::class:
$this->ignoredLines[$filename][] = $token->getLine();
break;
case \PHP_Token_NAMESPACE::class:
$this->ignoredLines[$filename][] = $token->getEndLine();
// Intentional fallthrough
case \PHP_Token_DECLARE::class:
case \PHP_Token_OPEN_TAG::class:
case \PHP_Token_CLOSE_TAG::class:
case \PHP_Token_USE::class:
$this->ignoredLines[$filename][] = $token->getLine();
break;
}
$this->ignoredLines[$filename][] = $numLines + 1;
if ($ignore) {
$this->ignoredLines[$filename][] = $token->getLine();
$this->ignoredLines[$filename] = array_unique(
$this->ignoredLines[$filename]
);
sort($this->ignoredLines[$filename]);
if ($stop) {
$ignore = false;
$stop = false;
}
}
}
$this->ignoredLines[$filename][] = \count($lines) + 1;
$this->ignoredLines[$filename] = \array_unique(
$this->ignoredLines[$filename]
);
$this->ignoredLines[$filename] = array_unique($this->ignoredLines[$filename]);
\sort($this->ignoredLines[$filename]);
return $this->ignoredLines[$filename];
}
@@ -901,6 +940,7 @@ class CodeCoverage
* @param array $linesToBeCovered
* @param array $linesToBeUsed
*
* @throws \ReflectionException
* @throws UnintentionallyCoveredCodeException
*/
private function performUnintentionallyCoveredCodeCheck(array &$data, array $linesToBeCovered, array $linesToBeUsed)
@@ -914,7 +954,7 @@ class CodeCoverage
foreach ($data as $file => $_data) {
foreach ($_data as $line => $flag) {
if ($flag == 1 && !isset($allowedLines[$file][$line])) {
if ($flag === 1 && !isset($allowedLines[$file][$line])) {
$unintentionallyCoveredUnits[] = $this->wizard->lookup($file, $line);
}
}
@@ -938,30 +978,24 @@ class CodeCoverage
*/
private function performUnexecutedCoveredCodeCheck(array &$data, array $linesToBeCovered, array $linesToBeUsed)
{
$expectedLines = $this->getAllowedLines(
$linesToBeCovered,
$linesToBeUsed
);
$executedCodeUnits = $this->coverageToCodeUnits($data);
$message = '';
foreach ($data as $file => $_data) {
foreach (array_keys($_data) as $line) {
if (!isset($expectedLines[$file][$line])) {
continue;
}
unset($expectedLines[$file][$line]);
foreach ($this->linesToCodeUnits($linesToBeCovered) as $codeUnit) {
if (!\in_array($codeUnit, $executedCodeUnits)) {
$message .= \sprintf(
'- %s is expected to be executed (@covers) but was not executed' . "\n",
$codeUnit
);
}
}
$message = '';
foreach ($expectedLines as $file => $lines) {
if (empty($lines)) {
continue;
}
foreach (array_keys($lines) as $line) {
$message .= sprintf('- %s:%d' . PHP_EOL, $file, $line);
foreach ($this->linesToCodeUnits($linesToBeUsed) as $codeUnit) {
if (!\in_array($codeUnit, $executedCodeUnits)) {
$message .= \sprintf(
'- %s is expected to be executed (@uses) but was not executed' . "\n",
$codeUnit
);
}
}
@@ -980,31 +1014,31 @@ class CodeCoverage
{
$allowedLines = [];
foreach (array_keys($linesToBeCovered) as $file) {
foreach (\array_keys($linesToBeCovered) as $file) {
if (!isset($allowedLines[$file])) {
$allowedLines[$file] = [];
}
$allowedLines[$file] = array_merge(
$allowedLines[$file] = \array_merge(
$allowedLines[$file],
$linesToBeCovered[$file]
);
}
foreach (array_keys($linesToBeUsed) as $file) {
foreach (\array_keys($linesToBeUsed) as $file) {
if (!isset($allowedLines[$file])) {
$allowedLines[$file] = [];
}
$allowedLines[$file] = array_merge(
$allowedLines[$file] = \array_merge(
$allowedLines[$file],
$linesToBeUsed[$file]
);
}
foreach (array_keys($allowedLines) as $file) {
$allowedLines[$file] = array_flip(
array_unique($allowedLines[$file])
foreach (\array_keys($allowedLines) as $file) {
$allowedLines[$file] = \array_flip(
\array_unique($allowedLines[$file])
);
}
@@ -1026,27 +1060,31 @@ class CodeCoverage
if ($runtime->isHHVM()) {
return new HHVM;
} elseif ($runtime->isPHPDBG()) {
return new PHPDBG;
} else {
return new Xdebug;
}
if ($runtime->isPHPDBG()) {
return new PHPDBG;
}
return new Xdebug;
}
/**
* @param array $unintentionallyCoveredUnits
*
* @return array
*
* @throws \ReflectionException
*/
private function processUnintentionallyCoveredUnits(array $unintentionallyCoveredUnits)
{
$unintentionallyCoveredUnits = array_unique($unintentionallyCoveredUnits);
sort($unintentionallyCoveredUnits);
$unintentionallyCoveredUnits = \array_unique($unintentionallyCoveredUnits);
\sort($unintentionallyCoveredUnits);
foreach (array_keys($unintentionallyCoveredUnits) as $k => $v) {
$unit = explode('::', $unintentionallyCoveredUnits[$k]);
foreach (\array_keys($unintentionallyCoveredUnits) as $k => $v) {
$unit = \explode('::', $unintentionallyCoveredUnits[$k]);
if (count($unit) != 2) {
if (\count($unit) !== 2) {
continue;
}
@@ -1055,17 +1093,20 @@ class CodeCoverage
foreach ($this->unintentionallyCoveredSubclassesWhitelist as $whitelisted) {
if ($class->isSubclassOf($whitelisted)) {
unset($unintentionallyCoveredUnits[$k]);
break;
}
}
}
return array_values($unintentionallyCoveredUnits);
return \array_values($unintentionallyCoveredUnits);
}
/**
* If we are processing uncovered files from whitelist,
* we can initialize the data before we start to speed up the tests
*
* @throws \SebastianBergmann\CodeCoverage\RuntimeException
*/
protected function initializeData()
{
@@ -1090,8 +1131,8 @@ class CodeCoverage
continue;
}
foreach (array_keys($fileCoverage) as $key) {
if ($fileCoverage[$key] == Driver::LINE_EXECUTED) {
foreach (\array_keys($fileCoverage) as $key) {
if ($fileCoverage[$key] === Driver::LINE_EXECUTED) {
$fileCoverage[$key] = Driver::LINE_NOT_EXECUTED;
}
}
@@ -1102,4 +1143,42 @@ class CodeCoverage
$this->append($data, 'UNCOVERED_FILES_FROM_WHITELIST');
}
}
/**
* @param array $data
*
* @return array
*/
private function coverageToCodeUnits(array $data)
{
$codeUnits = [];
foreach ($data as $filename => $lines) {
foreach ($lines as $line => $flag) {
if ($flag === 1) {
$codeUnits[] = $this->wizard->lookup($filename, $line);
}
}
}
return \array_unique($codeUnits);
}
/**
* @param array $data
*
* @return array
*/
private function linesToCodeUnits(array $data)
{
$codeUnits = [];
foreach ($data as $filename => $lines) {
foreach ($lines as $line) {
$codeUnits[] = $this->wizard->lookup($filename, $line);
}
}
return \array_unique($codeUnits);
}
}

View File

@@ -24,6 +24,6 @@ class HHVM extends Xdebug
*/
public function start($determineUnusedAndDead = true)
{
xdebug_start_code_coverage();
\xdebug_start_code_coverage();
}
}

View File

@@ -30,7 +30,7 @@ class PHPDBG implements Driver
);
}
if (!function_exists('phpdbg_start_oplog')) {
if (!\function_exists('phpdbg_start_oplog')) {
throw new RuntimeException(
'This build of PHPDBG does not support code coverage'
);
@@ -61,9 +61,9 @@ class PHPDBG implements Driver
if ($fetchedLines == []) {
$sourceLines = phpdbg_get_executable();
} else {
$newFiles = array_diff(
get_included_files(),
array_keys($fetchedLines)
$newFiles = \array_diff(
\get_included_files(),
\array_keys($fetchedLines)
);
if ($newFiles) {
@@ -81,7 +81,7 @@ class PHPDBG implements Driver
}
}
$fetchedLines = array_merge($fetchedLines, $sourceLines);
$fetchedLines = \array_merge($fetchedLines, $sourceLines);
return $this->detectExecutedLines($fetchedLines, $dbgData);
}

View File

@@ -31,12 +31,12 @@ class Xdebug implements Driver
*/
public function __construct()
{
if (!extension_loaded('xdebug')) {
if (!\extension_loaded('xdebug')) {
throw new RuntimeException('This driver requires Xdebug');
}
if (version_compare(phpversion('xdebug'), '2.2.1', '>=') &&
!ini_get('xdebug.coverage_enable')) {
if (\version_compare(\phpversion('xdebug'), '2.2.1', '>=') &&
!\ini_get('xdebug.coverage_enable')) {
throw new RuntimeException(
'xdebug.coverage_enable=On has to be set in php.ini'
);
@@ -51,9 +51,9 @@ class Xdebug implements Driver
public function start($determineUnusedAndDead = true)
{
if ($determineUnusedAndDead) {
xdebug_start_code_coverage(XDEBUG_CC_UNUSED | XDEBUG_CC_DEAD_CODE);
\xdebug_start_code_coverage(XDEBUG_CC_UNUSED | XDEBUG_CC_DEAD_CODE);
} else {
xdebug_start_code_coverage();
\xdebug_start_code_coverage();
}
}
@@ -64,8 +64,8 @@ class Xdebug implements Driver
*/
public function stop()
{
$data = xdebug_get_code_coverage();
xdebug_stop_code_coverage();
$data = \xdebug_get_code_coverage();
\xdebug_stop_code_coverage();
return $this->cleanup($data);
}
@@ -77,13 +77,13 @@ class Xdebug implements Driver
*/
private function cleanup(array $data)
{
foreach (array_keys($data) as $file) {
foreach (\array_keys($data) as $file) {
unset($data[$file][0]);
if (strpos($file, 'xdebug://debug-eval') !== 0 && file_exists($file)) {
if (\strpos($file, 'xdebug://debug-eval') !== 0 && \file_exists($file)) {
$numLines = $this->getNumberOfLinesInFile($file);
foreach (array_keys($data[$file]) as $line) {
foreach (\array_keys($data[$file]) as $line) {
if ($line > $numLines) {
unset($data[$file][$line]);
}
@@ -102,10 +102,10 @@ class Xdebug implements Driver
private function getNumberOfLinesInFile($file)
{
if (!isset($this->cacheNumLines[$file])) {
$buffer = file_get_contents($file);
$lines = substr_count($buffer, "\n");
$buffer = \file_get_contents($file);
$lines = \substr_count($buffer, "\n");
if (substr($buffer, -1) !== "\n") {
if (\substr($buffer, -1) !== "\n") {
$lines++;
}

View File

@@ -21,13 +21,13 @@ class InvalidArgumentException extends \InvalidArgumentException implements Exce
*/
public static function create($argument, $type, $value = null)
{
$stack = debug_backtrace(0);
$stack = \debug_backtrace(0);
return new self(
sprintf(
\sprintf(
'Argument #%d%sof %s::%s() must be a %s',
$argument,
$value !== null ? ' (' . gettype($value) . '#' . $value . ')' : ' (No Value) ',
$value !== null ? ' (' . \gettype($value) . '#' . $value . ')' : ' (No Value) ',
$stack[1]['class'],
$stack[1]['function'],
$type

View File

@@ -46,7 +46,7 @@ class Filter
*/
public function addFileToWhitelist($filename)
{
$this->whitelistedFiles[realpath($filename)] = true;
$this->whitelistedFiles[\realpath($filename)] = true;
}
/**
@@ -85,7 +85,7 @@ class Filter
*/
public function removeFileFromWhitelist($filename)
{
$filename = realpath($filename);
$filename = \realpath($filename);
unset($this->whitelistedFiles[$filename]);
}
@@ -100,17 +100,17 @@ class Filter
public function isFile($filename)
{
if ($filename == '-' ||
strpos($filename, 'vfs://') === 0 ||
strpos($filename, 'xdebug://debug-eval') !== false ||
strpos($filename, 'eval()\'d code') !== false ||
strpos($filename, 'runtime-created function') !== false ||
strpos($filename, 'runkit created function') !== false ||
strpos($filename, 'assert code') !== false ||
strpos($filename, 'regexp code') !== false) {
\strpos($filename, 'vfs://') === 0 ||
\strpos($filename, 'xdebug://debug-eval') !== false ||
\strpos($filename, 'eval()\'d code') !== false ||
\strpos($filename, 'runtime-created function') !== false ||
\strpos($filename, 'runkit created function') !== false ||
\strpos($filename, 'assert code') !== false ||
\strpos($filename, 'regexp code') !== false) {
return false;
}
return file_exists($filename);
return \file_exists($filename);
}
/**
@@ -126,7 +126,7 @@ class Filter
return true;
}
$filename = realpath($filename);
$filename = \realpath($filename);
return !isset($this->whitelistedFiles[$filename]);
}
@@ -138,7 +138,7 @@ class Filter
*/
public function getWhitelist()
{
return array_keys($this->whitelistedFiles);
return \array_keys($this->whitelistedFiles);
}
/**

View File

@@ -48,10 +48,10 @@ abstract class AbstractNode implements \Countable
* @param string $name
* @param AbstractNode $parent
*/
public function __construct($name, AbstractNode $parent = null)
public function __construct($name, self $parent = null)
{
if (substr($name, -1) == '/') {
$name = substr($name, 0, -1);
if (\substr($name, -1) == '/') {
$name = \substr($name, 0, -1);
}
$this->name = $name;
@@ -80,7 +80,7 @@ abstract class AbstractNode implements \Countable
$parentId = $parent->getId();
if ($parentId == 'index') {
$this->id = str_replace(':', '_', $this->name);
$this->id = \str_replace(':', '_', $this->name);
} else {
$this->id = $parentId . '/' . $this->name;
}
@@ -165,7 +165,7 @@ abstract class AbstractNode implements \Countable
}
/**
* Returns the percentage of traits that has been tested.
* Returns the percentage of classes and traits that has been tested.
*
* @param bool $asString
*
@@ -180,6 +180,22 @@ abstract class AbstractNode implements \Countable
);
}
/**
* Returns the percentage of functions that has been tested.
*
* @param bool $asString
*
* @return int
*/
public function getTestedFunctionsPercent($asString = true)
{
return Util::percent(
$this->getNumTestedFunctions(),
$this->getNumFunctions(),
$asString
);
}
/**
* Returns the percentage of methods that has been tested.
*
@@ -196,6 +212,22 @@ abstract class AbstractNode implements \Countable
);
}
/**
* Returns the percentage of functions and methods that has been tested.
*
* @param bool $asString
*
* @return int
*/
public function getTestedFunctionsAndMethodsPercent($asString = true)
{
return Util::percent(
$this->getNumTestedFunctionsAndMethods(),
$this->getNumFunctionsAndMethods(),
$asString
);
}
/**
* Returns the percentage of executed lines.
*
@@ -239,7 +271,37 @@ abstract class AbstractNode implements \Countable
*/
public function getClassesAndTraits()
{
return array_merge($this->getClasses(), $this->getTraits());
return \array_merge($this->getClasses(), $this->getTraits());
}
/**
* Returns the number of functions and methods.
*
* @return int
*/
public function getNumFunctionsAndMethods()
{
return $this->getNumFunctions() + $this->getNumMethods();
}
/**
* Returns the number of tested functions and methods.
*
* @return int
*/
public function getNumTestedFunctionsAndMethods()
{
return $this->getNumTestedFunctions() + $this->getNumTestedMethods();
}
/**
* Returns the functions and methods of this node.
*
* @return array
*/
public function getFunctionsAndMethods()
{
return \array_merge($this->getFunctions(), $this->getMethods());
}
/**

View File

@@ -47,10 +47,10 @@ class Builder
private function addItems(Directory $root, array $items, array $tests, $cacheTokens)
{
foreach ($items as $key => $value) {
if (substr($key, -2) == '/f') {
$key = substr($key, 0, -2);
if (\substr($key, -2) == '/f') {
$key = \substr($key, 0, -2);
if (file_exists($root->getPath() . DIRECTORY_SEPARATOR . $key)) {
if (\file_exists($root->getPath() . DIRECTORY_SEPARATOR . $key)) {
$root->addFile($key, $value, $tests, $cacheTokens);
}
} else {
@@ -109,9 +109,9 @@ class Builder
$result = [];
foreach ($files as $path => $file) {
$path = explode('/', $path);
$path = \explode('/', $path);
$pointer = &$result;
$max = count($path);
$max = \count($path);
for ($i = 0; $i < $max; $i++) {
if ($i == ($max - 1)) {
@@ -177,26 +177,26 @@ class Builder
}
$commonPath = '';
$paths = array_keys($files);
$paths = \array_keys($files);
if (count($files) == 1) {
$commonPath = dirname($paths[0]) . '/';
$files[basename($paths[0])] = $files[$paths[0]];
if (\count($files) == 1) {
$commonPath = \dirname($paths[0]) . '/';
$files[\basename($paths[0])] = $files[$paths[0]];
unset($files[$paths[0]]);
return $commonPath;
}
$max = count($paths);
$max = \count($paths);
for ($i = 0; $i < $max; $i++) {
// strip phar:// prefixes
if (strpos($paths[$i], 'phar://') === 0) {
$paths[$i] = substr($paths[$i], 7);
$paths[$i] = strtr($paths[$i], '/', DIRECTORY_SEPARATOR);
if (\strpos($paths[$i], 'phar://') === 0) {
$paths[$i] = \substr($paths[$i], 7);
$paths[$i] = \strtr($paths[$i], '/', DIRECTORY_SEPARATOR);
}
$paths[$i] = explode(DIRECTORY_SEPARATOR, $paths[$i]);
$paths[$i] = \explode(DIRECTORY_SEPARATOR, $paths[$i]);
if (empty($paths[$i][0])) {
$paths[$i][0] = DIRECTORY_SEPARATOR;
@@ -204,14 +204,15 @@ class Builder
}
$done = false;
$max = count($paths);
$max = \count($paths);
while (!$done) {
for ($i = 0; $i < $max - 1; $i++) {
if (!isset($paths[$i][0]) ||
!isset($paths[$i+1][0]) ||
$paths[$i][0] != $paths[$i+1][0]) {
!isset($paths[$i + 1][0]) ||
$paths[$i][0] != $paths[$i + 1][0]) {
$done = true;
break;
}
}
@@ -224,21 +225,21 @@ class Builder
}
for ($i = 0; $i < $max; $i++) {
array_shift($paths[$i]);
\array_shift($paths[$i]);
}
}
}
$original = array_keys($files);
$max = count($original);
$original = \array_keys($files);
$max = \count($original);
for ($i = 0; $i < $max; $i++) {
$files[implode('/', $paths[$i])] = $files[$original[$i]];
$files[\implode('/', $paths[$i])] = $files[$original[$i]];
unset($files[$original[$i]]);
}
ksort($files);
\ksort($files);
return substr($commonPath, 0, -1);
return \substr($commonPath, 0, -1);
}
}

View File

@@ -118,7 +118,7 @@ class Directory extends AbstractNode implements \IteratorAggregate
$this->numFiles = 0;
foreach ($this->children as $child) {
$this->numFiles += count($child);
$this->numFiles += \count($child);
}
}
@@ -150,7 +150,7 @@ class Directory extends AbstractNode implements \IteratorAggregate
$directory = new self($name, $this);
$this->children[] = $directory;
$this->directories[] = &$this->children[count($this->children) - 1];
$this->directories[] = &$this->children[\count($this->children) - 1];
return $directory;
}
@@ -178,7 +178,7 @@ class Directory extends AbstractNode implements \IteratorAggregate
);
$this->children[] = $file;
$this->files[] = &$this->children[count($this->children) - 1];
$this->files[] = &$this->children[\count($this->children) - 1];
$this->numExecutableLines = -1;
$this->numExecutedLines = -1;
@@ -227,7 +227,7 @@ class Directory extends AbstractNode implements \IteratorAggregate
$this->classes = [];
foreach ($this->children as $child) {
$this->classes = array_merge(
$this->classes = \array_merge(
$this->classes,
$child->getClasses()
);
@@ -248,7 +248,7 @@ class Directory extends AbstractNode implements \IteratorAggregate
$this->traits = [];
foreach ($this->children as $child) {
$this->traits = array_merge(
$this->traits = \array_merge(
$this->traits,
$child->getTraits()
);
@@ -269,7 +269,7 @@ class Directory extends AbstractNode implements \IteratorAggregate
$this->functions = [];
foreach ($this->children as $child) {
$this->functions = array_merge(
$this->functions = \array_merge(
$this->functions,
$child->getFunctions()
);
@@ -292,8 +292,8 @@ class Directory extends AbstractNode implements \IteratorAggregate
foreach ($this->children as $child) {
$linesOfCode = $child->getLinesOfCode();
$this->linesOfCode['loc'] += $linesOfCode['loc'];
$this->linesOfCode['cloc'] += $linesOfCode['cloc'];
$this->linesOfCode['loc'] += $linesOfCode['loc'];
$this->linesOfCode['cloc'] += $linesOfCode['cloc'];
$this->linesOfCode['ncloc'] += $linesOfCode['ncloc'];
}
}

View File

@@ -60,13 +60,23 @@ class File extends AbstractNode
/**
* @var int
*/
private $numTestedTraits = 0;
private $numClasses = null;
/**
* @var int
*/
private $numTestedClasses = 0;
/**
* @var int
*/
private $numTraits = null;
/**
* @var int
*/
private $numTestedTraits = 0;
/**
* @var int
*/
@@ -110,7 +120,7 @@ class File extends AbstractNode
*/
public function __construct($name, AbstractNode $parent, array $coverageData, array $testData, $cacheTokens)
{
if (!is_bool($cacheTokens)) {
if (!\is_bool($cacheTokens)) {
throw InvalidArgumentException::create(
1,
'boolean'
@@ -223,7 +233,21 @@ class File extends AbstractNode
*/
public function getNumClasses()
{
return count($this->classes);
if ($this->numClasses === null) {
$this->numClasses = 0;
foreach ($this->classes as $class) {
foreach ($class['methods'] as $method) {
if ($method['executableLines'] > 0) {
$this->numClasses++;
continue 2;
}
}
}
}
return $this->numClasses;
}
/**
@@ -243,7 +267,21 @@ class File extends AbstractNode
*/
public function getNumTraits()
{
return count($this->traits);
if ($this->numTraits === null) {
$this->numTraits = 0;
foreach ($this->traits as $trait) {
foreach ($trait['methods'] as $method) {
if ($method['executableLines'] > 0) {
$this->numTraits++;
continue 2;
}
}
}
}
return $this->numTraits;
}
/**
@@ -325,7 +363,7 @@ class File extends AbstractNode
*/
public function getNumFunctions()
{
return count($this->functions);
return \count($this->functions);
}
/**
@@ -412,7 +450,7 @@ class File extends AbstractNode
$this->numExecutableLines++;
if (count($this->coverageData[$lineNumber]) > 0) {
if (\count($this->coverageData[$lineNumber]) > 0) {
if (isset($currentClass)) {
$currentClass['executedLines']++;
}
@@ -439,8 +477,8 @@ class File extends AbstractNode
unset($currentClass);
if ($classStack) {
end($classStack);
$key = key($classStack);
\end($classStack);
$key = \key($classStack);
$currentClass = &$classStack[$key];
unset($classStack[$key]);
}
@@ -455,8 +493,8 @@ class File extends AbstractNode
unset($currentFunction);
if ($functionStack) {
end($functionStack);
$key = key($functionStack);
\end($functionStack);
$key = \key($functionStack);
$currentFunction = &$functionStack[$key];
unset($functionStack[$key]);
}
@@ -484,14 +522,14 @@ class File extends AbstractNode
if ($trait['executableLines'] > 0) {
$trait['coverage'] = ($trait['executedLines'] /
$trait['executableLines']) * 100;
if ($trait['coverage'] == 100) {
$this->numTestedClasses++;
}
} else {
$trait['coverage'] = 100;
}
if ($trait['coverage'] == 100) {
$this->numTestedClasses++;
}
$trait['crap'] = $this->crap(
$trait['ccn'],
$trait['coverage']
@@ -518,19 +556,37 @@ class File extends AbstractNode
if ($class['executableLines'] > 0) {
$class['coverage'] = ($class['executedLines'] /
$class['executableLines']) * 100;
if ($class['coverage'] == 100) {
$this->numTestedClasses++;
}
} else {
$class['coverage'] = 100;
}
if ($class['coverage'] == 100) {
$this->numTestedClasses++;
}
$class['crap'] = $this->crap(
$class['ccn'],
$class['coverage']
);
}
foreach ($this->functions as &$function) {
if ($function['executableLines'] > 0) {
$function['coverage'] = ($function['executedLines'] /
$function['executableLines']) * 100;
} else {
$function['coverage'] = 100;
}
if ($function['coverage'] == 100) {
$this->numTestedFunctions++;
}
$function['crap'] = $this->crap(
$function['ccn'],
$function['coverage']
);
}
}
/**
@@ -544,6 +600,10 @@ class File extends AbstractNode
$link = $this->getId() . '.html#';
foreach ($classes as $className => $class) {
if (!empty($class['package']['namespace'])) {
$className = $class['package']['namespace'] . '\\' . $className;
}
$this->classes[$className] = [
'className' => $className,
'methods' => [],
@@ -645,16 +705,16 @@ class File extends AbstractNode
protected function crap($ccn, $coverage)
{
if ($coverage == 0) {
return (string) (pow($ccn, 2) + $ccn);
return (string) (\pow($ccn, 2) + $ccn);
}
if ($coverage >= 95) {
return (string) $ccn;
}
return sprintf(
return \sprintf(
'%01.2F',
pow($ccn, 2) * pow(1 - $coverage/100, 3) + $ccn
\pow($ccn, 2) * \pow(1 - $coverage / 100, 3) + $ccn
);
}

View File

@@ -48,7 +48,7 @@ class Iterator implements \RecursiveIterator
*/
public function valid()
{
return $this->position < count($this->nodes);
return $this->position < \count($this->nodes);
}
/**

View File

@@ -37,7 +37,7 @@ class Clover
$xmlProject = $xmlDocument->createElement('project');
$xmlProject->setAttribute('timestamp', (int) $_SERVER['REQUEST_TIME']);
if (is_string($name)) {
if (\is_string($name)) {
$xmlProject->setAttribute('name', $name);
}
@@ -69,12 +69,12 @@ class Clover
$classMethods = 0;
foreach ($class['methods'] as $methodName => $method) {
if ($method['executableLines'] == 0) {
if ($method['executableLines'] == 0) {
continue;
}
$classMethods++;
$classStatements += $method['executableLines'];
$classStatements += $method['executableLines'];
$coveredClassStatements += $method['executedLines'];
if ($method['coverage'] == 100) {
@@ -83,9 +83,9 @@ class Clover
$methodCount = 0;
foreach (range($method['startLine'], $method['endLine']) as $line) {
foreach (\range($method['startLine'], $method['endLine']) as $line) {
if (isset($coverage[$line]) && ($coverage[$line] !== null)) {
$methodCount = max($methodCount, count($coverage[$line]));
$methodCount = \max($methodCount, \count($coverage[$line]));
}
}
@@ -156,11 +156,11 @@ class Clover
}
$lines[$line] = [
'count' => count($data), 'type' => 'stmt'
'count' => \count($data), 'type' => 'stmt'
];
}
ksort($lines);
\ksort($lines);
foreach ($lines as $line => $data) {
$xmlLine = $xmlDocument->createElement('line');
@@ -222,7 +222,7 @@ class Clover
$linesOfCode = $report->getLinesOfCode();
$xmlMetrics = $xmlDocument->createElement('metrics');
$xmlMetrics->setAttribute('files', count($report));
$xmlMetrics->setAttribute('files', \count($report));
$xmlMetrics->setAttribute('loc', $linesOfCode['loc']);
$xmlMetrics->setAttribute('ncloc', $linesOfCode['ncloc']);
$xmlMetrics->setAttribute('classes', $report->getNumClassesAndTraits());
@@ -239,11 +239,11 @@ class Clover
$buffer = $xmlDocument->saveXML();
if ($target !== null) {
if (!is_dir(dirname($target))) {
mkdir(dirname($target), 0777, true);
if (!\is_dir(\dirname($target))) {
\mkdir(\dirname($target), 0777, true);
}
file_put_contents($target, $buffer);
\file_put_contents($target, $buffer);
}
return $buffer;

View File

@@ -11,8 +11,8 @@
namespace SebastianBergmann\CodeCoverage\Report;
use SebastianBergmann\CodeCoverage\CodeCoverage;
use SebastianBergmann\CodeCoverage\Node\File;
use SebastianBergmann\CodeCoverage\InvalidArgumentException;
use SebastianBergmann\CodeCoverage\Node\File;
class Crap4j
{
@@ -26,7 +26,7 @@ class Crap4j
*/
public function __construct($threshold = 30)
{
if (!is_int($threshold)) {
if (!\is_int($threshold)) {
throw InvalidArgumentException::create(
1,
'integer'
@@ -51,9 +51,9 @@ class Crap4j
$root = $document->createElement('crap_result');
$document->appendChild($root);
$project = $document->createElement('project', is_string($name) ? $name : '');
$project = $document->createElement('project', \is_string($name) ? $name : '');
$root->appendChild($project);
$root->appendChild($document->createElement('timestamp', date('Y-m-d H:i:s', (int) $_SERVER['REQUEST_TIME'])));
$root->appendChild($document->createElement('timestamp', \date('Y-m-d H:i:s', (int) $_SERVER['REQUEST_TIME'])));
$stats = $document->createElement('stats');
$methodsNode = $document->createElement('methods');
@@ -82,7 +82,7 @@ class Crap4j
foreach ($class['methods'] as $methodName => $method) {
$crapLoad = $this->getCrapLoad($method['crap'], $method['ccn'], $method['coverage']);
$fullCrap += $method['crap'];
$fullCrap += $method['crap'];
$fullCrapLoad += $crapLoad;
$fullMethodCount++;
@@ -99,12 +99,12 @@ class Crap4j
$methodNode->appendChild($document->createElement('package', $namespace));
$methodNode->appendChild($document->createElement('className', $className));
$methodNode->appendChild($document->createElement('methodName', $methodName));
$methodNode->appendChild($document->createElement('methodSignature', htmlspecialchars($method['signature'])));
$methodNode->appendChild($document->createElement('fullMethod', htmlspecialchars($method['signature'])));
$methodNode->appendChild($document->createElement('methodSignature', \htmlspecialchars($method['signature'])));
$methodNode->appendChild($document->createElement('fullMethod', \htmlspecialchars($method['signature'])));
$methodNode->appendChild($document->createElement('crap', $this->roundValue($method['crap'])));
$methodNode->appendChild($document->createElement('complexity', $method['ccn']));
$methodNode->appendChild($document->createElement('coverage', $this->roundValue($method['coverage'])));
$methodNode->appendChild($document->createElement('crapLoad', round($crapLoad)));
$methodNode->appendChild($document->createElement('crapLoad', \round($crapLoad)));
$methodsNode->appendChild($methodNode);
}
@@ -114,7 +114,7 @@ class Crap4j
$stats->appendChild($document->createElement('name', 'Method Crap Stats'));
$stats->appendChild($document->createElement('methodCount', $fullMethodCount));
$stats->appendChild($document->createElement('crapMethodCount', $fullCrapMethodCount));
$stats->appendChild($document->createElement('crapLoad', round($fullCrapLoad)));
$stats->appendChild($document->createElement('crapLoad', \round($fullCrapLoad)));
$stats->appendChild($document->createElement('totalCrap', $fullCrap));
if ($fullMethodCount > 0) {
@@ -131,11 +131,11 @@ class Crap4j
$buffer = $document->saveXML();
if ($target !== null) {
if (!is_dir(dirname($target))) {
mkdir(dirname($target), 0777, true);
if (!\is_dir(\dirname($target))) {
\mkdir(\dirname($target), 0777, true);
}
file_put_contents($target, $buffer);
\file_put_contents($target, $buffer);
}
return $buffer;
@@ -167,6 +167,6 @@ class Crap4j
*/
private function roundValue($value)
{
return round($value, 2);
return \round($value, 2);
}
}

View File

@@ -65,10 +65,10 @@ class Facade
unset($coverage);
if (!isset($_SERVER['REQUEST_TIME'])) {
$_SERVER['REQUEST_TIME'] = time();
$_SERVER['REQUEST_TIME'] = \time();
}
$date = date('D M j G:i:s T Y', $_SERVER['REQUEST_TIME']);
$date = \date('D M j G:i:s T Y', $_SERVER['REQUEST_TIME']);
$dashboard = new Dashboard(
$this->templatePath,
@@ -101,17 +101,17 @@ class Facade
$id = $node->getId();
if ($node instanceof DirectoryNode) {
if (!file_exists($target . $id)) {
mkdir($target . $id, 0777, true);
if (!\file_exists($target . $id)) {
\mkdir($target . $id, 0777, true);
}
$directory->render($node, $target . $id . '/index.html');
$dashboard->render($node, $target . $id . '/dashboard.html');
} else {
$dir = dirname($target . $id);
$dir = \dirname($target . $id);
if (!file_exists($dir)) {
mkdir($dir, 0777, true);
if (!\file_exists($dir)) {
\mkdir($dir, 0777, true);
}
$file->render($node, $target . $id . '.html');
@@ -126,26 +126,37 @@ class Facade
*/
private function copyFiles($target)
{
$dir = $this->getDirectory($target . 'css');
copy($this->templatePath . 'css/bootstrap.min.css', $dir . 'bootstrap.min.css');
copy($this->templatePath . 'css/nv.d3.min.css', $dir . 'nv.d3.min.css');
copy($this->templatePath . 'css/style.css', $dir . 'style.css');
$dir = $this->getDirectory($target . '.css');
$dir = $this->getDirectory($target . 'fonts');
copy($this->templatePath . 'fonts/glyphicons-halflings-regular.eot', $dir . 'glyphicons-halflings-regular.eot');
copy($this->templatePath . 'fonts/glyphicons-halflings-regular.svg', $dir . 'glyphicons-halflings-regular.svg');
copy($this->templatePath . 'fonts/glyphicons-halflings-regular.ttf', $dir . 'glyphicons-halflings-regular.ttf');
copy($this->templatePath . 'fonts/glyphicons-halflings-regular.woff', $dir . 'glyphicons-halflings-regular.woff');
copy($this->templatePath . 'fonts/glyphicons-halflings-regular.woff2', $dir . 'glyphicons-halflings-regular.woff2');
\file_put_contents(
$dir . 'bootstrap.min.css',
\str_replace(
'url(../fonts/',
'url(../.fonts/',
\file_get_contents($this->templatePath . 'css/bootstrap.min.css')
)
$dir = $this->getDirectory($target . 'js');
copy($this->templatePath . 'js/bootstrap.min.js', $dir . 'bootstrap.min.js');
copy($this->templatePath . 'js/d3.min.js', $dir . 'd3.min.js');
copy($this->templatePath . 'js/holder.min.js', $dir . 'holder.min.js');
copy($this->templatePath . 'js/html5shiv.min.js', $dir . 'html5shiv.min.js');
copy($this->templatePath . 'js/jquery.min.js', $dir . 'jquery.min.js');
copy($this->templatePath . 'js/nv.d3.min.js', $dir . 'nv.d3.min.js');
copy($this->templatePath . 'js/respond.min.js', $dir . 'respond.min.js');
);
\copy($this->templatePath . 'css/nv.d3.min.css', $dir . 'nv.d3.min.css');
\copy($this->templatePath . 'css/style.css', $dir . 'style.css');
$dir = $this->getDirectory($target . '.fonts');
\copy($this->templatePath . 'fonts/glyphicons-halflings-regular.eot', $dir . 'glyphicons-halflings-regular.eot');
\copy($this->templatePath . 'fonts/glyphicons-halflings-regular.svg', $dir . 'glyphicons-halflings-regular.svg');
\copy($this->templatePath . 'fonts/glyphicons-halflings-regular.ttf', $dir . 'glyphicons-halflings-regular.ttf');
\copy($this->templatePath . 'fonts/glyphicons-halflings-regular.woff', $dir . 'glyphicons-halflings-regular.woff');
\copy($this->templatePath . 'fonts/glyphicons-halflings-regular.woff2', $dir . 'glyphicons-halflings-regular.woff2');
$dir = $this->getDirectory($target . '.js');
\copy($this->templatePath . 'js/bootstrap.min.js', $dir . 'bootstrap.min.js');
\copy($this->templatePath . 'js/d3.min.js', $dir . 'd3.min.js');
\copy($this->templatePath . 'js/holder.min.js', $dir . 'holder.min.js');
\copy($this->templatePath . 'js/html5shiv.min.js', $dir . 'html5shiv.min.js');
\copy($this->templatePath . 'js/jquery.min.js', $dir . 'jquery.min.js');
\copy($this->templatePath . 'js/nv.d3.min.js', $dir . 'nv.d3.min.js');
\copy($this->templatePath . 'js/respond.min.js', $dir . 'respond.min.js');
\copy($this->templatePath . 'js/file.js', $dir . 'file.js');
}
/**
@@ -157,20 +168,20 @@ class Facade
*/
private function getDirectory($directory)
{
if (substr($directory, -1, 1) != DIRECTORY_SEPARATOR) {
if (\substr($directory, -1, 1) != DIRECTORY_SEPARATOR) {
$directory .= DIRECTORY_SEPARATOR;
}
if (is_dir($directory)) {
if (\is_dir($directory)) {
return $directory;
}
if (@mkdir($directory, 0777, true)) {
if (@\mkdir($directory, 0777, true)) {
return $directory;
}
throw new RuntimeException(
sprintf(
\sprintf(
'Directory "%s" does not exist.',
$directory
)

View File

@@ -11,10 +11,10 @@
namespace SebastianBergmann\CodeCoverage\Report\Html;
use SebastianBergmann\CodeCoverage\Node\AbstractNode;
use SebastianBergmann\CodeCoverage\Node\File as FileNode;
use SebastianBergmann\CodeCoverage\Node\Directory as DirectoryNode;
use SebastianBergmann\CodeCoverage\Node\File as FileNode;
use SebastianBergmann\CodeCoverage\Version;
use SebastianBergmann\Environment\Runtime;
use SebastianBergmann\Version;
/**
* Base class for node renderers.
@@ -62,14 +62,12 @@ abstract class Renderer
*/
public function __construct($templatePath, $generator, $date, $lowUpperBound, $highLowerBound)
{
$version = new Version('4.0.2', dirname(dirname(dirname(dirname(__DIR__)))));
$this->templatePath = $templatePath;
$this->generator = $generator;
$this->date = $date;
$this->lowUpperBound = $lowUpperBound;
$this->highLowerBound = $highLowerBound;
$this->version = $version->getVersion();
$this->version = Version::id();
}
/**
@@ -92,9 +90,10 @@ abstract class Renderer
$data['testedClassesPercent']
);
} else {
$classesLevel = 'success';
$classesNumber = '0' . $numSeparator . '0';
$classesBar = $this->getCoverageBar(100);
$classesLevel = '';
$classesNumber = '0' . $numSeparator . '0';
$classesBar = '';
$data['testedClassesPercentAsString'] = 'n/a';
}
if ($data['numMethods'] > 0) {
@@ -107,10 +106,10 @@ abstract class Renderer
$data['testedMethodsPercent']
);
} else {
$methodsLevel = 'success';
$methodsLevel = '';
$methodsNumber = '0' . $numSeparator . '0';
$methodsBar = $this->getCoverageBar(100);
$data['testedMethodsPercentAsString'] = '100.00%';
$methodsBar = '';
$data['testedMethodsPercentAsString'] = 'n/a';
}
if ($data['numExecutableLines'] > 0) {
@@ -123,10 +122,10 @@ abstract class Renderer
$data['linesExecutedPercent']
);
} else {
$linesLevel = 'success';
$linesLevel = '';
$linesNumber = '0' . $numSeparator . '0';
$linesBar = $this->getCoverageBar(100);
$data['linesExecutedPercentAsString'] = '100.00%';
$linesBar = '';
$data['linesExecutedPercentAsString'] = 'n/a';
}
$template->setVar(
@@ -179,21 +178,21 @@ abstract class Renderer
$breadcrumbs = '';
$path = $node->getPathAsArray();
$pathToRoot = [];
$max = count($path);
$max = \count($path);
if ($node instanceof FileNode) {
$max--;
}
for ($i = 0; $i < $max; $i++) {
$pathToRoot[] = str_repeat('../', $i);
$pathToRoot[] = \str_repeat('../', $i);
}
foreach ($path as $step) {
if ($step !== $node) {
$breadcrumbs .= $this->getInactiveBreadcrumb(
$step,
array_pop($pathToRoot)
\array_pop($pathToRoot)
);
} else {
$breadcrumbs .= $this->getActiveBreadcrumb($step);
@@ -205,7 +204,7 @@ abstract class Renderer
protected function getActiveBreadcrumb(AbstractNode $node)
{
$buffer = sprintf(
$buffer = \sprintf(
' <li class="active">%s</li>' . "\n",
$node->getName()
);
@@ -219,7 +218,7 @@ abstract class Renderer
protected function getInactiveBreadcrumb(AbstractNode $node, $pathToRoot)
{
return sprintf(
return \sprintf(
' <li><a href="%sindex.html">%s</a></li>' . "\n",
$pathToRoot,
$node->getName()
@@ -229,14 +228,14 @@ abstract class Renderer
protected function getPathToRoot(AbstractNode $node)
{
$id = $node->getId();
$depth = substr_count($id, '/');
$depth = \substr_count($id, '/');
if ($id != 'index' &&
$node instanceof DirectoryNode) {
$depth++;
}
return str_repeat('../', $depth);
return \str_repeat('../', $depth);
}
protected function getCoverageBar($percent)
@@ -249,7 +248,7 @@ abstract class Renderer
'}}'
);
$template->setVar(['level' => $level, 'percent' => sprintf('%.2F', $percent)]);
$template->setVar(['level' => $level, 'percent' => \sprintf('%.2F', $percent)]);
return $template->render();
}
@@ -264,7 +263,7 @@ abstract class Renderer
if ($percent <= $this->lowUpperBound) {
return 'danger';
} elseif ($percent > $this->lowUpperBound &&
$percent < $this->highLowerBound) {
$percent < $this->highLowerBound) {
return 'warning';
} else {
return 'success';
@@ -278,7 +277,7 @@ abstract class Renderer
{
$runtime = new Runtime;
$buffer = sprintf(
$buffer = \sprintf(
'<a href="%s" target="_top">%s %s</a>',
$runtime->getVendorUrl(),
$runtime->getName(),
@@ -286,9 +285,9 @@ abstract class Renderer
);
if ($runtime->hasXdebug() && !$runtime->hasPHPDBGCodeCoverage()) {
$buffer .= sprintf(
$buffer .= \sprintf(
' with <a href="https://xdebug.org/">Xdebug %s</a>',
phpversion('xdebug')
\phpversion('xdebug')
);
}

View File

@@ -21,6 +21,8 @@ class Dashboard extends Renderer
/**
* @param DirectoryNode $node
* @param string $file
*
* @throws \InvalidArgumentException
*/
public function render(DirectoryNode $node, $file)
{
@@ -69,16 +71,16 @@ class Dashboard extends Renderer
foreach ($classes as $className => $class) {
foreach ($class['methods'] as $methodName => $method) {
if ($className != '*') {
if ($className !== '*') {
$methodName = $className . '::' . $methodName;
}
$result['method'][] = [
$method['coverage'],
$method['ccn'],
sprintf(
\sprintf(
'<a href="%s">%s</a>',
str_replace($baseLink, '', $method['link']),
\str_replace($baseLink, '', $method['link']),
$methodName
)
];
@@ -87,17 +89,17 @@ class Dashboard extends Renderer
$result['class'][] = [
$class['coverage'],
$class['ccn'],
sprintf(
\sprintf(
'<a href="%s">%s</a>',
str_replace($baseLink, '', $class['link']),
\str_replace($baseLink, '', $class['link']),
$className
)
];
}
return [
'class' => json_encode($result['class']),
'method' => json_encode($result['method'])
'class' => \json_encode($result['class']),
'method' => \json_encode($result['method'])
];
}
@@ -143,31 +145,31 @@ class Dashboard extends Renderer
foreach ($classes as $class) {
foreach ($class['methods'] as $methodName => $method) {
if ($method['coverage'] == 0) {
if ($method['coverage'] === 0) {
$result['method']['0%']++;
} elseif ($method['coverage'] == 100) {
} elseif ($method['coverage'] === 100) {
$result['method']['100%']++;
} else {
$key = floor($method['coverage'] / 10) * 10;
$key = \floor($method['coverage'] / 10) * 10;
$key = $key . '-' . ($key + 10) . '%';
$result['method'][$key]++;
}
}
if ($class['coverage'] == 0) {
if ($class['coverage'] === 0) {
$result['class']['0%']++;
} elseif ($class['coverage'] == 100) {
} elseif ($class['coverage'] === 100) {
$result['class']['100%']++;
} else {
$key = floor($class['coverage'] / 10) * 10;
$key = \floor($class['coverage'] / 10) * 10;
$key = $key . '-' . ($key + 10) . '%';
$result['class'][$key]++;
}
}
return [
'class' => json_encode(array_values($result['class'])),
'method' => json_encode(array_values($result['method']))
'class' => \json_encode(\array_values($result['class'])),
'method' => \json_encode(\array_values($result['method']))
];
}
@@ -188,10 +190,10 @@ class Dashboard extends Renderer
foreach ($classes as $className => $class) {
foreach ($class['methods'] as $methodName => $method) {
if ($method['coverage'] < $this->highLowerBound) {
if ($className != '*') {
$key = $methodName;
if ($className !== '*') {
$key = $className . '::' . $methodName;
} else {
$key = $methodName;
}
$leastTestedMethods[$key] = $method['coverage'];
@@ -203,24 +205,24 @@ class Dashboard extends Renderer
}
}
asort($leastTestedClasses);
asort($leastTestedMethods);
\asort($leastTestedClasses);
\asort($leastTestedMethods);
foreach ($leastTestedClasses as $className => $coverage) {
$result['class'] .= sprintf(
$result['class'] .= \sprintf(
' <tr><td><a href="%s">%s</a></td><td class="text-right">%d%%</td></tr>' . "\n",
str_replace($baseLink, '', $classes[$className]['link']),
\str_replace($baseLink, '', $classes[$className]['link']),
$className,
$coverage
);
}
foreach ($leastTestedMethods as $methodName => $coverage) {
list($class, $method) = explode('::', $methodName);
list($class, $method) = \explode('::', $methodName);
$result['method'] .= sprintf(
$result['method'] .= \sprintf(
' <tr><td><a href="%s"><abbr title="%s">%s</abbr></a></td><td class="text-right">%d%%</td></tr>' . "\n",
str_replace($baseLink, '', $classes[$class]['methods'][$method]['link']),
\str_replace($baseLink, '', $classes[$class]['methods'][$method]['link']),
$methodName,
$method,
$coverage
@@ -248,7 +250,7 @@ class Dashboard extends Renderer
foreach ($class['methods'] as $methodName => $method) {
if ($method['coverage'] < $this->highLowerBound &&
$method['ccn'] > 1) {
if ($className != '*') {
if ($className !== '*') {
$key = $className . '::' . $methodName;
} else {
$key = $methodName;
@@ -259,29 +261,29 @@ class Dashboard extends Renderer
}
if ($class['coverage'] < $this->highLowerBound &&
$class['ccn'] > count($class['methods'])) {
$class['ccn'] > \count($class['methods'])) {
$classRisks[$className] = $class['crap'];
}
}
arsort($classRisks);
arsort($methodRisks);
\arsort($classRisks);
\arsort($methodRisks);
foreach ($classRisks as $className => $crap) {
$result['class'] .= sprintf(
$result['class'] .= \sprintf(
' <tr><td><a href="%s">%s</a></td><td class="text-right">%d</td></tr>' . "\n",
str_replace($baseLink, '', $classes[$className]['link']),
\str_replace($baseLink, '', $classes[$className]['link']),
$className,
$crap
);
}
foreach ($methodRisks as $methodName => $crap) {
list($class, $method) = explode('::', $methodName);
list($class, $method) = \explode('::', $methodName);
$result['method'] .= sprintf(
$result['method'] .= \sprintf(
' <tr><td><a href="%s"><abbr title="%s">%s</abbr></a></td><td class="text-right">%d</td></tr>' . "\n",
str_replace($baseLink, '', $classes[$class]['methods'][$method]['link']),
\str_replace($baseLink, '', $classes[$class]['methods'][$method]['link']),
$methodName,
$method,
$crap
@@ -293,7 +295,7 @@ class Dashboard extends Renderer
protected function getActiveBreadcrumb(AbstractNode $node)
{
return sprintf(
return \sprintf(
' <li><a href="index.html">%s</a></li>' . "\n" .
' <li class="active">(Dashboard)</li>' . "\n",
$node->getName()

View File

@@ -59,14 +59,14 @@ class Directory extends Renderer
$data = [
'numClasses' => $node->getNumClassesAndTraits(),
'numTestedClasses' => $node->getNumTestedClassesAndTraits(),
'numMethods' => $node->getNumMethods(),
'numTestedMethods' => $node->getNumTestedMethods(),
'numMethods' => $node->getNumFunctionsAndMethods(),
'numTestedMethods' => $node->getNumTestedFunctionsAndMethods(),
'linesExecutedPercent' => $node->getLineExecutedPercent(false),
'linesExecutedPercentAsString' => $node->getLineExecutedPercent(),
'numExecutedLines' => $node->getNumExecutedLines(),
'numExecutableLines' => $node->getNumExecutableLines(),
'testedMethodsPercent' => $node->getTestedMethodsPercent(false),
'testedMethodsPercentAsString' => $node->getTestedMethodsPercent(),
'testedMethodsPercent' => $node->getTestedFunctionsAndMethodsPercent(false),
'testedMethodsPercentAsString' => $node->getTestedFunctionsAndMethodsPercent(),
'testedClassesPercent' => $node->getTestedClassesAndTraitsPercent(false),
'testedClassesPercentAsString' => $node->getTestedClassesAndTraitsPercent()
];
@@ -75,7 +75,7 @@ class Directory extends Renderer
$data['name'] = 'Total';
} else {
if ($node instanceof DirectoryNode) {
$data['name'] = sprintf(
$data['name'] = \sprintf(
'<a href="%s/index.html">%s</a>',
$node->getName(),
$node->getName()
@@ -83,7 +83,7 @@ class Directory extends Renderer
$data['icon'] = '<span class="glyphicon glyphicon-folder-open"></span> ';
} else {
$data['name'] = sprintf(
$data['name'] = \sprintf(
'<a href="%s.html">%s</a>',
$node->getName(),
$node->getName()

View File

@@ -88,14 +88,14 @@ class File extends Renderer
'name' => 'Total',
'numClasses' => $node->getNumClassesAndTraits(),
'numTestedClasses' => $node->getNumTestedClassesAndTraits(),
'numMethods' => $node->getNumMethods(),
'numTestedMethods' => $node->getNumTestedMethods(),
'numMethods' => $node->getNumFunctionsAndMethods(),
'numTestedMethods' => $node->getNumTestedFunctionsAndMethods(),
'linesExecutedPercent' => $node->getLineExecutedPercent(false),
'linesExecutedPercentAsString' => $node->getLineExecutedPercent(),
'numExecutedLines' => $node->getNumExecutedLines(),
'numExecutableLines' => $node->getNumExecutableLines(),
'testedMethodsPercent' => $node->getTestedMethodsPercent(false),
'testedMethodsPercentAsString' => $node->getTestedMethodsPercent(),
'testedMethodsPercent' => $node->getTestedFunctionsAndMethodsPercent(false),
'testedMethodsPercentAsString' => $node->getTestedFunctionsAndMethodsPercent(),
'testedClassesPercent' => $node->getTestedClassesAndTraitsPercent(false),
'testedClassesPercentAsString' => $node->getTestedClassesAndTraitsPercent(),
'crap' => '<abbr title="Change Risk Anti-Patterns (CRAP) Index">CRAP</abbr>'
@@ -138,7 +138,7 @@ class File extends Renderer
$buffer = '';
foreach ($items as $name => $item) {
$numMethods = count($item['methods']);
$numMethods = \count($item['methods']);
$numTestedMethods = 0;
foreach ($item['methods'] as $method) {
@@ -147,12 +147,26 @@ class File extends Renderer
}
}
if ($item['executableLines'] > 0) {
$numClasses = 1;
$numTestedClasses = $numTestedMethods == $numMethods ? 1 : 0;
$linesExecutedPercentAsString = Util::percent(
$item['executedLines'],
$item['executableLines'],
true
);
} else {
$numClasses = 'n/a';
$numTestedClasses = 'n/a';
$linesExecutedPercentAsString = 'n/a';
}
$buffer .= $this->renderItemTemplate(
$template,
[
'name' => $name,
'numClasses' => 1,
'numTestedClasses' => $numTestedMethods == $numMethods ? 1 : 0,
'numClasses' => $numClasses,
'numTestedClasses' => $numTestedClasses,
'numMethods' => $numMethods,
'numTestedMethods' => $numTestedMethods,
'linesExecutedPercent' => Util::percent(
@@ -160,11 +174,7 @@ class File extends Renderer
$item['executableLines'],
false
),
'linesExecutedPercentAsString' => Util::percent(
$item['executedLines'],
$item['executableLines'],
true
),
'linesExecutedPercentAsString' => $linesExecutedPercentAsString,
'numExecutedLines' => $item['executedLines'],
'numExecutableLines' => $item['executableLines'],
'testedMethodsPercent' => Util::percent(
@@ -239,11 +249,11 @@ class File extends Renderer
return $this->renderItemTemplate(
$template,
[
'name' => sprintf(
'name' => \sprintf(
'%s<a href="#%d"><abbr title="%s">%s</abbr></a>',
$indent,
$item['startLine'],
htmlspecialchars($item['signature']),
\htmlspecialchars($item['signature']),
isset($item['functionName']) ? $item['functionName'] : $item['methodName']
),
'numMethods' => 1,
@@ -293,8 +303,8 @@ class File extends Renderer
$popoverContent = '';
$popoverTitle = '';
if (array_key_exists($i, $coverageData)) {
$numTests = count($coverageData[$i]);
if (\array_key_exists($i, $coverageData)) {
$numTests = ($coverageData[$i] ? \count($coverageData[$i]) : 0);
if ($coverageData[$i] === null) {
$trClass = ' class="warning"';
@@ -322,39 +332,46 @@ class File extends Renderer
switch ($testData[$test]['size']) {
case 'small':
$testCSS = ' class="covered-by-small-tests"';
break;
case 'medium':
$testCSS = ' class="covered-by-medium-tests"';
break;
default:
$testCSS = ' class="covered-by-large-tests"';
break;
}
break;
case 1:
case 2:
$testCSS = ' class="warning"';
break;
case 3:
$testCSS = ' class="danger"';
break;
case 4:
$testCSS = ' class="danger"';
break;
default:
$testCSS = '';
}
$popoverContent .= sprintf(
$popoverContent .= \sprintf(
'<li%s>%s</li>',
$testCSS,
htmlspecialchars($test)
\htmlspecialchars($test)
);
}
@@ -364,16 +381,16 @@ class File extends Renderer
}
if (!empty($popoverTitle)) {
$popover = sprintf(
$popover = \sprintf(
' data-title="%s" data-content="%s" data-placement="bottom" data-html="true"',
$popoverTitle,
htmlspecialchars($popoverContent)
\htmlspecialchars($popoverContent)
);
} else {
$popover = '';
}
$lines .= sprintf(
$lines .= \sprintf(
' <tr%s%s><td><div align="right"><a name="%d"></a><a href="#%d">%d</a></div></td><td class="codeLine">%s</td></tr>' . "\n",
$trClass,
$popover,
@@ -396,28 +413,28 @@ class File extends Renderer
*/
protected function loadFile($file)
{
$buffer = file_get_contents($file);
$tokens = token_get_all($buffer);
$buffer = \file_get_contents($file);
$tokens = \token_get_all($buffer);
$result = [''];
$i = 0;
$stringFlag = false;
$fileEndsWithNewLine = substr($buffer, -1) == "\n";
$fileEndsWithNewLine = \substr($buffer, -1) == "\n";
unset($buffer);
foreach ($tokens as $j => $token) {
if (is_string($token)) {
if (\is_string($token)) {
if ($token === '"' && $tokens[$j - 1] !== '\\') {
$result[$i] .= sprintf(
$result[$i] .= \sprintf(
'<span class="string">%s</span>',
htmlspecialchars($token)
\htmlspecialchars($token)
);
$stringFlag = !$stringFlag;
} else {
$result[$i] .= sprintf(
$result[$i] .= \sprintf(
'<span class="keyword">%s</span>',
htmlspecialchars($token)
\htmlspecialchars($token)
);
}
@@ -426,19 +443,19 @@ class File extends Renderer
list($token, $value) = $token;
$value = str_replace(
$value = \str_replace(
["\t", ' '],
['&nbsp;&nbsp;&nbsp;&nbsp;', '&nbsp;'],
htmlspecialchars($value, $this->htmlspecialcharsFlags)
\htmlspecialchars($value, $this->htmlspecialcharsFlags)
);
if ($value === "\n") {
$result[++$i] = '';
} else {
$lines = explode("\n", $value);
$lines = \explode("\n", $value);
foreach ($lines as $jj => $line) {
$line = trim($line);
$line = \trim($line);
if ($line !== '') {
if ($stringFlag) {
@@ -447,11 +464,13 @@ class File extends Renderer
switch ($token) {
case T_INLINE_HTML:
$colour = 'html';
break;
case T_COMMENT:
case T_DOC_COMMENT:
$colour = 'comment';
break;
case T_ABSTRACT:
@@ -511,6 +530,7 @@ class File extends Renderer
case T_WHILE:
case T_YIELD:
$colour = 'keyword';
break;
default:
@@ -518,7 +538,7 @@ class File extends Renderer
}
}
$result[$i] .= sprintf(
$result[$i] .= \sprintf(
'<span class="%s">%s</span>',
$colour,
$line
@@ -533,7 +553,7 @@ class File extends Renderer
}
if ($fileEndsWithNewLine) {
unset($result[count($result)-1]);
unset($result[\count($result) - 1]);
}
return $result;

File diff suppressed because one or more lines are too long

View File

@@ -4,12 +4,12 @@
<meta charset="UTF-8">
<title>Dashboard for {{full_path}}</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="{{path_to_root}}css/bootstrap.min.css" rel="stylesheet">
<link href="{{path_to_root}}css/nv.d3.min.css" rel="stylesheet">
<link href="{{path_to_root}}css/style.css" rel="stylesheet">
<link href="{{path_to_root}}.css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href="{{path_to_root}}.css/nv.d3.min.css" rel="stylesheet" type="text/css">
<link href="{{path_to_root}}.css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="{{path_to_root}}js/html5shiv.min.js"></script>
<script src="{{path_to_root}}js/respond.min.js"></script>
<script src="{{path_to_root}}.js/html5shiv.min.js"></script>
<script src="{{path_to_root}}.js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -138,11 +138,11 @@
</p>
</footer>
</div>
<script src="{{path_to_root}}js/jquery.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}js/bootstrap.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}js/holder.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}js/d3.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}js/nv.d3.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/jquery.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/bootstrap.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/holder.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/d3.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/nv.d3.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function() {
nv.addGraph(function() {

View File

@@ -4,11 +4,11 @@
<meta charset="UTF-8">
<title>Code Coverage for {{full_path}}</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="{{path_to_root}}css/bootstrap.min.css" rel="stylesheet">
<link href="{{path_to_root}}css/style.css" rel="stylesheet">
<link href="{{path_to_root}}.css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href="{{path_to_root}}.css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="{{path_to_root}}js/html5shiv.min.js"></script>
<script src="{{path_to_root}}js/respond.min.js"></script>
<script src="{{path_to_root}}.js/html5shiv.min.js"></script>
<script src="{{path_to_root}}.js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -54,8 +54,8 @@
</p>
</footer>
</div>
<script src="{{path_to_root}}js/jquery.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}js/bootstrap.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}js/holder.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/jquery.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/bootstrap.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/holder.min.js" type="text/javascript"></script>
</body>
</html>

View File

@@ -4,11 +4,11 @@
<meta charset="UTF-8">
<title>Code Coverage for {{full_path}}</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="{{path_to_root}}css/bootstrap.min.css" rel="stylesheet">
<link href="{{path_to_root}}css/style.css" rel="stylesheet">
<link href="{{path_to_root}}.css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href="{{path_to_root}}.css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="{{path_to_root}}js/html5shiv.min.js"></script>
<script src="{{path_to_root}}js/respond.min.js"></script>
<script src="{{path_to_root}}.js/html5shiv.min.js"></script>
<script src="{{path_to_root}}.js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -60,31 +60,9 @@
<a title="Back to the top" id="toplink" href="#"><span class="glyphicon glyphicon-arrow-up"></span></a>
</footer>
</div>
<script src="{{path_to_root}}js/jquery.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}js/bootstrap.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}js/holder.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(function() {
var $window = $(window)
, $top_link = $('#toplink')
, $body = $('body, html')
, offset = $('#code').offset().top;
$top_link.hide().click(function(event) {
event.preventDefault();
$body.animate({scrollTop:0}, 800);
});
$window.scroll(function() {
if($window.scrollTop() > offset) {
$top_link.fadeIn();
} else {
$top_link.fadeOut();
}
}).scroll();
$('.popin').popover({trigger: 'hover'});
});
</script>
<script src="{{path_to_root}}.js/jquery.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/bootstrap.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/holder.min.js" type="text/javascript"></script>
<script src="{{path_to_root}}.js/file.js" type="text/javascript"></script>
</body>
</html>

File diff suppressed because one or more lines are too long

View File

@@ -0,0 +1,61 @@
$(function() {
var $window = $(window)
, $top_link = $('#toplink')
, $body = $('body, html')
, offset = $('#code').offset().top
, hidePopover = function ($target) {
$target.data('popover-hover', false);
setTimeout(function () {
if (!$target.data('popover-hover')) {
$target.popover('hide');
}
}, 300);
};
$top_link.hide().click(function(event) {
event.preventDefault();
$body.animate({scrollTop:0}, 800);
});
$window.scroll(function() {
if($window.scrollTop() > offset) {
$top_link.fadeIn();
} else {
$top_link.fadeOut();
}
}).scroll();
$('.popin')
.popover({trigger: 'manual'})
.on({
'mouseenter.popover': function () {
var $target = $(this);
$target.data('popover-hover', true);
// popover already displayed
if ($target.next('.popover').length) {
return;
}
// show the popover
$target.popover('show');
// register mouse events on the popover
$target.next('.popover:not(.popover-initialized)')
.on({
'mouseenter': function () {
$target.data('popover-hover', true);
},
'mouseleave': function () {
hidePopover($target);
}
})
.addClass('popover-initialized');
},
'mouseleave.popover': function () {
hidePopover($(this));
}
});
});

File diff suppressed because one or more lines are too long

View File

@@ -27,7 +27,7 @@ class PHP
{
$filter = $coverage->filter();
$output = sprintf(
$output = \sprintf(
'<?php
$coverage = new SebastianBergmann\CodeCoverage\CodeCoverage;
$coverage->setData(%s);
@@ -37,13 +37,13 @@ $filter = $coverage->filter();
$filter->setWhitelistedFiles(%s);
return $coverage;',
var_export($coverage->getData(true), 1),
var_export($coverage->getTests(), 1),
var_export($filter->getWhitelistedFiles(), 1)
\var_export($coverage->getData(true), 1),
\var_export($coverage->getTests(), 1),
\var_export($filter->getWhitelistedFiles(), 1)
);
if ($target !== null) {
return file_put_contents($target, $output);
return \file_put_contents($target, $output);
} else {
return $output;
}

View File

@@ -88,7 +88,7 @@ class Text
$colors['eol'] = $this->colors['eol'];
}
$classes = sprintf(
$classes = \sprintf(
' Classes: %6s (%d/%d)',
Util::percent(
$report->getNumTestedClassesAndTraits(),
@@ -99,7 +99,7 @@ class Text
$report->getNumClassesAndTraits()
);
$methods = sprintf(
$methods = \sprintf(
' Methods: %6s (%d/%d)',
Util::percent(
$report->getNumTestedMethods(),
@@ -110,7 +110,7 @@ class Text
$report->getNumMethods()
);
$lines = sprintf(
$lines = \sprintf(
' Lines: %6s (%d/%d)',
Util::percent(
$report->getNumExecutedLines(),
@@ -121,15 +121,15 @@ class Text
$report->getNumExecutableLines()
);
$padding = max(array_map('strlen', [$classes, $methods, $lines]));
$padding = \max(\array_map('strlen', [$classes, $methods, $lines]));
if ($this->showOnlySummary) {
$title = 'Code Coverage Report Summary:';
$padding = max($padding, strlen($title));
$padding = \max($padding, \strlen($title));
$output .= $this->format($colors['header'], $padding, $title);
} else {
$date = date(' Y-m-d H:i:s', $_SERVER['REQUEST_TIME']);
$date = \date(' Y-m-d H:i:s', $_SERVER['REQUEST_TIME']);
$title = 'Code Coverage Report:';
$output .= $this->format($colors['header'], $padding, $title);
@@ -167,7 +167,7 @@ class Text
}
$classMethods++;
$classStatements += $method['executableLines'];
$classStatements += $method['executableLines'];
$coveredClassStatements += $method['executedLines'];
if ($method['coverage'] == 100) {
$coveredMethods++;
@@ -193,7 +193,7 @@ class Text
}
}
ksort($classCoverage);
\ksort($classCoverage);
$methodColor = '';
$linesColor = '';
@@ -244,14 +244,14 @@ class Text
true,
true
) .
' (' . sprintf($format, $numberOfCoveredElements) . '/' .
sprintf($format, $totalNumberOfElements) . ')';
' (' . \sprintf($format, $numberOfCoveredElements) . '/' .
\sprintf($format, $totalNumberOfElements) . ')';
}
private function format($color, $padding, $string)
{
$reset = $color ? $this->colors['reset'] : '';
return $color . str_pad($string, $padding) . $reset . PHP_EOL;
return $color . \str_pad($string, $padding) . $reset . PHP_EOL;
}
}

View File

@@ -0,0 +1,101 @@
<?php
/*
* This file is part of the php-code-coverage package.
*
* (c) Sebastian Bergmann <sebastian@phpunit.de>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace SebastianBergmann\CodeCoverage\Report\Xml;
use SebastianBergmann\Environment\Runtime;
class BuildInformation
{
/**
* @var \DOMElement
*/
private $contextNode;
/**
* @param \DOMElement $contextNode
*/
public function __construct(\DOMElement $contextNode)
{
$this->contextNode = $contextNode;
}
/**
* @param Runtime $runtime
*/
public function setRuntimeInformation(Runtime $runtime)
{
$runtimeNode = $this->getNodeByName('runtime');
$runtimeNode->setAttribute('name', $runtime->getName());
$runtimeNode->setAttribute('version', $runtime->getVersion());
$runtimeNode->setAttribute('url', $runtime->getVendorUrl());
$driverNode = $this->getNodeByName('driver');
if ($runtime->isHHVM()) {
$driverNode->setAttribute('name', 'hhvm');
$driverNode->setAttribute('version', \constant('HHVM_VERSION'));
return;
}
if ($runtime->hasPHPDBGCodeCoverage()) {
$driverNode->setAttribute('name', 'phpdbg');
$driverNode->setAttribute('version', \constant('PHPDBG_VERSION'));
}
if ($runtime->hasXdebug()) {
$driverNode->setAttribute('name', 'xdebug');
$driverNode->setAttribute('version', \phpversion('xdebug'));
}
}
/**
* @param $name
*
* @return \DOMElement
*/
private function getNodeByName($name)
{
$node = $this->contextNode->getElementsByTagNameNS(
'http://schema.phpunit.de/coverage/1.0',
$name
)->item(0);
if (!$node) {
$node = $this->contextNode->appendChild(
$this->contextNode->ownerDocument->createElementNS(
'http://schema.phpunit.de/coverage/1.0',
$name
)
);
}
return $node;
}
/**
* @param \DateTime $date
*/
public function setBuildTime(\DateTime $date)
{
$this->contextNode->setAttribute('time', $date->format('D M j G:i:s T Y'));
}
/**
* @param string $phpUnitVersion
* @param string $coverageVersion
*/
public function setGeneratorVersions($phpUnitVersion, $coverageVersion)
{
$this->contextNode->setAttribute('phpunit', $phpUnitVersion);
$this->contextNode->setAttribute('coverage', $coverageVersion);
}
}

View File

@@ -33,7 +33,7 @@ class Coverage
{
$this->contextNode = $context;
$this->writer = new \XMLWriter;
$this->writer = new \XMLWriter();
$this->writer->openMemory();
$this->writer->startElementNs(null, $context->nodeName, 'http://schema.phpunit.de/coverage/1.0');
$this->writer->writeAttribute('nr', $line);

View File

@@ -15,6 +15,8 @@ use SebastianBergmann\CodeCoverage\Node\AbstractNode;
use SebastianBergmann\CodeCoverage\Node\Directory as DirectoryNode;
use SebastianBergmann\CodeCoverage\Node\File as FileNode;
use SebastianBergmann\CodeCoverage\RuntimeException;
use SebastianBergmann\CodeCoverage\Version;
use SebastianBergmann\Environment\Runtime;
class Facade
{
@@ -28,6 +30,19 @@ class Facade
*/
private $project;
/**
* @var string
*/
private $phpUnitVersion;
/**
* @param string $version
*/
public function __construct($version)
{
$this->phpUnitVersion = $version;
}
/**
* @param CodeCoverage $coverage
* @param string $target
@@ -36,7 +51,7 @@ class Facade
*/
public function process(CodeCoverage $coverage, $target)
{
if (substr($target, -1, 1) != DIRECTORY_SEPARATOR) {
if (\substr($target, -1, 1) != DIRECTORY_SEPARATOR) {
$target .= DIRECTORY_SEPARATOR;
}
@@ -49,33 +64,39 @@ class Facade
$coverage->getReport()->getName()
);
$this->setBuildInformation();
$this->processTests($coverage->getTests());
$this->processDirectory($report, $this->project);
$index = $this->project->asDom();
$index->formatOutput = true;
$index->preserveWhiteSpace = false;
$index->save($target . '/index.xml');
$this->saveDocument($this->project->asDom(), 'index');
}
private function setBuildInformation()
{
$buildNode = $this->project->getBuildInformation();
$buildNode->setRuntimeInformation(new Runtime());
$buildNode->setBuildTime(\DateTime::createFromFormat('U', $_SERVER['REQUEST_TIME']));
$buildNode->setGeneratorVersions($this->phpUnitVersion, Version::id());
}
/**
* @param string $directory
*/
private function initTargetDirectory($directory)
protected function initTargetDirectory($directory)
{
if (file_exists($directory)) {
if (!is_dir($directory)) {
if (\file_exists($directory)) {
if (!\is_dir($directory)) {
throw new RuntimeException(
"'$directory' exists but is not a directory."
);
}
if (!is_writable($directory)) {
if (!\is_writable($directory)) {
throw new RuntimeException(
"'$directory' exists but is not writable."
);
}
} elseif (!@mkdir($directory, 0777, true)) {
} elseif (!@\mkdir($directory, 0777, true)) {
throw new RuntimeException(
"'$directory' could not be created."
);
@@ -84,24 +105,20 @@ class Facade
private function processDirectory(DirectoryNode $directory, Node $context)
{
$dirObject = $context->addDirectory($directory->getName());
$dirname = $directory->getName();
if ($this->project->getProjectSourceDirectory() === $dirname) {
$dirname = '/';
}
$dirObject = $context->addDirectory($dirname);
$this->setTotals($directory, $dirObject->getTotals());
foreach ($directory as $node) {
if ($node instanceof DirectoryNode) {
$this->processDirectory($node, $dirObject);
continue;
}
foreach ($directory->getDirectories() as $node) {
$this->processDirectory($node, $dirObject);
}
if ($node instanceof FileNode) {
$this->processFile($node, $dirObject);
continue;
}
throw new RuntimeException(
'Unknown node type for XML report'
);
foreach ($directory->getFiles() as $node) {
$this->processFile($node, $dirObject);
}
}
@@ -114,7 +131,11 @@ class Facade
$this->setTotals($file, $fileObject->getTotals());
$fileReport = new Report($file->getName());
$path = \substr(
$file->getPath(),
\strlen($this->project->getProjectSourceDirectory())
);
$fileReport = new Report($path);
$this->setTotals($file, $fileReport->getTotals());
@@ -127,7 +148,7 @@ class Facade
}
foreach ($file->getCoverageData() as $line => $tests) {
if (!is_array($tests) || count($tests) == 0) {
if (!\is_array($tests) || \count($tests) === 0) {
continue;
}
@@ -140,14 +161,11 @@ class Facade
$coverage->finalize();
}
$this->initTargetDirectory(
$this->target . dirname($file->getId()) . '/'
$fileReport->getSource()->setSourceCode(
\file_get_contents($file->getPath())
);
$fileDom = $fileReport->asDom();
$fileDom->formatOutput = true;
$fileDom->preserveWhiteSpace = false;
$fileDom->save($this->target . $file->getId() . '.xml');
$this->saveDocument($fileReport->asDom(), $file->getId());
}
private function processUnit($unit, Report $report)
@@ -243,4 +261,23 @@ class Facade
$node->getNumTestedFunctions()
);
}
/**
* @return string
*/
protected function getTargetDirectory()
{
return $this->target;
}
protected function saveDocument(\DOMDocument $document, $name)
{
$filename = \sprintf('%s/%s.xml', $this->getTargetDirectory(), $name);
$document->formatOutput = true;
$document->preserveWhiteSpace = false;
$this->initTargetDirectory(\dirname($filename));
$document->save($filename);
}
}

View File

@@ -15,12 +15,12 @@ class File
/**
* @var \DOMDocument
*/
protected $dom;
private $dom;
/**
* @var \DOMElement
*/
protected $contextNode;
private $contextNode;
public function __construct(\DOMElement $context)
{
@@ -28,6 +28,22 @@ class File
$this->contextNode = $context;
}
/**
* @return \DOMElement
*/
protected function getContextNode()
{
return $this->contextNode;
}
/**
* @return \DOMDocument
*/
protected function getDomDocument()
{
return $this->dom;
}
public function getTotals()
{
$totalsContainer = $this->contextNode->firstChild;

View File

@@ -12,16 +12,19 @@ namespace SebastianBergmann\CodeCoverage\Report\Xml;
class Project extends Node
{
public function __construct($name)
/**
* @param string $directory
*/
public function __construct($directory)
{
$this->init();
$this->setProjectName($name);
$this->setProjectSourceDirectory($directory);
}
private function init()
{
$dom = new \DOMDocument;
$dom->loadXML('<?xml version="1.0" ?><phpunit xmlns="http://schema.phpunit.de/coverage/1.0"><project/></phpunit>');
$dom = new \DOMDocument();
$dom->loadXML('<?xml version="1.0" ?><phpunit xmlns="http://schema.phpunit.de/coverage/1.0"><build/><project/></phpunit>');
$this->setContextNode(
$dom->getElementsByTagNameNS(
@@ -31,9 +34,39 @@ class Project extends Node
);
}
private function setProjectName($name)
private function setProjectSourceDirectory($name)
{
$this->getContextNode()->setAttribute('name', $name);
$this->getContextNode()->setAttribute('source', $name);
}
/**
* @return string
*/
public function getProjectSourceDirectory()
{
return $this->getContextNode()->getAttribute('source');
}
/**
* @return BuildInformation
*/
public function getBuildInformation()
{
$buildNode = $this->getDom()->getElementsByTagNameNS(
'http://schema.phpunit.de/coverage/1.0',
'build'
)->item(0);
if (!$buildNode) {
$buildNode = $this->getDom()->documentElement->appendChild(
$this->getDom()->createElementNS(
'http://schema.phpunit.de/coverage/1.0',
'build'
)
);
}
return new BuildInformation($buildNode);
}
public function getTests()

View File

@@ -14,31 +14,33 @@ class Report extends File
{
public function __construct($name)
{
$this->dom = new \DOMDocument;
$this->dom->loadXML('<?xml version="1.0" ?><phpunit xmlns="http://schema.phpunit.de/coverage/1.0"><file /></phpunit>');
$dom = new \DOMDocument();
$dom->loadXML('<?xml version="1.0" ?><phpunit xmlns="http://schema.phpunit.de/coverage/1.0"><file /></phpunit>');
$this->contextNode = $this->dom->getElementsByTagNameNS(
$contextNode = $dom->getElementsByTagNameNS(
'http://schema.phpunit.de/coverage/1.0',
'file'
)->item(0);
parent::__construct($contextNode);
$this->setName($name);
}
private function setName($name)
{
$this->contextNode->setAttribute('name', $name);
$this->getContextNode()->setAttribute('name', \basename($name));
$this->getContextNode()->setAttribute('path', \dirname($name));
}
public function asDom()
{
return $this->dom;
return $this->getDomDocument();
}
public function getFunctionObject($name)
{
$node = $this->contextNode->appendChild(
$this->dom->createElementNS(
$node = $this->getContextNode()->appendChild(
$this->getDomDocument()->createElementNS(
'http://schema.phpunit.de/coverage/1.0',
'function'
)
@@ -59,8 +61,8 @@ class Report extends File
private function getUnitObject($tagName, $name)
{
$node = $this->contextNode->appendChild(
$this->dom->createElementNS(
$node = $this->getContextNode()->appendChild(
$this->getDomDocument()->createElementNS(
'http://schema.phpunit.de/coverage/1.0',
$tagName
)
@@ -68,4 +70,23 @@ class Report extends File
return new Unit($node, $name);
}
public function getSource()
{
$source = $this->getContextNode()->getElementsByTagNameNS(
'http://schema.phpunit.de/coverage/1.0',
'source'
)->item(0);
if (!$source) {
$source = $this->getContextNode()->appendChild(
$this->getDomDocument()->createElementNS(
'http://schema.phpunit.de/coverage/1.0',
'source'
)
);
}
return new Source($source);
}
}

View File

@@ -0,0 +1,45 @@
<?php
/*
* This file is part of the php-code-coverage package.
*
* (c) Sebastian Bergmann <sebastian@phpunit.de>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace SebastianBergmann\CodeCoverage\Report\Xml;
use TheSeer\Tokenizer\NamespaceUri;
use TheSeer\Tokenizer\Tokenizer;
use TheSeer\Tokenizer\XMLSerializer;
class Source
{
/** @var \DOMElement */
private $context;
/**
* @param \DOMElement $context
*/
public function __construct(\DOMElement $context)
{
$this->context = $context;
}
/**
* @param string $source
*/
public function setSourceCode(string $source)
{
$context = $this->context;
$tokens = (new Tokenizer())->parse($source);
$srcDom = (new XMLSerializer(new NamespaceUri($context->namespaceURI)))->toDom($tokens);
$context->parentNode->replaceChild(
$context->ownerDocument->importNode($srcDom->documentElement, true),
$context
);
}
}

View File

@@ -95,7 +95,7 @@ class Totals
$this->linesNode->setAttribute('executed', $executed);
$this->linesNode->setAttribute(
'percent',
Util::percent($executed, $executable, true)
$executable === 0 ? 0 : \sprintf('%01.2F', Util::percent($executed, $executable, false))
);
}
@@ -105,7 +105,7 @@ class Totals
$this->classesNode->setAttribute('tested', $tested);
$this->classesNode->setAttribute(
'percent',
Util::percent($tested, $count, true)
$count === 0 ? 0 : \sprintf('%01.2F', Util::percent($tested, $count, false))
);
}
@@ -115,7 +115,7 @@ class Totals
$this->traitsNode->setAttribute('tested', $tested);
$this->traitsNode->setAttribute(
'percent',
Util::percent($tested, $count, true)
$count === 0 ? 0 : \sprintf('%01.2F', Util::percent($tested, $count, false))
);
}
@@ -125,7 +125,7 @@ class Totals
$this->methodsNode->setAttribute('tested', $tested);
$this->methodsNode->setAttribute(
'percent',
Util::percent($tested, $count, true)
$count === 0 ? 0 : \sprintf('%01.2F', Util::percent($tested, $count, false))
);
}
@@ -135,7 +135,7 @@ class Totals
$this->functionsNode->setAttribute('tested', $tested);
$this->functionsNode->setAttribute(
'percent',
Util::percent($tested, $count, true)
$count === 0 ? 0 : \sprintf('%01.2F', Util::percent($tested, $count, false))
);
}
}

View File

@@ -29,20 +29,18 @@ class Util
return '';
}
$percent = 100;
if ($b > 0) {
$percent = ($a / $b) * 100;
} else {
$percent = 100;
}
if ($asString) {
if ($fixedWidth) {
return sprintf('%6.2F%%', $percent);
}
$format = $fixedWidth ? '%6.2F%%' : '%01.2F%%';
return sprintf('%01.2F%%', $percent);
} else {
return $percent;
return \sprintf($format, $percent);
}
return $percent;
}
}

View File

@@ -0,0 +1,31 @@
<?php
/*
* This file is part of the php-code-coverage package.
*
* (c) Sebastian Bergmann <sebastian@phpunit.de>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace SebastianBergmann\CodeCoverage;
use SebastianBergmann\Version as VersionId;
class Version
{
private static $version;
/**
* @return string
*/
public static function id()
{
if (self::$version === null) {
$version = new VersionId('5.3.0', \dirname(__DIR__));
self::$version = $version->getVersion();
}
return self::$version;
}
}

View File

@@ -17,7 +17,7 @@ use SebastianBergmann\CodeCoverage\Driver\Xdebug;
*
* @since Class available since Release 1.0.0
*/
abstract class TestCase extends \PHPUnit_Framework_TestCase
abstract class TestCase extends \PHPUnit\Framework\TestCase
{
protected static $TEST_TMP_PATH;

View File

@@ -1,7 +1,9 @@
<?php
require_once 'BankAccount.php';
class BankAccountTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class BankAccountTest extends TestCase
{
protected $ba;

View File

@@ -1,5 +1,7 @@
<?php
class CoverageClassExtendedTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageClassExtendedTest extends TestCase
{
/**
* @covers CoveredClass<extended>

View File

@@ -1,5 +1,7 @@
<?php
class CoverageClassTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageClassTest extends TestCase
{
/**
* @covers CoveredClass

View File

@@ -1,5 +1,7 @@
<?php
class CoverageFunctionParenthesesTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageFunctionParenthesesTest extends TestCase
{
/**
* @covers ::globalFunction()

View File

@@ -1,5 +1,7 @@
<?php
class CoverageFunctionParenthesesWhitespaceTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageFunctionParenthesesWhitespaceTest extends TestCase
{
/**
* @covers ::globalFunction ( )

View File

@@ -1,5 +1,7 @@
<?php
class CoverageFunctionTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageFunctionTest extends TestCase
{
/**
* @covers ::globalFunction

View File

@@ -1,6 +1,7 @@
<?php
use PHPUnit\Framework\TestCase;
class CoverageMethodOneLineAnnotationTest extends PHPUnit_Framework_TestCase
class CoverageMethodOneLineAnnotationTest extends TestCase
{
/** @covers CoveredClass::publicMethod */
public function testSomething()

View File

@@ -1,5 +1,7 @@
<?php
class CoverageMethodParenthesesTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageMethodParenthesesTest extends TestCase
{
/**
* @covers CoveredClass::publicMethod()

View File

@@ -1,5 +1,7 @@
<?php
class CoverageMethodParenthesesWhitespaceTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageMethodParenthesesWhitespaceTest extends TestCase
{
/**
* @covers CoveredClass::publicMethod ( )

View File

@@ -1,5 +1,7 @@
<?php
class CoverageMethodTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageMethodTest extends TestCase
{
/**
* @covers CoveredClass::publicMethod

View File

@@ -1,5 +1,7 @@
<?php
class CoverageNoneTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageNoneTest extends TestCase
{
public function testSomething()
{

View File

@@ -1,5 +1,7 @@
<?php
class CoverageNotPrivateTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageNotPrivateTest extends TestCase
{
/**
* @covers CoveredClass::<!private>

View File

@@ -1,5 +1,7 @@
<?php
class CoverageNotProtectedTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageNotProtectedTest extends TestCase
{
/**
* @covers CoveredClass::<!protected>

View File

@@ -1,5 +1,7 @@
<?php
class CoverageNotPublicTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageNotPublicTest extends TestCase
{
/**
* @covers CoveredClass::<!public>

View File

@@ -1,5 +1,7 @@
<?php
class CoverageNothingTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageNothingTest extends TestCase
{
/**
* @covers CoveredClass::publicMethod

View File

@@ -1,5 +1,7 @@
<?php
class CoveragePrivateTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoveragePrivateTest extends TestCase
{
/**
* @covers CoveredClass::<private>

View File

@@ -1,5 +1,7 @@
<?php
class CoverageProtectedTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoverageProtectedTest extends TestCase
{
/**
* @covers CoveredClass::<protected>

View File

@@ -1,5 +1,7 @@
<?php
class CoveragePublicTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class CoveragePublicTest extends TestCase
{
/**
* @covers CoveredClass::<public>

View File

@@ -1,5 +1,4 @@
<?php
/**
* @coversDefaultClass \NamespaceOne
* @coversDefaultClass \AnotherDefault\Name\Space\Does\Not\Work

View File

@@ -1,5 +1,7 @@
<?php
class NamespaceCoverageClassExtendedTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NamespaceCoverageClassExtendedTest extends TestCase
{
/**
* @covers Foo\CoveredClass<extended>

View File

@@ -1,5 +1,7 @@
<?php
class NamespaceCoverageClassTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NamespaceCoverageClassTest extends TestCase
{
/**
* @covers Foo\CoveredClass

View File

@@ -1,8 +1,10 @@
<?php
use PHPUnit\Framework\TestCase;
/**
* @coversDefaultClass \Foo\CoveredClass
*/
class NamespaceCoverageCoversClassPublicTest extends PHPUnit_Framework_TestCase
class NamespaceCoverageCoversClassPublicTest extends TestCase
{
/**
* @covers ::publicMethod

View File

@@ -1,8 +1,10 @@
<?php
use PHPUnit\Framework\TestCase;
/**
* @coversDefaultClass \Foo\CoveredClass
*/
class NamespaceCoverageCoversClassTest extends PHPUnit_Framework_TestCase
class NamespaceCoverageCoversClassTest extends TestCase
{
/**
* @covers ::privateMethod

View File

@@ -1,5 +1,7 @@
<?php
class NamespaceCoverageMethodTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NamespaceCoverageMethodTest extends TestCase
{
/**
* @covers Foo\CoveredClass::publicMethod

View File

@@ -1,5 +1,7 @@
<?php
class NamespaceCoverageNotPrivateTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NamespaceCoverageNotPrivateTest extends TestCase
{
/**
* @covers Foo\CoveredClass::<!private>

View File

@@ -1,5 +1,7 @@
<?php
class NamespaceCoverageNotProtectedTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NamespaceCoverageNotProtectedTest extends TestCase
{
/**
* @covers Foo\CoveredClass::<!protected>

View File

@@ -1,5 +1,7 @@
<?php
class NamespaceCoverageNotPublicTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NamespaceCoverageNotPublicTest extends TestCase
{
/**
* @covers Foo\CoveredClass::<!public>

View File

@@ -1,5 +1,7 @@
<?php
class NamespaceCoveragePrivateTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NamespaceCoveragePrivateTest extends TestCase
{
/**
* @covers Foo\CoveredClass::<private>

View File

@@ -1,5 +1,7 @@
<?php
class NamespaceCoverageProtectedTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NamespaceCoverageProtectedTest extends TestCase
{
/**
* @covers Foo\CoveredClass::<protected>

View File

@@ -1,5 +1,7 @@
<?php
class NamespaceCoveragePublicTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NamespaceCoveragePublicTest extends TestCase
{
/**
* @covers Foo\CoveredClass::<public>

View File

@@ -1,5 +1,7 @@
<?php
class NotExistingCoveredElementTest extends PHPUnit_Framework_TestCase
use PHPUnit\Framework\TestCase;
class NotExistingCoveredElementTest extends TestCase
{
/**
* @covers NotExistingClass

View File

@@ -4,11 +4,11 @@
<meta charset="UTF-8">
<title>Code Coverage for %s/BankAccount.php</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="css/bootstrap.min.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<link href=".css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href=".css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="js/html5shiv.min.js"></script>
<script src="js/respond.min.js"></script>
<script src=".js/html5shiv.min.js"></script>
<script src=".js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -232,36 +232,14 @@
<span class="warning"><strong>Dead Code</strong></span>
</p>
<p>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="http%sphp.net/" target="_top">PHP%s</a>%s at %s.</small>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="%s" target="_top">%s</a> at %s.</small>
</p>
<a title="Back to the top" id="toplink" href="#"><span class="glyphicon glyphicon-arrow-up"></span></a>
</footer>
</div>
<script src="js/jquery.min.js" type="text/javascript"></script>
<script src="js/bootstrap.min.js" type="text/javascript"></script>
<script src="js/holder.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(function() {
var $window = $(window)
, $top_link = $('#toplink')
, $body = $('body, html')
, offset = $('#code').offset().top;
$top_link.hide().click(function(event) {
event.preventDefault();
$body.animate({scrollTop:0}, 800);
});
$window.scroll(function() {
if($window.scrollTop() > offset) {
$top_link.fadeIn();
} else {
$top_link.fadeOut();
}
}).scroll();
$('.popin').popover({trigger: 'hover'});
});
</script>
<script src=".js/jquery.min.js" type="text/javascript"></script>
<script src=".js/bootstrap.min.js" type="text/javascript"></script>
<script src=".js/holder.min.js" type="text/javascript"></script>
<script src=".js/file.js" type="text/javascript"></script>
</body>
</html>

View File

@@ -4,12 +4,12 @@
<meta charset="UTF-8">
<title>Dashboard for %s</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="css/bootstrap.min.css" rel="stylesheet">
<link href="css/nv.d3.min.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<link href=".css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href=".css/nv.d3.min.css" rel="stylesheet" type="text/css">
<link href=".css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="js/html5shiv.min.js"></script>
<script src="js/respond.min.js"></script>
<script src=".js/html5shiv.min.js"></script>
<script src=".js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -140,15 +140,15 @@
<footer>
<hr/>
<p>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="http%sphp.net/" target="_top">PHP%s</a>%s at %s.</small>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="%s" target="_top">%s</a> at %s.</small>
</p>
</footer>
</div>
<script src="js/jquery.min.js" type="text/javascript"></script>
<script src="js/bootstrap.min.js" type="text/javascript"></script>
<script src="js/holder.min.js" type="text/javascript"></script>
<script src="js/d3.min.js" type="text/javascript"></script>
<script src="js/nv.d3.min.js" type="text/javascript"></script>
<script src=".js/jquery.min.js" type="text/javascript"></script>
<script src=".js/bootstrap.min.js" type="text/javascript"></script>
<script src=".js/holder.min.js" type="text/javascript"></script>
<script src=".js/d3.min.js" type="text/javascript"></script>
<script src=".js/nv.d3.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function() {
nv.addGraph(function() {

View File

@@ -4,11 +4,11 @@
<meta charset="UTF-8">
<title>Code Coverage for %s</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="css/bootstrap.min.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<link href=".css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href=".css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="js/html5shiv.min.js"></script>
<script src="js/respond.min.js"></script>
<script src=".js/html5shiv.min.js"></script>
<script src=".js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -108,12 +108,12 @@
<span class="success"><strong>High</strong>: 90% to 100%</span>
</p>
<p>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="http%sphp.net/" target="_top">PHP%s</a>%s at %s.</small>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="%s" target="_top">%s</a> at %s.</small>
</p>
</footer>
</div>
<script src="js/jquery.min.js" type="text/javascript"></script>
<script src="js/bootstrap.min.js" type="text/javascript"></script>
<script src="js/holder.min.js" type="text/javascript"></script>
<script src=".js/jquery.min.js" type="text/javascript"></script>
<script src=".js/bootstrap.min.js" type="text/javascript"></script>
<script src=".js/holder.min.js" type="text/javascript"></script>
</body>
</html>

View File

@@ -4,12 +4,12 @@
<meta charset="UTF-8">
<title>Dashboard for %s</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="css/bootstrap.min.css" rel="stylesheet">
<link href="css/nv.d3.min.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<link href=".css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href=".css/nv.d3.min.css" rel="stylesheet" type="text/css">
<link href=".css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="js/html5shiv.min.js"></script>
<script src="js/respond.min.js"></script>
<script src=".js/html5shiv.min.js"></script>
<script src=".js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -138,15 +138,15 @@
<footer>
<hr/>
<p>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="http%sphp.net/" target="_top">PHP%s</a>%s at %s.</small>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="%s" target="_top">%s</a> at %s.</small>
</p>
</footer>
</div>
<script src="js/jquery.min.js" type="text/javascript"></script>
<script src="js/bootstrap.min.js" type="text/javascript"></script>
<script src="js/holder.min.js" type="text/javascript"></script>
<script src="js/d3.min.js" type="text/javascript"></script>
<script src="js/nv.d3.min.js" type="text/javascript"></script>
<script src=".js/jquery.min.js" type="text/javascript"></script>
<script src=".js/bootstrap.min.js" type="text/javascript"></script>
<script src=".js/holder.min.js" type="text/javascript"></script>
<script src=".js/d3.min.js" type="text/javascript"></script>
<script src=".js/nv.d3.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function() {
nv.addGraph(function() {
@@ -251,7 +251,7 @@ $(document).ready(function() {
chart.yAxis.axisLabel('Method Complexity');
d3.select('#methodComplexity svg')
.datum(getComplexityData([[66.666666666667,1,"<a href=\"source_with_class_and_anonymous_function.php.html#5\">CoveredClassWithAnonymousFunctionInStaticMethod::runAnonymous<\/a>"],[100,1,"<a href=\"source_with_class_and_anonymous_function.php.html#11\">CoveredClassWithAnonymousFunctionInStaticMethod::anonymous function<\/a>"]], 'Method Complexity'))
.datum(getComplexityData([[66.666666666667,1,"<a href=\"source_with_class_and_anonymous_function.php.html#5\">CoveredClassWithAnonymousFunctionInStaticMethod::runAnonymous<\/a>"],[100,1,"<a href=\"source_with_class_and_anonymous_function.php.html#11\">CoveredClassWithAnonymousFunctionInStaticMethod::anonymousFunction:11#41<\/a>"]], 'Method Complexity'))
.transition()
.duration(500)
.call(chart);

View File

@@ -4,11 +4,11 @@
<meta charset="UTF-8">
<title>Code Coverage for %s</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="css/bootstrap.min.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<link href=".css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href=".css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="js/html5shiv.min.js"></script>
<script src="js/respond.min.js"></script>
<script src=".js/html5shiv.min.js"></script>
<script src=".js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -108,12 +108,12 @@
<span class="success"><strong>High</strong>: 90% to 100%</span>
</p>
<p>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="http%sphp.net/" target="_top">PHP%s</a>%s at %s.</small>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="%s" target="_top">%s</a> at %s.</small>
</p>
</footer>
</div>
<script src="js/jquery.min.js" type="text/javascript"></script>
<script src="js/bootstrap.min.js" type="text/javascript"></script>
<script src="js/holder.min.js" type="text/javascript"></script>
<script src=".js/jquery.min.js" type="text/javascript"></script>
<script src=".js/bootstrap.min.js" type="text/javascript"></script>
<script src=".js/holder.min.js" type="text/javascript"></script>
</body>
</html>

View File

@@ -4,11 +4,11 @@
<meta charset="UTF-8">
<title>Code Coverage for %s/source_with_class_and_anonymous_function.php</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="css/bootstrap.min.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<link href=".css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href=".css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="js/html5shiv.min.js"></script>
<script src="js/respond.min.js"></script>
<script src=".js/html5shiv.min.js"></script>
<script src=".js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -120,7 +120,7 @@
</tr>
<tr>
<td class="success" colspan="4">&nbsp;<a href="#11"><abbr title="anonymous function (&amp;$val, $key)">anonymous function</abbr></a></td>
<td class="success" colspan="4">&nbsp;<a href="#11"><abbr title="anonymousFunction (&amp;$val, $key)">anonymousFunction:11#41</abbr></a></td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
@@ -176,36 +176,14 @@
<span class="warning"><strong>Dead Code</strong></span>
</p>
<p>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="http%sphp.net/" target="_top">PHP%s</a>%s at %s.</small>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="%s" target="_top">%s</a> at %s.</small>
</p>
<a title="Back to the top" id="toplink" href="#"><span class="glyphicon glyphicon-arrow-up"></span></a>
</footer>
</div>
<script src="js/jquery.min.js" type="text/javascript"></script>
<script src="js/bootstrap.min.js" type="text/javascript"></script>
<script src="js/holder.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(function() {
var $window = $(window)
, $top_link = $('#toplink')
, $body = $('body, html')
, offset = $('#code').offset().top;
$top_link.hide().click(function(event) {
event.preventDefault();
$body.animate({scrollTop:0}, 800);
});
$window.scroll(function() {
if($window.scrollTop() > offset) {
$top_link.fadeIn();
} else {
$top_link.fadeOut();
}
}).scroll();
$('.popin').popover({trigger: 'hover'});
});
</script>
<script src=".js/jquery.min.js" type="text/javascript"></script>
<script src=".js/bootstrap.min.js" type="text/javascript"></script>
<script src=".js/holder.min.js" type="text/javascript"></script>
<script src=".js/file.js" type="text/javascript"></script>
</body>
</html>

View File

@@ -4,12 +4,12 @@
<meta charset="UTF-8">
<title>Dashboard for %s</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="css/bootstrap.min.css" rel="stylesheet">
<link href="css/nv.d3.min.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<link href=".css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href=".css/nv.d3.min.css" rel="stylesheet" type="text/css">
<link href=".css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="js/html5shiv.min.js"></script>
<script src="js/respond.min.js"></script>
<script src=".js/html5shiv.min.js"></script>
<script src=".js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -136,15 +136,15 @@
<footer>
<hr/>
<p>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="http%sphp.net/" target="_top">PHP%s</a>%s at %s.</small>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="%s" target="_top">%s</a> at %s.</small>
</p>
</footer>
</div>
<script src="js/jquery.min.js" type="text/javascript"></script>
<script src="js/bootstrap.min.js" type="text/javascript"></script>
<script src="js/holder.min.js" type="text/javascript"></script>
<script src="js/d3.min.js" type="text/javascript"></script>
<script src="js/nv.d3.min.js" type="text/javascript"></script>
<script src=".js/jquery.min.js" type="text/javascript"></script>
<script src=".js/bootstrap.min.js" type="text/javascript"></script>
<script src=".js/holder.min.js" type="text/javascript"></script>
<script src=".js/d3.min.js" type="text/javascript"></script>
<script src=".js/nv.d3.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function() {
nv.addGraph(function() {

View File

@@ -4,11 +4,11 @@
<meta charset="UTF-8">
<title>Code Coverage for %s</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="css/bootstrap.min.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<link href=".css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href=".css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="js/html5shiv.min.js"></script>
<script src="js/respond.min.js"></script>
<script src=".js/html5shiv.min.js"></script>
<script src=".js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -57,15 +57,10 @@
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">2&nbsp;/&nbsp;2</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
</tr>
<tr>
@@ -85,15 +80,10 @@
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">2&nbsp;/&nbsp;2</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
</tr>
@@ -108,12 +98,12 @@
<span class="success"><strong>High</strong>: 90% to 100%</span>
</p>
<p>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="http%sphp.net/" target="_top">PHP%s</a>%s at %s.</small>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="%s" target="_top">%s</a> at %s.</small>
</p>
</footer>
</div>
<script src="js/jquery.min.js" type="text/javascript"></script>
<script src="js/bootstrap.min.js" type="text/javascript"></script>
<script src="js/holder.min.js" type="text/javascript"></script>
<script src=".js/jquery.min.js" type="text/javascript"></script>
<script src=".js/bootstrap.min.js" type="text/javascript"></script>
<script src=".js/holder.min.js" type="text/javascript"></script>
</body>
</html>

View File

@@ -2,13 +2,13 @@
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Code Coverage for %s/source_with_ignore.php</title>
<title>Code Coverage for %s</title>
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link href="css/bootstrap.min.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<link href=".css/bootstrap.min.css" rel="stylesheet" type="text/css">
<link href=".css/style.css" rel="stylesheet" type="text/css">
<!--[if lt IE 9]>
<script src="js/html5shiv.min.js"></script>
<script src="js/respond.min.js"></script>
<script src=".js/html5shiv.min.js"></script>
<script src=".js/respond.min.js"></script>
<![endif]-->
</head>
<body>
@@ -41,7 +41,10 @@
</thead>
<tbody>
<tr>
<td class="success">Total</td>
<td class="">Total</td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
@@ -49,15 +52,7 @@
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">2&nbsp;/&nbsp;2</div></td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class="success small"><abbr title="Change Risk Anti-Patterns (CRAP) Index">CRAP</abbr></td>
<td class="danger big"> <div class="progress">
<div class="progress-bar progress-bar-danger" role="progressbar" aria-valuenow="50.00" aria-valuemin="0" aria-valuemax="100" style="width: 50.00%">
@@ -79,27 +74,17 @@
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class="success small">0</td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class="success small">1</td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
</tr>
<tr>
<td class="success">Foo</td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class="">Foo</td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
@@ -109,14 +94,9 @@
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class="success small">1</td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
</tr>
<tr>
@@ -130,26 +110,16 @@
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class="success small">1</td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
</tr>
<tr>
<td class="success">Bar</td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class="">Bar</td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
@@ -159,14 +129,9 @@
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class="success small">1</td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
</tr>
<tr>
@@ -180,14 +145,9 @@
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">1&nbsp;/&nbsp;1</div></td>
<td class="success small">1</td>
<td class="success big"> <div class="progress">
<div class="progress-bar progress-bar-success" role="progressbar" aria-valuenow="100.00" aria-valuemin="0" aria-valuemax="100" style="width: 100.00%">
<span class="sr-only">100.00% covered (success)</span>
</div>
</div>
</td>
<td class="success small"><div align="right">100.00%</div></td>
<td class="success small"><div align="right">0&nbsp;/&nbsp;0</div></td>
<td class=" big"></td>
<td class=" small"><div align="right">n/a</div></td>
<td class=" small"><div align="right">0&nbsp;/&nbsp;0</div></td>
</tr>
@@ -244,36 +204,14 @@
<span class="warning"><strong>Dead Code</strong></span>
</p>
<p>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="http%sphp.net/" target="_top">PHP%s</a>%s at %s.</small>
<small>Generated by <a href="https://github.com/sebastianbergmann/php-code-coverage" target="_top">php-code-coverage %s</a> using <a href="%s" target="_top">%s</a> at %s.</small>
</p>
<a title="Back to the top" id="toplink" href="#"><span class="glyphicon glyphicon-arrow-up"></span></a>
</footer>
</div>
<script src="js/jquery.min.js" type="text/javascript"></script>
<script src="js/bootstrap.min.js" type="text/javascript"></script>
<script src="js/holder.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(function() {
var $window = $(window)
, $top_link = $('#toplink')
, $body = $('body, html')
, offset = $('#code').offset().top;
$top_link.hide().click(function(event) {
event.preventDefault();
$body.animate({scrollTop:0}, 800);
});
$window.scroll(function() {
if($window.scrollTop() > offset) {
$top_link.fadeIn();
} else {
$top_link.fadeOut();
}
}).scroll();
$('.popin').popover({trigger: 'hover'});
});
</script>
<script src=".js/jquery.min.js" type="text/javascript"></script>
<script src=".js/bootstrap.min.js" type="text/javascript"></script>
<script src=".js/holder.min.js" type="text/javascript"></script>
<script src=".js/file.js" type="text/javascript"></script>
</body>
</html>

View File

@@ -1,12 +1,12 @@
<?xml version="1.0"?>
<phpunit xmlns="http://schema.phpunit.de/coverage/1.0">
<file name="BankAccount.php">
<file name="BankAccount.php" path="/">
<totals>
<lines total="33" comments="0" code="33" executable="10" executed="5" percent="50.00%"/>
<methods count="4" tested="3" percent="75.00%"/>
<functions count="0" tested="0" percent=""/>
<classes count="1" tested="0" percent="0.00%"/>
<traits count="0" tested="0" percent=""/>
<lines total="33" comments="0" code="33" executable="10" executed="5" percent="50.00"/>
<methods count="4" tested="3" percent="75.00"/>
<functions count="0" tested="0" percent="0"/>
<classes count="1" tested="0" percent="0.00"/>
<traits count="0" tested="0" percent="0"/>
</totals>
<class name="BankAccount" start="2" executable="10" executed="5" crap="8.12">
<package full="" name="" sub="" category=""/>
@@ -36,5 +36,227 @@
<covered by="BankAccountTest::testDepositWithdrawMoney"/>
</line>
</coverage>
<source>
<line no="1">
<token name="T_OPEN_TAG">&lt;?php</token>
</line>
<line no="2">
<token name="T_CLASS">class</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">BankAccount</token>
</line>
<line no="3">
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="4">
<token name="T_WHITESPACE"> </token>
<token name="T_PROTECTED">protected</token>
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$balance</token>
<token name="T_WHITESPACE"> </token>
<token name="T_EQUAL">=</token>
<token name="T_WHITESPACE"> </token>
<token name="T_LNUMBER">0</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="5"/>
<line no="6">
<token name="T_WHITESPACE"> </token>
<token name="T_PUBLIC">public</token>
<token name="T_WHITESPACE"> </token>
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">getBalance</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
</line>
<line no="7">
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="8">
<token name="T_WHITESPACE"> </token>
<token name="T_RETURN">return</token>
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$this</token>
<token name="T_OBJECT_OPERATOR">-&gt;</token>
<token name="T_STRING">balance</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="9">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="10"/>
<line no="11">
<token name="T_WHITESPACE"> </token>
<token name="T_PROTECTED">protected</token>
<token name="T_WHITESPACE"> </token>
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">setBalance</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_VARIABLE">$balance</token>
<token name="T_CLOSE_BRACKET">)</token>
</line>
<line no="12">
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="13">
<token name="T_WHITESPACE"> </token>
<token name="T_IF">if</token>
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_VARIABLE">$balance</token>
<token name="T_WHITESPACE"> </token>
<token name="T_IS_GREATER_OR_EQUAL">&gt;=</token>
<token name="T_WHITESPACE"> </token>
<token name="T_LNUMBER">0</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="14">
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$this</token>
<token name="T_OBJECT_OPERATOR">-&gt;</token>
<token name="T_STRING">balance</token>
<token name="T_WHITESPACE"> </token>
<token name="T_EQUAL">=</token>
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$balance</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="15">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
<token name="T_WHITESPACE"> </token>
<token name="T_ELSE">else</token>
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="16">
<token name="T_WHITESPACE"> </token>
<token name="T_THROW">throw</token>
<token name="T_WHITESPACE"> </token>
<token name="T_NEW">new</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">RuntimeException</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="17">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="18">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="19"/>
<line no="20">
<token name="T_WHITESPACE"> </token>
<token name="T_PUBLIC">public</token>
<token name="T_WHITESPACE"> </token>
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">depositMoney</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_VARIABLE">$balance</token>
<token name="T_CLOSE_BRACKET">)</token>
</line>
<line no="21">
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="22">
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$this</token>
<token name="T_OBJECT_OPERATOR">-&gt;</token>
<token name="T_STRING">setBalance</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_VARIABLE">$this</token>
<token name="T_OBJECT_OPERATOR">-&gt;</token>
<token name="T_STRING">getBalance</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_WHITESPACE"> </token>
<token name="T_PLUS">+</token>
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$balance</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="23"/>
<line no="24">
<token name="T_WHITESPACE"> </token>
<token name="T_RETURN">return</token>
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$this</token>
<token name="T_OBJECT_OPERATOR">-&gt;</token>
<token name="T_STRING">getBalance</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="25">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="26"/>
<line no="27">
<token name="T_WHITESPACE"> </token>
<token name="T_PUBLIC">public</token>
<token name="T_WHITESPACE"> </token>
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">withdrawMoney</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_VARIABLE">$balance</token>
<token name="T_CLOSE_BRACKET">)</token>
</line>
<line no="28">
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="29">
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$this</token>
<token name="T_OBJECT_OPERATOR">-&gt;</token>
<token name="T_STRING">setBalance</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_VARIABLE">$this</token>
<token name="T_OBJECT_OPERATOR">-&gt;</token>
<token name="T_STRING">getBalance</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_WHITESPACE"> </token>
<token name="T_MINUS">-</token>
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$balance</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="30"/>
<line no="31">
<token name="T_WHITESPACE"> </token>
<token name="T_RETURN">return</token>
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$this</token>
<token name="T_OBJECT_OPERATOR">-&gt;</token>
<token name="T_STRING">getBalance</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="32">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="33">
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="34"/>
</source>
</file>
</phpunit>

View File

@@ -1,6 +1,10 @@
<?xml version="1.0"?>
<phpunit xmlns="http://schema.phpunit.de/coverage/1.0">
<project name="%s">
<build time="%s" phpunit="%s" coverage="%s">
<runtime name="%s" version="%s" url="%s"/>
<driver name="%s" version="%s"/>
</build>
<project source="%s">
<tests>
<test name="BankAccountTest::testBalanceIsInitiallyZero" size="unknown" result="0" status="PASSED"/>
<test name="BankAccountTest::testBalanceCannotBecomeNegative" size="unknown" result="0" status="PASSED"/>
@@ -9,19 +13,19 @@
</tests>
<directory name="%s">
<totals>
<lines total="33" comments="0" code="33" executable="10" executed="5" percent="50.00%"/>
<methods count="4" tested="3" percent="75.00%"/>
<functions count="0" tested="0" percent=""/>
<classes count="1" tested="0" percent="0.00%"/>
<traits count="0" tested="0" percent=""/>
<lines total="33" comments="0" code="33" executable="10" executed="5" percent="50.00"/>
<methods count="4" tested="3" percent="75.00"/>
<functions count="0" tested="0" percent="0"/>
<classes count="1" tested="0" percent="0.00"/>
<traits count="0" tested="0" percent="0"/>
</totals>
<file name="BankAccount.php" href="BankAccount.php.xml">
<totals>
<lines total="33" comments="0" code="33" executable="10" executed="5" percent="50.00%"/>
<methods count="4" tested="3" percent="75.00%"/>
<functions count="0" tested="0" percent=""/>
<classes count="1" tested="0" percent="0.00%"/>
<traits count="0" tested="0" percent=""/>
<lines total="33" comments="0" code="33" executable="10" executed="5" percent="50.00"/>
<methods count="4" tested="3" percent="75.00"/>
<functions count="0" tested="0" percent="0"/>
<classes count="1" tested="0" percent="0.00"/>
<traits count="0" tested="0" percent="0"/>
</totals>
</file>
</directory>

View File

@@ -1,24 +1,28 @@
<?xml version="1.0"?>
<phpunit xmlns="http://schema.phpunit.de/coverage/1.0">
<project name="%s">
<build time="%s" phpunit="%s" coverage="%s">
<runtime name="%s" version="%s" url="%s"/>
<driver name="%s" version="%s"/>
</build>
<project source="%s">
<tests>
<test name="ClassWithAnonymousFunction" size="unknown" result="0" status="PASSED"/>
</tests>
<directory name="%s">
<totals>
<lines total="19" comments="2" code="17" executable="8" executed="7" percent="87.50%"/>
<methods count="2" tested="1" percent="50.00%"/>
<functions count="0" tested="0" percent=""/>
<classes count="1" tested="0" percent="0.00%"/>
<traits count="0" tested="0" percent=""/>
<lines total="19" comments="2" code="17" executable="8" executed="7" percent="87.50"/>
<methods count="2" tested="1" percent="50.00"/>
<functions count="0" tested="0" percent="0"/>
<classes count="1" tested="0" percent="0.00"/>
<traits count="0" tested="0" percent="0"/>
</totals>
<file name="source_with_class_and_anonymous_function.php" href="source_with_class_and_anonymous_function.php.xml">
<totals>
<lines total="19" comments="2" code="17" executable="8" executed="7" percent="87.50%"/>
<methods count="2" tested="1" percent="50.00%"/>
<functions count="0" tested="0" percent=""/>
<classes count="1" tested="0" percent="0.00%"/>
<traits count="0" tested="0" percent=""/>
<lines total="19" comments="2" code="17" executable="8" executed="7" percent="87.50"/>
<methods count="2" tested="1" percent="50.00"/>
<functions count="0" tested="0" percent="0"/>
<classes count="1" tested="0" percent="0.00"/>
<traits count="0" tested="0" percent="0"/>
</totals>
</file>
</directory>

View File

@@ -1,18 +1,18 @@
<?xml version="1.0"?>
<phpunit xmlns="http://schema.phpunit.de/coverage/1.0">
<file name="source_with_class_and_anonymous_function.php">
<file name="source_with_class_and_anonymous_function.php" path="/">
<totals>
<lines total="19" comments="2" code="17" executable="8" executed="7" percent="87.50%"/>
<methods count="2" tested="1" percent="50.00%"/>
<functions count="0" tested="0" percent=""/>
<classes count="1" tested="0" percent="0.00%"/>
<traits count="0" tested="0" percent=""/>
<lines total="19" comments="2" code="17" executable="8" executed="7" percent="87.50"/>
<methods count="2" tested="1" percent="50.00"/>
<functions count="0" tested="0" percent="0"/>
<classes count="1" tested="0" percent="0.00"/>
<traits count="0" tested="0" percent="0"/>
</totals>
<class name="CoveredClassWithAnonymousFunctionInStaticMethod" start="3" executable="8" executed="7" crap="2.01">
<package full="" name="" sub="" category=""/>
<namespace name=""/>
<method name="runAnonymous" signature="runAnonymous()" start="5" end="18" crap="1.04" executable="3" executed="2" coverage="66.666666666667"/>
<method name="anonymous function" signature="anonymous function (&amp;$val, $key)" start="11" end="13" crap="1" executable="2" executed="2" coverage="100"/>
<method name="anonymousFunction:11#41" signature="anonymousFunction (&amp;$val, $key)" start="11" end="13" crap="1" executable="2" executed="2" coverage="100"/>
</class>
<coverage>
<line nr="7">
@@ -37,5 +37,126 @@
<covered by="ClassWithAnonymousFunction"/>
</line>
</coverage>
<source>
<line no="1">
<token name="T_OPEN_TAG">&lt;?php</token>
</line>
<line no="2"/>
<line no="3">
<token name="T_CLASS">class</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">CoveredClassWithAnonymousFunctionInStaticMethod</token>
</line>
<line no="4">
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="5">
<token name="T_WHITESPACE"> </token>
<token name="T_PUBLIC">public</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STATIC">static</token>
<token name="T_WHITESPACE"> </token>
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">runAnonymous</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
</line>
<line no="6">
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="7">
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$filter</token>
<token name="T_WHITESPACE"> </token>
<token name="T_EQUAL">=</token>
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_SQUARE">[</token>
<token name="T_CONSTANT_ENCAPSED_STRING">'abc124'</token>
<token name="T_COMMA">,</token>
<token name="T_WHITESPACE"> </token>
<token name="T_CONSTANT_ENCAPSED_STRING">'abc123'</token>
<token name="T_COMMA">,</token>
<token name="T_WHITESPACE"> </token>
<token name="T_CONSTANT_ENCAPSED_STRING">'123'</token>
<token name="T_CLOSE_SQUARE">]</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="8"/>
<line no="9">
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">array_walk</token>
<token name="T_OPEN_BRACKET">(</token>
</line>
<line no="10">
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$filter</token>
<token name="T_COMMA">,</token>
</line>
<line no="11">
<token name="T_WHITESPACE"> </token>
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_AMPERSAND">&amp;</token>
<token name="T_VARIABLE">$val</token>
<token name="T_COMMA">,</token>
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$key</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="12">
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$val</token>
<token name="T_WHITESPACE"> </token>
<token name="T_EQUAL">=</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">preg_replace</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CONSTANT_ENCAPSED_STRING">'|[^0-9]|'</token>
<token name="T_COMMA">,</token>
<token name="T_WHITESPACE"> </token>
<token name="T_CONSTANT_ENCAPSED_STRING">''</token>
<token name="T_COMMA">,</token>
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$val</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="13">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="14">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="15"/>
<line no="16">
<token name="T_WHITESPACE"> </token>
<token name="T_COMMENT">// Should be covered</token>
</line>
<line no="17">
<token name="T_WHITESPACE"> </token>
<token name="T_VARIABLE">$extravar</token>
<token name="T_WHITESPACE"> </token>
<token name="T_EQUAL">=</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">true</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="18">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="19">
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="20"/>
</source>
</file>
</phpunit>

View File

@@ -1,24 +1,28 @@
<?xml version="1.0"?>
<phpunit xmlns="http://schema.phpunit.de/coverage/1.0">
<project name="%s">
<build time="%s" phpunit="%s" coverage="%s">
<runtime name="%s" version="%s" url="%s"/>
<driver name="%s" version="%s"/>
</build>
<project source="%s">
<tests>
<test name="FileWithIgnoredLines" size="unknown" result="0" status="PASSED"/>
</tests>
<directory name="%s">
<totals>
<lines total="37" comments="12" code="25" executable="2" executed="1" percent="50.00%"/>
<methods count="0" tested="0" percent=""/>
<functions count="1" tested="0" percent="0.00%"/>
<classes count="2" tested="2" percent="100.00%"/>
<traits count="0" tested="0" percent=""/>
<lines total="37" comments="12" code="25" executable="2" executed="1" percent="50.00"/>
<methods count="0" tested="0" percent="0"/>
<functions count="1" tested="1" percent="100.00"/>
<classes count="0" tested="0" percent="0"/>
<traits count="0" tested="0" percent="0"/>
</totals>
<file name="source_with_ignore.php" href="source_with_ignore.php.xml">
<totals>
<lines total="37" comments="12" code="25" executable="2" executed="1" percent="50.00%"/>
<methods count="0" tested="0" percent=""/>
<functions count="1" tested="0" percent="0.00%"/>
<classes count="2" tested="2" percent="100.00%"/>
<traits count="0" tested="0" percent=""/>
<lines total="37" comments="12" code="25" executable="2" executed="1" percent="50.00"/>
<methods count="0" tested="0" percent="0"/>
<functions count="1" tested="1" percent="100.00"/>
<classes count="0" tested="0" percent="0"/>
<traits count="0" tested="0" percent="0"/>
</totals>
</file>
</directory>

View File

@@ -1,12 +1,12 @@
<?xml version="1.0"?>
<phpunit xmlns="http://schema.phpunit.de/coverage/1.0">
<file name="source_with_ignore.php">
<file name="source_with_ignore.php" path="/">
<totals>
<lines total="37" comments="12" code="25" executable="2" executed="1" percent="50.00%"/>
<methods count="0" tested="0" percent=""/>
<functions count="1" tested="0" percent="0.00%"/>
<classes count="2" tested="2" percent="100.00%"/>
<traits count="0" tested="0" percent=""/>
<lines total="37" comments="12" code="25" executable="2" executed="1" percent="50.00"/>
<methods count="0" tested="0" percent="0"/>
<functions count="1" tested="1" percent="100.00"/>
<classes count="0" tested="0" percent="0"/>
<traits count="0" tested="0" percent="0"/>
</totals>
<class name="Foo" start="11" executable="0" executed="0" crap="1">
<package full="" name="" sub="" category=""/>
@@ -18,11 +18,170 @@
<namespace name=""/>
<method name="foo" signature="foo()" start="23" end="25" crap="1" executable="0" executed="0" coverage="100"/>
</class>
<function name="baz" signature="baz()" start="28" crap="0" executable="0" executed="0" coverage="0"/>
<function name="baz" signature="baz()" start="28" crap="1" executable="0" executed="0" coverage="100"/>
<coverage>
<line nr="2">
<covered by="FileWithIgnoredLines"/>
</line>
</coverage>
<source>
<line no="1">
<token name="T_OPEN_TAG">&lt;?php</token>
</line>
<line no="2">
<token name="T_IF">if</token>
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_VARIABLE">$neverHappens</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="3">
<token name="T_WHITESPACE"> </token>
<token name="T_COMMENT">// @codeCoverageIgnoreStart</token>
</line>
<line no="4">
<token name="T_WHITESPACE"> </token>
<token name="T_PRINT">print</token>
<token name="T_WHITESPACE"> </token>
<token name="T_CONSTANT_ENCAPSED_STRING">'*'</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="5">
<token name="T_WHITESPACE"> </token>
<token name="T_COMMENT">// @codeCoverageIgnoreEnd</token>
</line>
<line no="6">
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="7"/>
<line no="8">
<token name="T_DOC_COMMENT">/**</token>
</line>
<line no="9">
<token name="T_DOC_COMMENT"> * @codeCoverageIgnore</token>
</line>
<line no="10">
<token name="T_DOC_COMMENT"> */</token>
</line>
<line no="11">
<token name="T_CLASS">class</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">Foo</token>
</line>
<line no="12">
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="13">
<token name="T_WHITESPACE"> </token>
<token name="T_PUBLIC">public</token>
<token name="T_WHITESPACE"> </token>
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">bar</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
</line>
<line no="14">
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="15">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="16">
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="17"/>
<line no="18">
<token name="T_CLASS">class</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">Bar</token>
</line>
<line no="19">
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="20">
<token name="T_WHITESPACE"> </token>
<token name="T_DOC_COMMENT">/**</token>
</line>
<line no="21">
<token name="T_DOC_COMMENT"> * @codeCoverageIgnore</token>
</line>
<line no="22">
<token name="T_DOC_COMMENT"> */</token>
</line>
<line no="23">
<token name="T_WHITESPACE"> </token>
<token name="T_PUBLIC">public</token>
<token name="T_WHITESPACE"> </token>
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">foo</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
</line>
<line no="24">
<token name="T_WHITESPACE"> </token>
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="25">
<token name="T_WHITESPACE"> </token>
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="26">
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="27"/>
<line no="28">
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">baz</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
</line>
<line no="29">
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="30">
<token name="T_WHITESPACE"> </token>
<token name="T_PRINT">print</token>
<token name="T_WHITESPACE"> </token>
<token name="T_CONSTANT_ENCAPSED_STRING">'*'</token>
<token name="T_SEMICOLON">;</token>
<token name="T_WHITESPACE"> </token>
<token name="T_COMMENT">// @codeCoverageIgnore</token>
</line>
<line no="31">
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="32"/>
<line no="33">
<token name="T_INTERFACE">interface</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">Bor</token>
</line>
<line no="34">
<token name="T_OPEN_CURLY">{</token>
</line>
<line no="35">
<token name="T_WHITESPACE"> </token>
<token name="T_PUBLIC">public</token>
<token name="T_WHITESPACE"> </token>
<token name="T_FUNCTION">function</token>
<token name="T_WHITESPACE"> </token>
<token name="T_STRING">foo</token>
<token name="T_OPEN_BRACKET">(</token>
<token name="T_CLOSE_BRACKET">)</token>
<token name="T_SEMICOLON">;</token>
</line>
<line no="36"/>
<line no="37">
<token name="T_CLOSE_CURLY">}</token>
</line>
<line no="38"/>
</source>
</file>
</phpunit>

View File

@@ -9,7 +9,7 @@
<line num="7" type="stmt" count="1"/>
<line num="9" type="stmt" count="1"/>
<line num="10" type="stmt" count="0"/>
<line num="11" type="method" name="anonymous function" complexity="1" crap="1" count="1"/>
<line num="11" type="method" name="anonymousFunction:11#41" complexity="1" crap="1" count="1"/>
<line num="12" type="stmt" count="1"/>
<line num="13" type="stmt" count="1"/>
<line num="14" type="stmt" count="1"/>

Some files were not shown because too many files have changed in this diff Show More