PageRenderTime 25ms CodeModel.GetById 20ms RepoModel.GetById 0ms app.codeStats 1ms

/public_html/vendor/phpunit/php-code-coverage/PHP/CodeCoverage/Util.php

https://bitbucket.org/rybadour/todo_list_site
PHP | 268 lines | 157 code | 35 blank | 76 comment | 43 complexity | 89d1b82446e5234955de5fa3a7978d8d MD5 | raw file
  1. <?php
  2. /**
  3. * PHP_CodeCoverage
  4. *
  5. * Copyright (c) 2009-2012, Sebastian Bergmann <sb@sebastian-bergmann.de>.
  6. * All rights reserved.
  7. *
  8. * Redistribution and use in source and binary forms, with or without
  9. * modification, are permitted provided that the following conditions
  10. * are met:
  11. *
  12. * * Redistributions of source code must retain the above copyright
  13. * notice, this list of conditions and the following disclaimer.
  14. *
  15. * * Redistributions in binary form must reproduce the above copyright
  16. * notice, this list of conditions and the following disclaimer in
  17. * the documentation and/or other materials provided with the
  18. * distribution.
  19. *
  20. * * Neither the name of Sebastian Bergmann nor the names of his
  21. * contributors may be used to endorse or promote products derived
  22. * from this software without specific prior written permission.
  23. *
  24. * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  25. * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  26. * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
  27. * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
  28. * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
  29. * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
  30. * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
  31. * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
  32. * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  33. * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
  34. * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
  35. * POSSIBILITY OF SUCH DAMAGE.
  36. *
  37. * @category PHP
  38. * @package CodeCoverage
  39. * @author Sebastian Bergmann <sb@sebastian-bergmann.de>
  40. * @copyright 2009-2012 Sebastian Bergmann <sb@sebastian-bergmann.de>
  41. * @license http://www.opensource.org/licenses/BSD-3-Clause The BSD 3-Clause License
  42. * @link http://github.com/sebastianbergmann/php-code-coverage
  43. * @since File available since Release 1.0.0
  44. */
  45. /**
  46. * Utility methods.
  47. *
  48. * @category PHP
  49. * @package CodeCoverage
  50. * @author Sebastian Bergmann <sb@sebastian-bergmann.de>
  51. * @copyright 2009-2012 Sebastian Bergmann <sb@sebastian-bergmann.de>
  52. * @license http://www.opensource.org/licenses/BSD-3-Clause The BSD 3-Clause License
  53. * @link http://github.com/sebastianbergmann/php-code-coverage
  54. * @since Class available since Release 1.0.0
  55. */
  56. class PHP_CodeCoverage_Util
  57. {
  58. /**
  59. * @var array
  60. */
  61. protected static $ignoredLines = array();
  62. /**
  63. * @var array
  64. */
  65. protected static $ids = array();
  66. /**
  67. * Returns the lines of a source file that should be ignored.
  68. *
  69. * @param string $filename
  70. * @param boolean $cacheTokens
  71. * @return array
  72. * @throws PHP_CodeCoverage_Exception
  73. */
  74. public static function getLinesToBeIgnored($filename, $cacheTokens = TRUE)
  75. {
  76. if (!is_string($filename)) {
  77. throw PHP_CodeCoverage_Util_InvalidArgumentHelper::factory(
  78. 1, 'string'
  79. );
  80. }
  81. if (!is_bool($cacheTokens)) {
  82. throw PHP_CodeCoverage_Util_InvalidArgumentHelper::factory(
  83. 2, 'boolean'
  84. );
  85. }
  86. if (!isset(self::$ignoredLines[$filename])) {
  87. self::$ignoredLines[$filename] = array();
  88. $ignore = FALSE;
  89. $stop = FALSE;
  90. $lines = file($filename);
  91. foreach ($lines as $index => $line) {
  92. if (!trim($line)) {
  93. self::$ignoredLines[$filename][$index+1] = TRUE;
  94. }
  95. }
  96. if ($cacheTokens) {
  97. $tokens = PHP_Token_Stream_CachingFactory::get($filename);
  98. } else {
  99. $tokens = new PHP_Token_Stream($filename);
  100. }
  101. $classes = array_merge($tokens->getClasses(), $tokens->getTraits());
  102. $tokens = $tokens->tokens();
  103. foreach ($tokens as $token) {
  104. switch (get_class($token)) {
  105. case 'PHP_Token_COMMENT':
  106. case 'PHP_Token_DOC_COMMENT': {
  107. $count = substr_count($token, "\n");
  108. $line = $token->getLine();
  109. for ($i = $line; $i < $line + $count; $i++) {
  110. self::$ignoredLines[$filename][$i] = TRUE;
  111. }
  112. if ($token instanceof PHP_Token_DOC_COMMENT) {
  113. // Workaround for the fact the DOC_COMMENT token
  114. // does not include the final \n character in its
  115. // text.
  116. if (substr(trim($lines[$i-1]), -2) == '*/') {
  117. self::$ignoredLines[$filename][$i] = TRUE;
  118. }
  119. break;
  120. }
  121. $_token = trim($token);
  122. if ($_token == '// @codeCoverageIgnore' ||
  123. $_token == '//@codeCoverageIgnore') {
  124. $ignore = TRUE;
  125. $stop = TRUE;
  126. }
  127. else if ($_token == '// @codeCoverageIgnoreStart' ||
  128. $_token == '//@codeCoverageIgnoreStart') {
  129. $ignore = TRUE;
  130. }
  131. else if ($_token == '// @codeCoverageIgnoreEnd' ||
  132. $_token == '//@codeCoverageIgnoreEnd') {
  133. $stop = TRUE;
  134. }
  135. }
  136. break;
  137. case 'PHP_Token_INTERFACE':
  138. case 'PHP_Token_TRAIT':
  139. case 'PHP_Token_CLASS':
  140. case 'PHP_Token_FUNCTION': {
  141. $docblock = $token->getDocblock();
  142. if (strpos($docblock, '@codeCoverageIgnore')) {
  143. $endLine = $token->getEndLine();
  144. for ($i = $token->getLine(); $i <= $endLine; $i++) {
  145. self::$ignoredLines[$filename][$i] = TRUE;
  146. }
  147. }
  148. else if ($token instanceof PHP_Token_INTERFACE ||
  149. $token instanceof PHP_Token_TRAIT ||
  150. $token instanceof PHP_Token_CLASS) {
  151. if (empty($classes[$token->getName()]['methods'])) {
  152. for ($i = $token->getLine();
  153. $i <= $token->getEndLine();
  154. $i++) {
  155. self::$ignoredLines[$filename][$i] = TRUE;
  156. }
  157. } else {
  158. $firstMethod = array_shift(
  159. $classes[$token->getName()]['methods']
  160. );
  161. $lastMethod = array_pop(
  162. $classes[$token->getName()]['methods']
  163. );
  164. if ($lastMethod === NULL) {
  165. $lastMethod = $firstMethod;
  166. }
  167. for ($i = $token->getLine();
  168. $i < $firstMethod['startLine'];
  169. $i++) {
  170. self::$ignoredLines[$filename][$i] = TRUE;
  171. }
  172. for ($i = $token->getEndLine();
  173. $i > $lastMethod['endLine'];
  174. $i--) {
  175. self::$ignoredLines[$filename][$i] = TRUE;
  176. }
  177. }
  178. }
  179. }
  180. break;
  181. case 'PHP_Token_INTERFACE': {
  182. $endLine = $token->getEndLine();
  183. for ($i = $token->getLine(); $i <= $endLine; $i++) {
  184. self::$ignoredLines[$filename][$i] = TRUE;
  185. }
  186. }
  187. break;
  188. case 'PHP_Token_NAMESPACE': {
  189. self::$ignoredLines[$filename][$token->getEndLine()] = TRUE;
  190. } // Intentional fallthrough
  191. case 'PHP_Token_OPEN_TAG':
  192. case 'PHP_Token_CLOSE_TAG':
  193. case 'PHP_Token_USE': {
  194. self::$ignoredLines[$filename][$token->getLine()] = TRUE;
  195. }
  196. break;
  197. }
  198. if ($ignore) {
  199. self::$ignoredLines[$filename][$token->getLine()] = TRUE;
  200. if ($stop) {
  201. $ignore = FALSE;
  202. $stop = FALSE;
  203. }
  204. }
  205. }
  206. }
  207. return self::$ignoredLines[$filename];
  208. }
  209. /**
  210. * @param float $a
  211. * @param float $b
  212. * @return float ($a / $b) * 100
  213. */
  214. public static function percent($a, $b, $asString = FALSE, $fixedWidth = FALSE)
  215. {
  216. if ($asString && $b == 0) {
  217. return '';
  218. }
  219. if ($b > 0) {
  220. $percent = ($a / $b) * 100;
  221. } else {
  222. $percent = 100;
  223. }
  224. if ($asString) {
  225. if ($fixedWidth) {
  226. return sprintf('%6.2F%%', $percent);
  227. }
  228. return sprintf('%01.2F%%', $percent);
  229. } else {
  230. return $percent;
  231. }
  232. }
  233. }