Unit_test.php 8.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384
  1. <?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');
  2. /**
  3. * CodeIgniter
  4. *
  5. * An open source application development framework for PHP 5.1.6 or newer
  6. *
  7. * @package CodeIgniter
  8. * @author EllisLab Dev Team
  9. * @copyright Copyright (c) 2008 - 2014, EllisLab, Inc.
  10. * @copyright Copyright (c) 2014 - 2015, British Columbia Institute of Technology (http://bcit.ca/)
  11. * @license http://codeigniter.com/user_guide/license.html
  12. * @link http://codeigniter.com
  13. * @since Version 1.3.1
  14. * @filesource
  15. */
  16. // ------------------------------------------------------------------------
  17. /**
  18. * Unit Testing Class
  19. *
  20. * Simple testing class
  21. *
  22. * @package CodeIgniter
  23. * @subpackage Libraries
  24. * @category UnitTesting
  25. * @author EllisLab Dev Team
  26. * @link http://codeigniter.com/user_guide/libraries/uri.html
  27. */
  28. class CI_Unit_test {
  29. var $active = TRUE;
  30. var $results = array();
  31. var $strict = FALSE;
  32. var $_template = NULL;
  33. var $_template_rows = NULL;
  34. var $_test_items_visible = array();
  35. public function __construct()
  36. {
  37. // These are the default items visible when a test is run.
  38. $this->_test_items_visible = array (
  39. 'test_name',
  40. 'test_datatype',
  41. 'res_datatype',
  42. 'result',
  43. 'file',
  44. 'line',
  45. 'notes'
  46. );
  47. log_message('debug', "Unit Testing Class Initialized");
  48. }
  49. // --------------------------------------------------------------------
  50. /**
  51. * Run the tests
  52. *
  53. * Runs the supplied tests
  54. *
  55. * @access public
  56. * @param array
  57. * @return void
  58. */
  59. function set_test_items($items = array())
  60. {
  61. if ( ! empty($items) AND is_array($items))
  62. {
  63. $this->_test_items_visible = $items;
  64. }
  65. }
  66. // --------------------------------------------------------------------
  67. /**
  68. * Run the tests
  69. *
  70. * Runs the supplied tests
  71. *
  72. * @access public
  73. * @param mixed
  74. * @param mixed
  75. * @param string
  76. * @return string
  77. */
  78. function run($test, $expected = TRUE, $test_name = 'undefined', $notes = '')
  79. {
  80. if ($this->active == FALSE)
  81. {
  82. return FALSE;
  83. }
  84. if (in_array($expected, array('is_object', 'is_string', 'is_bool', 'is_true', 'is_false', 'is_int', 'is_numeric', 'is_float', 'is_double', 'is_array', 'is_null'), TRUE))
  85. {
  86. $expected = str_replace('is_float', 'is_double', $expected);
  87. $result = ($expected($test)) ? TRUE : FALSE;
  88. $extype = str_replace(array('true', 'false'), 'bool', str_replace('is_', '', $expected));
  89. }
  90. else
  91. {
  92. if ($this->strict == TRUE)
  93. $result = ($test === $expected) ? TRUE : FALSE;
  94. else
  95. $result = ($test == $expected) ? TRUE : FALSE;
  96. $extype = gettype($expected);
  97. }
  98. $back = $this->_backtrace();
  99. $report[] = array (
  100. 'test_name' => $test_name,
  101. 'test_datatype' => gettype($test),
  102. 'res_datatype' => $extype,
  103. 'result' => ($result === TRUE) ? 'passed' : 'failed',
  104. 'file' => $back['file'],
  105. 'line' => $back['line'],
  106. 'notes' => $notes
  107. );
  108. $this->results[] = $report;
  109. return($this->report($this->result($report)));
  110. }
  111. // --------------------------------------------------------------------
  112. /**
  113. * Generate a report
  114. *
  115. * Displays a table with the test data
  116. *
  117. * @access public
  118. * @return string
  119. */
  120. function report($result = array())
  121. {
  122. if (count($result) == 0)
  123. {
  124. $result = $this->result();
  125. }
  126. $CI =& get_instance();
  127. $CI->load->language('unit_test');
  128. $this->_parse_template();
  129. $r = '';
  130. foreach ($result as $res)
  131. {
  132. $table = '';
  133. foreach ($res as $key => $val)
  134. {
  135. if ($key == $CI->lang->line('ut_result'))
  136. {
  137. if ($val == $CI->lang->line('ut_passed'))
  138. {
  139. $val = '<span style="color: #0C0;">'.$val.'</span>';
  140. }
  141. elseif ($val == $CI->lang->line('ut_failed'))
  142. {
  143. $val = '<span style="color: #C00;">'.$val.'</span>';
  144. }
  145. }
  146. $temp = $this->_template_rows;
  147. $temp = str_replace('{item}', $key, $temp);
  148. $temp = str_replace('{result}', $val, $temp);
  149. $table .= $temp;
  150. }
  151. $r .= str_replace('{rows}', $table, $this->_template);
  152. }
  153. return $r;
  154. }
  155. // --------------------------------------------------------------------
  156. /**
  157. * Use strict comparison
  158. *
  159. * Causes the evaluation to use === rather than ==
  160. *
  161. * @access public
  162. * @param bool
  163. * @return null
  164. */
  165. function use_strict($state = TRUE)
  166. {
  167. $this->strict = ($state == FALSE) ? FALSE : TRUE;
  168. }
  169. // --------------------------------------------------------------------
  170. /**
  171. * Make Unit testing active
  172. *
  173. * Enables/disables unit testing
  174. *
  175. * @access public
  176. * @param bool
  177. * @return null
  178. */
  179. function active($state = TRUE)
  180. {
  181. $this->active = ($state == FALSE) ? FALSE : TRUE;
  182. }
  183. // --------------------------------------------------------------------
  184. /**
  185. * Result Array
  186. *
  187. * Returns the raw result data
  188. *
  189. * @access public
  190. * @return array
  191. */
  192. function result($results = array())
  193. {
  194. $CI =& get_instance();
  195. $CI->load->language('unit_test');
  196. if (count($results) == 0)
  197. {
  198. $results = $this->results;
  199. }
  200. $retval = array();
  201. foreach ($results as $result)
  202. {
  203. $temp = array();
  204. foreach ($result as $key => $val)
  205. {
  206. if ( ! in_array($key, $this->_test_items_visible))
  207. {
  208. continue;
  209. }
  210. if (is_array($val))
  211. {
  212. foreach ($val as $k => $v)
  213. {
  214. if (FALSE !== ($line = $CI->lang->line(strtolower('ut_'.$v))))
  215. {
  216. $v = $line;
  217. }
  218. $temp[$CI->lang->line('ut_'.$k)] = $v;
  219. }
  220. }
  221. else
  222. {
  223. if (FALSE !== ($line = $CI->lang->line(strtolower('ut_'.$val))))
  224. {
  225. $val = $line;
  226. }
  227. $temp[$CI->lang->line('ut_'.$key)] = $val;
  228. }
  229. }
  230. $retval[] = $temp;
  231. }
  232. return $retval;
  233. }
  234. // --------------------------------------------------------------------
  235. /**
  236. * Set the template
  237. *
  238. * This lets us set the template to be used to display results
  239. *
  240. * @access public
  241. * @param string
  242. * @return void
  243. */
  244. function set_template($template)
  245. {
  246. $this->_template = $template;
  247. }
  248. // --------------------------------------------------------------------
  249. /**
  250. * Generate a backtrace
  251. *
  252. * This lets us show file names and line numbers
  253. *
  254. * @access private
  255. * @return array
  256. */
  257. function _backtrace()
  258. {
  259. if (function_exists('debug_backtrace'))
  260. {
  261. $back = debug_backtrace();
  262. $file = ( ! isset($back['1']['file'])) ? '' : $back['1']['file'];
  263. $line = ( ! isset($back['1']['line'])) ? '' : $back['1']['line'];
  264. return array('file' => $file, 'line' => $line);
  265. }
  266. return array('file' => 'Unknown', 'line' => 'Unknown');
  267. }
  268. // --------------------------------------------------------------------
  269. /**
  270. * Get Default Template
  271. *
  272. * @access private
  273. * @return string
  274. */
  275. function _default_template()
  276. {
  277. $this->_template = "\n".'<table style="width:100%; font-size:small; margin:10px 0; border-collapse:collapse; border:1px solid #CCC;">';
  278. $this->_template .= '{rows}';
  279. $this->_template .= "\n".'</table>';
  280. $this->_template_rows = "\n\t".'<tr>';
  281. $this->_template_rows .= "\n\t\t".'<th style="text-align: left; border-bottom:1px solid #CCC;">{item}</th>';
  282. $this->_template_rows .= "\n\t\t".'<td style="border-bottom:1px solid #CCC;">{result}</td>';
  283. $this->_template_rows .= "\n\t".'</tr>';
  284. }
  285. // --------------------------------------------------------------------
  286. /**
  287. * Parse Template
  288. *
  289. * Harvests the data within the template {pseudo-variables}
  290. *
  291. * @access private
  292. * @return void
  293. */
  294. function _parse_template()
  295. {
  296. if ( ! is_null($this->_template_rows))
  297. {
  298. return;
  299. }
  300. if (is_null($this->_template))
  301. {
  302. $this->_default_template();
  303. return;
  304. }
  305. if ( ! preg_match("/\{rows\}(.*?)\{\/rows\}/si", $this->_template, $match))
  306. {
  307. $this->_default_template();
  308. return;
  309. }
  310. $this->_template_rows = $match['1'];
  311. $this->_template = str_replace($match['0'], '{rows}', $this->_template);
  312. }
  313. }
  314. // END Unit_test Class
  315. /**
  316. * Helper functions to test boolean true/false
  317. *
  318. *
  319. * @access private
  320. * @return bool
  321. */
  322. function is_true($test)
  323. {
  324. return (is_bool($test) AND $test === TRUE) ? TRUE : FALSE;
  325. }
  326. function is_false($test)
  327. {
  328. return (is_bool($test) AND $test === FALSE) ? TRUE : FALSE;
  329. }
  330. /* End of file Unit_test.php */
  331. /* Location: ./system/libraries/Unit_test.php */