PageRenderTime 80ms CodeModel.GetById 40ms RepoModel.GetById 1ms app.codeStats 1ms

/lib/tests/moodlelib_test.php

https://github.com/dcai/moodle
PHP | 4690 lines | 3410 code | 542 blank | 738 comment | 18 complexity | 7f786953036f6286f8245824fb854600 MD5 | raw file
Possible License(s): LGPL-2.1, BSD-3-Clause, MIT, GPL-3.0, Apache-2.0

Large files files are truncated, but you can click here to view the full file

  1. <?php
  2. // This file is part of Moodle - http://moodle.org/
  3. //
  4. // Moodle is free software: you can redistribute it and/or modify
  5. // it under the terms of the GNU General Public License as published by
  6. // the Free Software Foundation, either version 3 of the License, or
  7. // (at your option) any later version.
  8. //
  9. // Moodle is distributed in the hope that it will be useful,
  10. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. // GNU General Public License for more details.
  13. //
  14. // You should have received a copy of the GNU General Public License
  15. // along with Moodle. If not, see <http://www.gnu.org/licenses/>.
  16. /**
  17. * Unit tests for (some of) ../moodlelib.php.
  18. *
  19. * @package core
  20. * @category phpunit
  21. * @copyright &copy; 2006 The Open University
  22. * @author T.J.Hunt@open.ac.uk
  23. * @author nicolas@moodle.com
  24. */
  25. defined('MOODLE_INTERNAL') || die();
  26. class core_moodlelib_testcase extends advanced_testcase {
  27. public static $includecoverage = array('lib/moodlelib.php');
  28. /**
  29. * Define a local decimal separator.
  30. *
  31. * It is not possible to directly change the result of get_string in
  32. * a unit test. Instead, we create a language pack for language 'xx' in
  33. * dataroot and make langconfig.php with the string we need to change.
  34. * The default example separator used here is 'X'; on PHP 5.3 and before this
  35. * must be a single byte character due to PHP bug/limitation in
  36. * number_format, so you can't use UTF-8 characters.
  37. *
  38. * @param string $decsep Separator character. Defaults to `'X'`.
  39. */
  40. protected function define_local_decimal_separator(string $decsep = 'X') {
  41. global $SESSION, $CFG;
  42. $SESSION->lang = 'xx';
  43. $langconfig = "<?php\n\$string['decsep'] = '$decsep';";
  44. $langfolder = $CFG->dataroot . '/lang/xx';
  45. check_dir_exists($langfolder);
  46. file_put_contents($langfolder . '/langconfig.php', $langconfig);
  47. // Ensure the new value is picked up and not taken from the cache.
  48. $stringmanager = get_string_manager();
  49. $stringmanager->reset_caches(true);
  50. }
  51. public function test_cleanremoteaddr() {
  52. // IPv4.
  53. $this->assertNull(cleanremoteaddr('1023.121.234.1'));
  54. $this->assertSame('123.121.234.1', cleanremoteaddr('123.121.234.01 '));
  55. // IPv6.
  56. $this->assertNull(cleanremoteaddr('0:0:0:0:0:0:0:0:0'));
  57. $this->assertNull(cleanremoteaddr('0:0:0:0:0:0:0:abh'));
  58. $this->assertNull(cleanremoteaddr('0:0:0:::0:0:1'));
  59. $this->assertSame('::', cleanremoteaddr('0:0:0:0:0:0:0:0', true));
  60. $this->assertSame('::1:1', cleanremoteaddr('0:0:0:0:0:0:1:1', true));
  61. $this->assertSame('abcd:ef::', cleanremoteaddr('abcd:00ef:0:0:0:0:0:0', true));
  62. $this->assertSame('1::1', cleanremoteaddr('1:0:0:0:0:0:0:1', true));
  63. $this->assertSame('0:0:0:0:0:0:10:1', cleanremoteaddr('::10:1', false));
  64. $this->assertSame('1:1:0:0:0:0:0:0', cleanremoteaddr('01:1::', false));
  65. $this->assertSame('10:0:0:0:0:0:0:10', cleanremoteaddr('10::10', false));
  66. $this->assertSame('::ffff:c0a8:11', cleanremoteaddr('::ffff:192.168.1.1', true));
  67. }
  68. public function test_address_in_subnet() {
  69. // 1: xxx.xxx.xxx.xxx/nn or xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:xxxx/nnn (number of bits in net mask).
  70. $this->assertTrue(address_in_subnet('123.121.234.1', '123.121.234.1/32'));
  71. $this->assertFalse(address_in_subnet('123.121.23.1', '123.121.23.0/32'));
  72. $this->assertTrue(address_in_subnet('10.10.10.100', '123.121.23.45/0'));
  73. $this->assertTrue(address_in_subnet('123.121.234.1', '123.121.234.0/24'));
  74. $this->assertFalse(address_in_subnet('123.121.34.1', '123.121.234.0/24'));
  75. $this->assertTrue(address_in_subnet('123.121.234.1', '123.121.234.0/30'));
  76. $this->assertFalse(address_in_subnet('123.121.23.8', '123.121.23.0/30'));
  77. $this->assertTrue(address_in_subnet('baba:baba::baba', 'baba:baba::baba/128'));
  78. $this->assertFalse(address_in_subnet('bab:baba::baba', 'bab:baba::cece/128'));
  79. $this->assertTrue(address_in_subnet('baba:baba::baba', 'cece:cece::cece/0'));
  80. $this->assertTrue(address_in_subnet('baba:baba::baba', 'baba:baba::baba/128'));
  81. $this->assertTrue(address_in_subnet('baba:baba::00ba', 'baba:baba::/120'));
  82. $this->assertFalse(address_in_subnet('baba:baba::aba', 'baba:baba::/120'));
  83. $this->assertTrue(address_in_subnet('baba::baba:00ba', 'baba::baba:0/112'));
  84. $this->assertFalse(address_in_subnet('baba::aba:00ba', 'baba::baba:0/112'));
  85. $this->assertFalse(address_in_subnet('aba::baba:0000', 'baba::baba:0/112'));
  86. // Fixed input.
  87. $this->assertTrue(address_in_subnet('123.121.23.1 ', ' 123.121.23.0 / 24'));
  88. $this->assertTrue(address_in_subnet('::ffff:10.1.1.1', ' 0:0:0:000:0:ffff:a1:10 / 126'));
  89. // Incorrect input.
  90. $this->assertFalse(address_in_subnet('123.121.234.1', '123.121.234.1/-2'));
  91. $this->assertFalse(address_in_subnet('123.121.234.1', '123.121.234.1/64'));
  92. $this->assertFalse(address_in_subnet('123.121.234.x', '123.121.234.1/24'));
  93. $this->assertFalse(address_in_subnet('123.121.234.0', '123.121.234.xx/24'));
  94. $this->assertFalse(address_in_subnet('123.121.234.1', '123.121.234.1/xx0'));
  95. $this->assertFalse(address_in_subnet('::1', '::aa:0/xx0'));
  96. $this->assertFalse(address_in_subnet('::1', '::aa:0/-5'));
  97. $this->assertFalse(address_in_subnet('::1', '::aa:0/130'));
  98. $this->assertFalse(address_in_subnet('x:1', '::aa:0/130'));
  99. $this->assertFalse(address_in_subnet('::1', '::ax:0/130'));
  100. // 2: xxx.xxx.xxx.xxx-yyy or xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:xxxx::xxxx-yyyy (a range of IP addresses in the last group).
  101. $this->assertTrue(address_in_subnet('123.121.234.12', '123.121.234.12-14'));
  102. $this->assertTrue(address_in_subnet('123.121.234.13', '123.121.234.12-14'));
  103. $this->assertTrue(address_in_subnet('123.121.234.14', '123.121.234.12-14'));
  104. $this->assertFalse(address_in_subnet('123.121.234.1', '123.121.234.12-14'));
  105. $this->assertFalse(address_in_subnet('123.121.234.20', '123.121.234.12-14'));
  106. $this->assertFalse(address_in_subnet('123.121.23.12', '123.121.234.12-14'));
  107. $this->assertFalse(address_in_subnet('123.12.234.12', '123.121.234.12-14'));
  108. $this->assertTrue(address_in_subnet('baba:baba::baba', 'baba:baba::baba-babe'));
  109. $this->assertTrue(address_in_subnet('baba:baba::babc', 'baba:baba::baba-babe'));
  110. $this->assertTrue(address_in_subnet('baba:baba::babe', 'baba:baba::baba-babe'));
  111. $this->assertFalse(address_in_subnet('bab:baba::bab0', 'bab:baba::baba-babe'));
  112. $this->assertFalse(address_in_subnet('bab:baba::babf', 'bab:baba::baba-babe'));
  113. $this->assertFalse(address_in_subnet('bab:baba::bfbe', 'bab:baba::baba-babe'));
  114. $this->assertFalse(address_in_subnet('bfb:baba::babe', 'bab:baba::baba-babe'));
  115. // Fixed input.
  116. $this->assertTrue(address_in_subnet('123.121.234.12', '123.121.234.12 - 14 '));
  117. $this->assertTrue(address_in_subnet('bab:baba::babe', 'bab:baba::baba - babe '));
  118. // Incorrect input.
  119. $this->assertFalse(address_in_subnet('123.121.234.12', '123.121.234.12-234.14'));
  120. $this->assertFalse(address_in_subnet('123.121.234.12', '123.121.234.12-256'));
  121. $this->assertFalse(address_in_subnet('123.121.234.12', '123.121.234.12--256'));
  122. // 3: xxx.xxx or xxx.xxx. or xxx:xxx:xxxx or xxx:xxx:xxxx. (incomplete address, a bit non-technical ;-).
  123. $this->assertTrue(address_in_subnet('123.121.234.12', '123.121.234.12'));
  124. $this->assertFalse(address_in_subnet('123.121.23.12', '123.121.23.13'));
  125. $this->assertTrue(address_in_subnet('123.121.234.12', '123.121.234.'));
  126. $this->assertTrue(address_in_subnet('123.121.234.12', '123.121.234'));
  127. $this->assertTrue(address_in_subnet('123.121.234.12', '123.121'));
  128. $this->assertTrue(address_in_subnet('123.121.234.12', '123'));
  129. $this->assertFalse(address_in_subnet('123.121.234.1', '12.121.234.'));
  130. $this->assertFalse(address_in_subnet('123.121.234.1', '12.121.234'));
  131. $this->assertTrue(address_in_subnet('baba:baba::bab', 'baba:baba::bab'));
  132. $this->assertFalse(address_in_subnet('baba:baba::ba', 'baba:baba::bc'));
  133. $this->assertTrue(address_in_subnet('baba:baba::bab', 'baba:baba'));
  134. $this->assertTrue(address_in_subnet('baba:baba::bab', 'baba:'));
  135. $this->assertFalse(address_in_subnet('bab:baba::bab', 'baba:'));
  136. // Multiple subnets.
  137. $this->assertTrue(address_in_subnet('123.121.234.12', '::1/64, 124., 123.121.234.10-30'));
  138. $this->assertTrue(address_in_subnet('124.121.234.12', '::1/64, 124., 123.121.234.10-30'));
  139. $this->assertTrue(address_in_subnet('::2', '::1/64, 124., 123.121.234.10-30'));
  140. $this->assertFalse(address_in_subnet('12.121.234.12', '::1/64, 124., 123.121.234.10-30'));
  141. // Other incorrect input.
  142. $this->assertFalse(address_in_subnet('123.123.123.123', ''));
  143. }
  144. public function test_fix_utf8() {
  145. // Make sure valid data including other types is not changed.
  146. $this->assertSame(null, fix_utf8(null));
  147. $this->assertSame(1, fix_utf8(1));
  148. $this->assertSame(1.1, fix_utf8(1.1));
  149. $this->assertSame(true, fix_utf8(true));
  150. $this->assertSame('', fix_utf8(''));
  151. $this->assertSame('abc', fix_utf8('abc'));
  152. $array = array('do', 're', 'mi');
  153. $this->assertSame($array, fix_utf8($array));
  154. $object = new stdClass();
  155. $object->a = 'aa';
  156. $object->b = 'bb';
  157. $this->assertEquals($object, fix_utf8($object));
  158. // valid utf8 string
  159. $this->assertSame("žlutý koníček přeskočil potůček \n\t\r", fix_utf8("žlutý koníček přeskočil potůček \n\t\r\0"));
  160. // Invalid utf8 string.
  161. $this->assertSame('aš', fix_utf8('a'.chr(130).'š'), 'This fails with buggy iconv() when mbstring extenstion is not available as fallback.');
  162. }
  163. public function test_optional_param() {
  164. global $CFG;
  165. $_POST['username'] = 'post_user';
  166. $_GET['username'] = 'get_user';
  167. $this->assertSame($_POST['username'], optional_param('username', 'default_user', PARAM_RAW));
  168. unset($_POST['username']);
  169. $this->assertSame($_GET['username'], optional_param('username', 'default_user', PARAM_RAW));
  170. unset($_GET['username']);
  171. $this->assertSame('default_user', optional_param('username', 'default_user', PARAM_RAW));
  172. // Make sure exception is triggered when some params are missing, hide error notices here - new in 2.2.
  173. $_POST['username'] = 'post_user';
  174. try {
  175. optional_param('username', 'default_user', null);
  176. $this->fail('coding_exception expected');
  177. } catch (moodle_exception $ex) {
  178. $this->assertInstanceOf('coding_exception', $ex);
  179. }
  180. try {
  181. @optional_param('username', 'default_user');
  182. $this->fail('coding_exception expected');
  183. } catch (moodle_exception $ex) {
  184. $this->assertInstanceOf('coding_exception', $ex);
  185. } catch (Error $error) {
  186. // PHP 7.1 throws Error even earlier.
  187. $this->assertRegExp('/Too few arguments to function/', $error->getMessage());
  188. }
  189. try {
  190. @optional_param('username');
  191. $this->fail('coding_exception expected');
  192. } catch (moodle_exception $ex) {
  193. $this->assertInstanceOf('coding_exception', $ex);
  194. } catch (Error $error) {
  195. // PHP 7.1 throws Error even earlier.
  196. $this->assertRegExp('/Too few arguments to function/', $error->getMessage());
  197. }
  198. try {
  199. optional_param('', 'default_user', PARAM_RAW);
  200. $this->fail('coding_exception expected');
  201. } catch (moodle_exception $ex) {
  202. $this->assertInstanceOf('coding_exception', $ex);
  203. }
  204. // Make sure warning is displayed if array submitted - TODO: throw exception in Moodle 2.3.
  205. $_POST['username'] = array('a'=>'a');
  206. $this->assertSame($_POST['username'], optional_param('username', 'default_user', PARAM_RAW));
  207. $this->assertDebuggingCalled();
  208. }
  209. public function test_optional_param_array() {
  210. global $CFG;
  211. $_POST['username'] = array('a'=>'post_user');
  212. $_GET['username'] = array('a'=>'get_user');
  213. $this->assertSame($_POST['username'], optional_param_array('username', array('a'=>'default_user'), PARAM_RAW));
  214. unset($_POST['username']);
  215. $this->assertSame($_GET['username'], optional_param_array('username', array('a'=>'default_user'), PARAM_RAW));
  216. unset($_GET['username']);
  217. $this->assertSame(array('a'=>'default_user'), optional_param_array('username', array('a'=>'default_user'), PARAM_RAW));
  218. // Make sure exception is triggered when some params are missing, hide error notices here - new in 2.2.
  219. $_POST['username'] = array('a'=>'post_user');
  220. try {
  221. optional_param_array('username', array('a'=>'default_user'), null);
  222. $this->fail('coding_exception expected');
  223. } catch (moodle_exception $ex) {
  224. $this->assertInstanceOf('coding_exception', $ex);
  225. }
  226. try {
  227. @optional_param_array('username', array('a'=>'default_user'));
  228. $this->fail('coding_exception expected');
  229. } catch (moodle_exception $ex) {
  230. $this->assertInstanceOf('coding_exception', $ex);
  231. } catch (Error $error) {
  232. // PHP 7.1 throws Error even earlier.
  233. $this->assertRegExp('/Too few arguments to function/', $error->getMessage());
  234. }
  235. try {
  236. @optional_param_array('username');
  237. $this->fail('coding_exception expected');
  238. } catch (moodle_exception $ex) {
  239. $this->assertInstanceOf('coding_exception', $ex);
  240. } catch (Error $error) {
  241. // PHP 7.1 throws Error even earlier.
  242. $this->assertRegExp('/Too few arguments to function/', $error->getMessage());
  243. }
  244. try {
  245. optional_param_array('', array('a'=>'default_user'), PARAM_RAW);
  246. $this->fail('coding_exception expected');
  247. } catch (moodle_exception $ex) {
  248. $this->assertInstanceOf('coding_exception', $ex);
  249. }
  250. // Do not allow nested arrays.
  251. try {
  252. $_POST['username'] = array('a'=>array('b'=>'post_user'));
  253. optional_param_array('username', array('a'=>'default_user'), PARAM_RAW);
  254. $this->fail('coding_exception expected');
  255. } catch (coding_exception $ex) {
  256. $this->assertTrue(true);
  257. }
  258. // Do not allow non-arrays.
  259. $_POST['username'] = 'post_user';
  260. $this->assertSame(array('a'=>'default_user'), optional_param_array('username', array('a'=>'default_user'), PARAM_RAW));
  261. $this->assertDebuggingCalled();
  262. // Make sure array keys are sanitised.
  263. $_POST['username'] = array('abc123_;-/*-+ '=>'arrggh', 'a1_-'=>'post_user');
  264. $this->assertSame(array('a1_-'=>'post_user'), optional_param_array('username', array(), PARAM_RAW));
  265. $this->assertDebuggingCalled();
  266. }
  267. public function test_required_param() {
  268. $_POST['username'] = 'post_user';
  269. $_GET['username'] = 'get_user';
  270. $this->assertSame('post_user', required_param('username', PARAM_RAW));
  271. unset($_POST['username']);
  272. $this->assertSame('get_user', required_param('username', PARAM_RAW));
  273. unset($_GET['username']);
  274. try {
  275. $this->assertSame('default_user', required_param('username', PARAM_RAW));
  276. $this->fail('moodle_exception expected');
  277. } catch (moodle_exception $ex) {
  278. $this->assertInstanceOf('moodle_exception', $ex);
  279. }
  280. // Make sure exception is triggered when some params are missing, hide error notices here - new in 2.2.
  281. $_POST['username'] = 'post_user';
  282. try {
  283. @required_param('username');
  284. $this->fail('coding_exception expected');
  285. } catch (moodle_exception $ex) {
  286. $this->assertInstanceOf('coding_exception', $ex);
  287. } catch (Error $error) {
  288. // PHP 7.1 throws Error even earlier.
  289. $this->assertRegExp('/Too few arguments to function/', $error->getMessage());
  290. }
  291. try {
  292. required_param('username', '');
  293. $this->fail('coding_exception expected');
  294. } catch (moodle_exception $ex) {
  295. $this->assertInstanceOf('coding_exception', $ex);
  296. }
  297. try {
  298. required_param('', PARAM_RAW);
  299. $this->fail('coding_exception expected');
  300. } catch (moodle_exception $ex) {
  301. $this->assertInstanceOf('coding_exception', $ex);
  302. }
  303. // Make sure warning is displayed if array submitted - TODO: throw exception in Moodle 2.3.
  304. $_POST['username'] = array('a'=>'a');
  305. $this->assertSame($_POST['username'], required_param('username', PARAM_RAW));
  306. $this->assertDebuggingCalled();
  307. }
  308. public function test_required_param_array() {
  309. global $CFG;
  310. $_POST['username'] = array('a'=>'post_user');
  311. $_GET['username'] = array('a'=>'get_user');
  312. $this->assertSame($_POST['username'], required_param_array('username', PARAM_RAW));
  313. unset($_POST['username']);
  314. $this->assertSame($_GET['username'], required_param_array('username', PARAM_RAW));
  315. // Make sure exception is triggered when some params are missing, hide error notices here - new in 2.2.
  316. $_POST['username'] = array('a'=>'post_user');
  317. try {
  318. required_param_array('username', null);
  319. $this->fail('coding_exception expected');
  320. } catch (moodle_exception $ex) {
  321. $this->assertInstanceOf('coding_exception', $ex);
  322. }
  323. try {
  324. @required_param_array('username');
  325. $this->fail('coding_exception expected');
  326. } catch (moodle_exception $ex) {
  327. $this->assertInstanceOf('coding_exception', $ex);
  328. } catch (Error $error) {
  329. // PHP 7.1 throws Error.
  330. $this->assertRegExp('/Too few arguments to function/', $error->getMessage());
  331. }
  332. try {
  333. required_param_array('', PARAM_RAW);
  334. $this->fail('coding_exception expected');
  335. } catch (moodle_exception $ex) {
  336. $this->assertInstanceOf('coding_exception', $ex);
  337. }
  338. // Do not allow nested arrays.
  339. try {
  340. $_POST['username'] = array('a'=>array('b'=>'post_user'));
  341. required_param_array('username', PARAM_RAW);
  342. $this->fail('coding_exception expected');
  343. } catch (moodle_exception $ex) {
  344. $this->assertInstanceOf('coding_exception', $ex);
  345. }
  346. // Do not allow non-arrays.
  347. try {
  348. $_POST['username'] = 'post_user';
  349. required_param_array('username', PARAM_RAW);
  350. $this->fail('moodle_exception expected');
  351. } catch (moodle_exception $ex) {
  352. $this->assertInstanceOf('moodle_exception', $ex);
  353. }
  354. // Make sure array keys are sanitised.
  355. $_POST['username'] = array('abc123_;-/*-+ '=>'arrggh', 'a1_-'=>'post_user');
  356. $this->assertSame(array('a1_-'=>'post_user'), required_param_array('username', PARAM_RAW));
  357. $this->assertDebuggingCalled();
  358. }
  359. public function test_clean_param() {
  360. // Forbid objects and arrays.
  361. try {
  362. clean_param(array('x', 'y'), PARAM_RAW);
  363. $this->fail('coding_exception expected');
  364. } catch (moodle_exception $ex) {
  365. $this->assertInstanceOf('coding_exception', $ex);
  366. }
  367. try {
  368. $param = new stdClass();
  369. $param->id = 1;
  370. clean_param($param, PARAM_RAW);
  371. $this->fail('coding_exception expected');
  372. } catch (moodle_exception $ex) {
  373. $this->assertInstanceOf('coding_exception', $ex);
  374. }
  375. // Require correct type.
  376. try {
  377. clean_param('x', 'xxxxxx');
  378. $this->fail('moodle_exception expected');
  379. } catch (moodle_exception $ex) {
  380. $this->assertInstanceOf('moodle_exception', $ex);
  381. }
  382. try {
  383. @clean_param('x');
  384. $this->fail('moodle_exception expected');
  385. } catch (moodle_exception $ex) {
  386. $this->assertInstanceOf('moodle_exception', $ex);
  387. } catch (Error $error) {
  388. // PHP 7.1 throws Error even earlier.
  389. $this->assertRegExp('/Too few arguments to function/', $error->getMessage());
  390. }
  391. }
  392. public function test_clean_param_array() {
  393. $this->assertSame(array(), clean_param_array(null, PARAM_RAW));
  394. $this->assertSame(array('a', 'b'), clean_param_array(array('a', 'b'), PARAM_RAW));
  395. $this->assertSame(array('a', array('b')), clean_param_array(array('a', array('b')), PARAM_RAW, true));
  396. // Require correct type.
  397. try {
  398. clean_param_array(array('x'), 'xxxxxx');
  399. $this->fail('moodle_exception expected');
  400. } catch (moodle_exception $ex) {
  401. $this->assertInstanceOf('moodle_exception', $ex);
  402. }
  403. try {
  404. @clean_param_array(array('x'));
  405. $this->fail('moodle_exception expected');
  406. } catch (moodle_exception $ex) {
  407. $this->assertInstanceOf('moodle_exception', $ex);
  408. } catch (Error $error) {
  409. // PHP 7.1 throws Error even earlier.
  410. $this->assertRegExp('/Too few arguments to function/', $error->getMessage());
  411. }
  412. try {
  413. clean_param_array(array('x', array('y')), PARAM_RAW);
  414. $this->fail('coding_exception expected');
  415. } catch (moodle_exception $ex) {
  416. $this->assertInstanceOf('coding_exception', $ex);
  417. }
  418. // Test recursive.
  419. }
  420. public function test_clean_param_raw() {
  421. $this->assertSame(
  422. '#()*#,9789\'".,<42897></?$(*DSFMO#$*)(SDJ)($*)',
  423. clean_param('#()*#,9789\'".,<42897></?$(*DSFMO#$*)(SDJ)($*)', PARAM_RAW));
  424. }
  425. public function test_clean_param_trim() {
  426. $this->assertSame('Frog toad', clean_param(" Frog toad \r\n ", PARAM_RAW_TRIMMED));
  427. }
  428. public function test_clean_param_clean() {
  429. // PARAM_CLEAN is an ugly hack, do not use in new code (skodak),
  430. // instead use more specific type, or submit sothing that can be verified properly.
  431. $this->assertSame('xx', clean_param('xx<script>', PARAM_CLEAN));
  432. }
  433. public function test_clean_param_alpha() {
  434. $this->assertSame('DSFMOSDJ', clean_param('#()*#,9789\'".,<42897></?$(*DSFMO#$*)(SDJ)($*)', PARAM_ALPHA));
  435. }
  436. public function test_clean_param_alphanum() {
  437. $this->assertSame('978942897DSFMOSDJ', clean_param('#()*#,9789\'".,<42897></?$(*DSFMO#$*)(SDJ)($*)', PARAM_ALPHANUM));
  438. }
  439. public function test_clean_param_alphaext() {
  440. $this->assertSame('DSFMOSDJ', clean_param('#()*#,9789\'".,<42897></?$(*DSFMO#$*)(SDJ)($*)', PARAM_ALPHAEXT));
  441. }
  442. public function test_clean_param_sequence() {
  443. $this->assertSame(',9789,42897', clean_param('#()*#,9789\'".,<42897></?$(*DSFMO#$*)(SDJ)($*)', PARAM_SEQUENCE));
  444. }
  445. public function test_clean_param_component() {
  446. // Please note the cleaning of component names is very strict, no guessing here.
  447. $this->assertSame('mod_forum', clean_param('mod_forum', PARAM_COMPONENT));
  448. $this->assertSame('block_online_users', clean_param('block_online_users', PARAM_COMPONENT));
  449. $this->assertSame('block_blond_online_users', clean_param('block_blond_online_users', PARAM_COMPONENT));
  450. $this->assertSame('mod_something2', clean_param('mod_something2', PARAM_COMPONENT));
  451. $this->assertSame('forum', clean_param('forum', PARAM_COMPONENT));
  452. $this->assertSame('user', clean_param('user', PARAM_COMPONENT));
  453. $this->assertSame('rating', clean_param('rating', PARAM_COMPONENT));
  454. $this->assertSame('feedback360', clean_param('feedback360', PARAM_COMPONENT));
  455. $this->assertSame('mod_feedback360', clean_param('mod_feedback360', PARAM_COMPONENT));
  456. $this->assertSame('', clean_param('mod_2something', PARAM_COMPONENT));
  457. $this->assertSame('', clean_param('2mod_something', PARAM_COMPONENT));
  458. $this->assertSame('', clean_param('mod_something_xx', PARAM_COMPONENT));
  459. $this->assertSame('', clean_param('auth_something__xx', PARAM_COMPONENT));
  460. $this->assertSame('', clean_param('mod_Something', PARAM_COMPONENT));
  461. $this->assertSame('', clean_param('mod_somethíng', PARAM_COMPONENT));
  462. $this->assertSame('', clean_param('mod__something', PARAM_COMPONENT));
  463. $this->assertSame('', clean_param('auth_xx-yy', PARAM_COMPONENT));
  464. $this->assertSame('', clean_param('_auth_xx', PARAM_COMPONENT));
  465. $this->assertSame('a2uth_xx', clean_param('a2uth_xx', PARAM_COMPONENT));
  466. $this->assertSame('', clean_param('auth_xx_', PARAM_COMPONENT));
  467. $this->assertSame('', clean_param('auth_xx.old', PARAM_COMPONENT));
  468. $this->assertSame('', clean_param('_user', PARAM_COMPONENT));
  469. $this->assertSame('', clean_param('2rating', PARAM_COMPONENT));
  470. $this->assertSame('', clean_param('user_', PARAM_COMPONENT));
  471. }
  472. public function test_clean_param_localisedfloat() {
  473. $this->assertSame(0.5, clean_param('0.5', PARAM_LOCALISEDFLOAT));
  474. $this->assertSame(false, clean_param('0X5', PARAM_LOCALISEDFLOAT));
  475. $this->assertSame(0.5, clean_param('.5', PARAM_LOCALISEDFLOAT));
  476. $this->assertSame(false, clean_param('X5', PARAM_LOCALISEDFLOAT));
  477. $this->assertSame(10.5, clean_param('10.5', PARAM_LOCALISEDFLOAT));
  478. $this->assertSame(false, clean_param('10X5', PARAM_LOCALISEDFLOAT));
  479. $this->assertSame(1000.5, clean_param('1 000.5', PARAM_LOCALISEDFLOAT));
  480. $this->assertSame(false, clean_param('1 000X5', PARAM_LOCALISEDFLOAT));
  481. $this->assertSame(false, clean_param('1.000.5', PARAM_LOCALISEDFLOAT));
  482. $this->assertSame(false, clean_param('1X000X5', PARAM_LOCALISEDFLOAT));
  483. $this->assertSame(false, clean_param('nan', PARAM_LOCALISEDFLOAT));
  484. $this->assertSame(false, clean_param('10.6blah', PARAM_LOCALISEDFLOAT));
  485. // Tests with a localised decimal separator.
  486. $this->define_local_decimal_separator();
  487. $this->assertSame(0.5, clean_param('0.5', PARAM_LOCALISEDFLOAT));
  488. $this->assertSame(0.5, clean_param('0X5', PARAM_LOCALISEDFLOAT));
  489. $this->assertSame(0.5, clean_param('.5', PARAM_LOCALISEDFLOAT));
  490. $this->assertSame(0.5, clean_param('X5', PARAM_LOCALISEDFLOAT));
  491. $this->assertSame(10.5, clean_param('10.5', PARAM_LOCALISEDFLOAT));
  492. $this->assertSame(10.5, clean_param('10X5', PARAM_LOCALISEDFLOAT));
  493. $this->assertSame(1000.5, clean_param('1 000.5', PARAM_LOCALISEDFLOAT));
  494. $this->assertSame(1000.5, clean_param('1 000X5', PARAM_LOCALISEDFLOAT));
  495. $this->assertSame(false, clean_param('1.000.5', PARAM_LOCALISEDFLOAT));
  496. $this->assertSame(false, clean_param('1X000X5', PARAM_LOCALISEDFLOAT));
  497. $this->assertSame(false, clean_param('nan', PARAM_LOCALISEDFLOAT));
  498. $this->assertSame(false, clean_param('10X6blah', PARAM_LOCALISEDFLOAT));
  499. }
  500. public function test_is_valid_plugin_name() {
  501. $this->assertTrue(is_valid_plugin_name('forum'));
  502. $this->assertTrue(is_valid_plugin_name('forum2'));
  503. $this->assertTrue(is_valid_plugin_name('feedback360'));
  504. $this->assertTrue(is_valid_plugin_name('online_users'));
  505. $this->assertTrue(is_valid_plugin_name('blond_online_users'));
  506. $this->assertFalse(is_valid_plugin_name('online__users'));
  507. $this->assertFalse(is_valid_plugin_name('forum '));
  508. $this->assertFalse(is_valid_plugin_name('forum.old'));
  509. $this->assertFalse(is_valid_plugin_name('xx-yy'));
  510. $this->assertFalse(is_valid_plugin_name('2xx'));
  511. $this->assertFalse(is_valid_plugin_name('Xx'));
  512. $this->assertFalse(is_valid_plugin_name('_xx'));
  513. $this->assertFalse(is_valid_plugin_name('xx_'));
  514. }
  515. public function test_clean_param_plugin() {
  516. // Please note the cleaning of plugin names is very strict, no guessing here.
  517. $this->assertSame('forum', clean_param('forum', PARAM_PLUGIN));
  518. $this->assertSame('forum2', clean_param('forum2', PARAM_PLUGIN));
  519. $this->assertSame('feedback360', clean_param('feedback360', PARAM_PLUGIN));
  520. $this->assertSame('online_users', clean_param('online_users', PARAM_PLUGIN));
  521. $this->assertSame('blond_online_users', clean_param('blond_online_users', PARAM_PLUGIN));
  522. $this->assertSame('', clean_param('online__users', PARAM_PLUGIN));
  523. $this->assertSame('', clean_param('forum ', PARAM_PLUGIN));
  524. $this->assertSame('', clean_param('forum.old', PARAM_PLUGIN));
  525. $this->assertSame('', clean_param('xx-yy', PARAM_PLUGIN));
  526. $this->assertSame('', clean_param('2xx', PARAM_PLUGIN));
  527. $this->assertSame('', clean_param('Xx', PARAM_PLUGIN));
  528. $this->assertSame('', clean_param('_xx', PARAM_PLUGIN));
  529. $this->assertSame('', clean_param('xx_', PARAM_PLUGIN));
  530. }
  531. public function test_clean_param_area() {
  532. // Please note the cleaning of area names is very strict, no guessing here.
  533. $this->assertSame('something', clean_param('something', PARAM_AREA));
  534. $this->assertSame('something2', clean_param('something2', PARAM_AREA));
  535. $this->assertSame('some_thing', clean_param('some_thing', PARAM_AREA));
  536. $this->assertSame('some_thing_xx', clean_param('some_thing_xx', PARAM_AREA));
  537. $this->assertSame('feedback360', clean_param('feedback360', PARAM_AREA));
  538. $this->assertSame('', clean_param('_something', PARAM_AREA));
  539. $this->assertSame('', clean_param('something_', PARAM_AREA));
  540. $this->assertSame('', clean_param('2something', PARAM_AREA));
  541. $this->assertSame('', clean_param('Something', PARAM_AREA));
  542. $this->assertSame('', clean_param('some-thing', PARAM_AREA));
  543. $this->assertSame('', clean_param('somethííng', PARAM_AREA));
  544. $this->assertSame('', clean_param('something.x', PARAM_AREA));
  545. }
  546. public function test_clean_param_text() {
  547. $this->assertSame(PARAM_TEXT, PARAM_MULTILANG);
  548. // Standard.
  549. $this->assertSame('xx<lang lang="en">aa</lang><lang lang="yy">pp</lang>', clean_param('xx<lang lang="en">aa</lang><lang lang="yy">pp</lang>', PARAM_TEXT));
  550. $this->assertSame('<span lang="en" class="multilang">aa</span><span lang="xy" class="multilang">bb</span>', clean_param('<span lang="en" class="multilang">aa</span><span lang="xy" class="multilang">bb</span>', PARAM_TEXT));
  551. $this->assertSame('xx<lang lang="en">aa'."\n".'</lang><lang lang="yy">pp</lang>', clean_param('xx<lang lang="en">aa'."\n".'</lang><lang lang="yy">pp</lang>', PARAM_TEXT));
  552. // Malformed.
  553. $this->assertSame('<span lang="en" class="multilang">aa</span>', clean_param('<span lang="en" class="multilang">aa</span>', PARAM_TEXT));
  554. $this->assertSame('aa', clean_param('<span lang="en" class="nothing" class="multilang">aa</span>', PARAM_TEXT));
  555. $this->assertSame('aa', clean_param('<lang lang="en" class="multilang">aa</lang>', PARAM_TEXT));
  556. $this->assertSame('aa', clean_param('<lang lang="en!!">aa</lang>', PARAM_TEXT));
  557. $this->assertSame('aa', clean_param('<span lang="en==" class="multilang">aa</span>', PARAM_TEXT));
  558. $this->assertSame('abc', clean_param('a<em>b</em>c', PARAM_TEXT));
  559. $this->assertSame('a>c>', clean_param('a><xx >c>', PARAM_TEXT)); // Standard strip_tags() behaviour.
  560. $this->assertSame('a', clean_param('a<b', PARAM_TEXT));
  561. $this->assertSame('a>b', clean_param('a>b', PARAM_TEXT));
  562. $this->assertSame('<lang lang="en">a>a</lang>', clean_param('<lang lang="en">a>a</lang>', PARAM_TEXT)); // Standard strip_tags() behaviour.
  563. $this->assertSame('a', clean_param('<lang lang="en">a<a</lang>', PARAM_TEXT));
  564. $this->assertSame('<lang lang="en">aa</lang>', clean_param('<lang lang="en">a<br>a</lang>', PARAM_TEXT));
  565. }
  566. public function test_clean_param_url() {
  567. // Test PARAM_URL and PARAM_LOCALURL a bit.
  568. // Valid URLs.
  569. $this->assertSame('http://google.com/', clean_param('http://google.com/', PARAM_URL));
  570. $this->assertSame('http://some.very.long.and.silly.domain/with/a/path/', clean_param('http://some.very.long.and.silly.domain/with/a/path/', PARAM_URL));
  571. $this->assertSame('http://localhost/', clean_param('http://localhost/', PARAM_URL));
  572. $this->assertSame('http://0.255.1.1/numericip.php', clean_param('http://0.255.1.1/numericip.php', PARAM_URL));
  573. $this->assertSame('https://google.com/', clean_param('https://google.com/', PARAM_URL));
  574. $this->assertSame('https://some.very.long.and.silly.domain/with/a/path/', clean_param('https://some.very.long.and.silly.domain/with/a/path/', PARAM_URL));
  575. $this->assertSame('https://localhost/', clean_param('https://localhost/', PARAM_URL));
  576. $this->assertSame('https://0.255.1.1/numericip.php', clean_param('https://0.255.1.1/numericip.php', PARAM_URL));
  577. $this->assertSame('ftp://ftp.debian.org/debian/', clean_param('ftp://ftp.debian.org/debian/', PARAM_URL));
  578. $this->assertSame('/just/a/path', clean_param('/just/a/path', PARAM_URL));
  579. // Invalid URLs.
  580. $this->assertSame('', clean_param('funny:thing', PARAM_URL));
  581. $this->assertSame('', clean_param('http://example.ee/sdsf"f', PARAM_URL));
  582. $this->assertSame('', clean_param('javascript://comment%0Aalert(1)', PARAM_URL));
  583. $this->assertSame('', clean_param('rtmp://example.com/livestream', PARAM_URL));
  584. $this->assertSame('', clean_param('rtmp://example.com/live&foo', PARAM_URL));
  585. $this->assertSame('', clean_param('rtmp://example.com/fms&mp4:path/to/file.mp4', PARAM_URL));
  586. $this->assertSame('', clean_param('mailto:support@moodle.org', PARAM_URL));
  587. $this->assertSame('', clean_param('mailto:support@moodle.org?subject=Hello%20Moodle', PARAM_URL));
  588. $this->assertSame('', clean_param('mailto:support@moodle.org?subject=Hello%20Moodle&cc=feedback@moodle.org', PARAM_URL));
  589. }
  590. public function test_clean_param_localurl() {
  591. global $CFG;
  592. $this->resetAfterTest();
  593. // External, invalid.
  594. $this->assertSame('', clean_param('funny:thing', PARAM_LOCALURL));
  595. $this->assertSame('', clean_param('http://google.com/', PARAM_LOCALURL));
  596. $this->assertSame('', clean_param('https://google.com/?test=true', PARAM_LOCALURL));
  597. $this->assertSame('', clean_param('http://some.very.long.and.silly.domain/with/a/path/', PARAM_LOCALURL));
  598. // Local absolute.
  599. $this->assertSame(clean_param($CFG->wwwroot, PARAM_LOCALURL), $CFG->wwwroot);
  600. $this->assertSame($CFG->wwwroot . '/with/something?else=true',
  601. clean_param($CFG->wwwroot . '/with/something?else=true', PARAM_LOCALURL));
  602. // Local relative.
  603. $this->assertSame('/just/a/path', clean_param('/just/a/path', PARAM_LOCALURL));
  604. $this->assertSame('course/view.php?id=3', clean_param('course/view.php?id=3', PARAM_LOCALURL));
  605. // Local absolute HTTPS in a non HTTPS site.
  606. $CFG->wwwroot = str_replace('https:', 'http:', $CFG->wwwroot); // Need to simulate non-https site.
  607. $httpsroot = str_replace('http:', 'https:', $CFG->wwwroot);
  608. $this->assertSame('', clean_param($httpsroot, PARAM_LOCALURL));
  609. $this->assertSame('', clean_param($httpsroot . '/with/something?else=true', PARAM_LOCALURL));
  610. // Local absolute HTTPS in a HTTPS site.
  611. $CFG->wwwroot = str_replace('http:', 'https:', $CFG->wwwroot);
  612. $httpsroot = $CFG->wwwroot;
  613. $this->assertSame($httpsroot, clean_param($httpsroot, PARAM_LOCALURL));
  614. $this->assertSame($httpsroot . '/with/something?else=true',
  615. clean_param($httpsroot . '/with/something?else=true', PARAM_LOCALURL));
  616. // Test open redirects are not possible.
  617. $CFG->wwwroot = 'http://www.example.com';
  618. $this->assertSame('', clean_param('http://www.example.com.evil.net/hack.php', PARAM_LOCALURL));
  619. $CFG->wwwroot = 'https://www.example.com';
  620. $this->assertSame('', clean_param('https://www.example.com.evil.net/hack.php', PARAM_LOCALURL));
  621. }
  622. public function test_clean_param_file() {
  623. $this->assertSame('correctfile.txt', clean_param('correctfile.txt', PARAM_FILE));
  624. $this->assertSame('badfile.txt', clean_param('b\'a<d`\\/fi:l>e.t"x|t', PARAM_FILE));
  625. $this->assertSame('..parentdirfile.txt', clean_param('../parentdirfile.txt', PARAM_FILE));
  626. $this->assertSame('....grandparentdirfile.txt', clean_param('../../grandparentdirfile.txt', PARAM_FILE));
  627. $this->assertSame('..winparentdirfile.txt', clean_param('..\winparentdirfile.txt', PARAM_FILE));
  628. $this->assertSame('....wingrandparentdir.txt', clean_param('..\..\wingrandparentdir.txt', PARAM_FILE));
  629. $this->assertSame('myfile.a.b.txt', clean_param('myfile.a.b.txt', PARAM_FILE));
  630. $this->assertSame('myfile..a..b.txt', clean_param('myfile..a..b.txt', PARAM_FILE));
  631. $this->assertSame('myfile.a..b...txt', clean_param('myfile.a..b...txt', PARAM_FILE));
  632. $this->assertSame('myfile.a.txt', clean_param('myfile.a.txt', PARAM_FILE));
  633. $this->assertSame('myfile...txt', clean_param('myfile...txt', PARAM_FILE));
  634. $this->assertSame('...jpg', clean_param('...jpg', PARAM_FILE));
  635. $this->assertSame('.a.b.', clean_param('.a.b.', PARAM_FILE));
  636. $this->assertSame('', clean_param('.', PARAM_FILE));
  637. $this->assertSame('', clean_param('..', PARAM_FILE));
  638. $this->assertSame('...', clean_param('...', PARAM_FILE));
  639. $this->assertSame('. . . .', clean_param('. . . .', PARAM_FILE));
  640. $this->assertSame('dontrtrim.me. .. .. . ', clean_param('dontrtrim.me. .. .. . ', PARAM_FILE));
  641. $this->assertSame(' . .dontltrim.me', clean_param(' . .dontltrim.me', PARAM_FILE));
  642. $this->assertSame('here is a tab.txt', clean_param("here is a tab\t.txt", PARAM_FILE));
  643. $this->assertSame('here is a linebreak.txt', clean_param("here is a line\r\nbreak.txt", PARAM_FILE));
  644. // The following behaviours have been maintained although they seem a little odd.
  645. $this->assertSame('funnything', clean_param('funny:thing', PARAM_FILE));
  646. $this->assertSame('.currentdirfile.txt', clean_param('./currentdirfile.txt', PARAM_FILE));
  647. $this->assertSame('ctempwindowsfile.txt', clean_param('c:\temp\windowsfile.txt', PARAM_FILE));
  648. $this->assertSame('homeuserlinuxfile.txt', clean_param('/home/user/linuxfile.txt', PARAM_FILE));
  649. $this->assertSame('~myfile.txt', clean_param('~/myfile.txt', PARAM_FILE));
  650. }
  651. public function test_clean_param_path() {
  652. $this->assertSame('correctfile.txt', clean_param('correctfile.txt', PARAM_PATH));
  653. $this->assertSame('bad/file.txt', clean_param('b\'a<d`\\/fi:l>e.t"x|t', PARAM_PATH));
  654. $this->assertSame('/parentdirfile.txt', clean_param('../parentdirfile.txt', PARAM_PATH));
  655. $this->assertSame('/grandparentdirfile.txt', clean_param('../../grandparentdirfile.txt', PARAM_PATH));
  656. $this->assertSame('/winparentdirfile.txt', clean_param('..\winparentdirfile.txt', PARAM_PATH));
  657. $this->assertSame('/wingrandparentdir.txt', clean_param('..\..\wingrandparentdir.txt', PARAM_PATH));
  658. $this->assertSame('funnything', clean_param('funny:thing', PARAM_PATH));
  659. $this->assertSame('./here', clean_param('./././here', PARAM_PATH));
  660. $this->assertSame('./currentdirfile.txt', clean_param('./currentdirfile.txt', PARAM_PATH));
  661. $this->assertSame('c/temp/windowsfile.txt', clean_param('c:\temp\windowsfile.txt', PARAM_PATH));
  662. $this->assertSame('/home/user/linuxfile.txt', clean_param('/home/user/linuxfile.txt', PARAM_PATH));
  663. $this->assertSame('/home../user ./.linuxfile.txt', clean_param('/home../user ./.linuxfile.txt', PARAM_PATH));
  664. $this->assertSame('~/myfile.txt', clean_param('~/myfile.txt', PARAM_PATH));
  665. $this->assertSame('~/myfile.txt', clean_param('~/../myfile.txt', PARAM_PATH));
  666. $this->assertSame('/..b../.../myfile.txt', clean_param('/..b../.../myfile.txt', PARAM_PATH));
  667. $this->assertSame('..b../.../myfile.txt', clean_param('..b../.../myfile.txt', PARAM_PATH));
  668. $this->assertSame('/super/slashes/', clean_param('/super//slashes///', PARAM_PATH));
  669. }
  670. public function test_clean_param_username() {
  671. global $CFG;
  672. $currentstatus = $CFG->extendedusernamechars;
  673. // Run tests with extended character == false;.
  674. $CFG->extendedusernamechars = false;
  675. $this->assertSame('johndoe123', clean_param('johndoe123', PARAM_USERNAME) );
  676. $this->assertSame('john.doe', clean_param('john.doe', PARAM_USERNAME));
  677. $this->assertSame('john-doe', clean_param('john-doe', PARAM_USERNAME));
  678. $this->assertSame('john-doe', clean_param('john- doe', PARAM_USERNAME));
  679. $this->assertSame('john_doe', clean_param('john_doe', PARAM_USERNAME));
  680. $this->assertSame('john@doe', clean_param('john@doe', PARAM_USERNAME));
  681. $this->assertSame('johndoe', clean_param('john~doe', PARAM_USERNAME));
  682. $this->assertSame('johndoe', clean_param('john´doe', PARAM_USERNAME));
  683. $this->assertSame(clean_param('john# $%&()+_^', PARAM_USERNAME), 'john_');
  684. $this->assertSame(clean_param(' john# $%&()+_^ ', PARAM_USERNAME), 'john_');
  685. $this->assertSame(clean_param('john#$%&() ', PARAM_USERNAME), 'john');
  686. $this->assertSame('johnd', clean_param('JOHNdóé ', PARAM_USERNAME));
  687. $this->assertSame(clean_param('john.,:;-_/|\ñÑ[]A_X-,D {} ~!@#$%^&*()_+ ?><[] ščřžžý ?ýáž?žý??šdoe ', PARAM_USERNAME), 'john.-_a_x-d@_doe');
  688. // Test success condition, if extendedusernamechars == ENABLE;.
  689. $CFG->extendedusernamechars = true;
  690. $this->assertSame('john_doe', clean_param('john_doe', PARAM_USERNAME));
  691. $this->assertSame('john@doe', clean_param('john@doe', PARAM_USERNAME));
  692. $this->assertSame(clean_param('john# $%&()+_^', PARAM_USERNAME), 'john# $%&()+_^');
  693. $this->assertSame(clean_param(' john# $%&()+_^ ', PARAM_USERNAME), 'john# $%&()+_^');
  694. $this->assertSame('john~doe', clean_param('john~doe', PARAM_USERNAME));
  695. $this->assertSame('john´doe', clean_param('joHN´doe', PARAM_USERNAME));
  696. $this->assertSame('johndoe', clean_param('johnDOE', PARAM_USERNAME));
  697. $this->assertSame('johndóé', clean_param('johndóé ', PARAM_USERNAME));
  698. $CFG->extendedusernamechars = $currentstatus;
  699. }
  700. public function test_clean_param_stringid() {
  701. // Test string identifiers validation.
  702. // Valid strings.
  703. $this->assertSame('validstring', clean_param('validstring', PARAM_STRINGID));
  704. $this->assertSame('mod/foobar:valid_capability', clean_param('mod/foobar:valid_capability', PARAM_STRINGID));
  705. $this->assertSame('CZ', clean_param('CZ', PARAM_STRINGID));
  706. $this->assertSame('application/vnd.ms-powerpoint', clean_param('application/vnd.ms-powerpoint', PARAM_STRINGID));
  707. $this->assertSame('grade2', clean_param('grade2', PARAM_STRINGID));
  708. // Invalid strings.
  709. $this->assertSame('', clean_param('trailing ', PARAM_STRINGID));
  710. $this->assertSame('', clean_param('space bar', PARAM_STRINGID));
  711. $this->assertSame('', clean_param('0numeric', PARAM_STRINGID));
  712. $this->assertSame('', clean_param('*', PARAM_STRINGID));
  713. $this->assertSame('', clean_param(' ', PARAM_STRINGID));
  714. }
  715. public function test_clean_param_timezone() {
  716. // Test timezone validation.
  717. $testvalues = array (
  718. 'America/Jamaica' => 'America/Jamaica',
  719. 'America/Argentina/Cordoba' => 'America/Argentina/Cordoba',
  720. 'America/Port-au-Prince' => 'America/Port-au-Prince',
  721. 'America/Argentina/Buenos_Aires' => 'America/Argentina/Buenos_Aires',
  722. 'PST8PDT' => 'PST8PDT',
  723. 'Wrong.Value' => '',
  724. 'Wrong/.Value' => '',
  725. 'Wrong(Value)' => '',
  726. '0' => '0',
  727. '0.0' => '0.0',
  728. '0.5' => '0.5',
  729. '9.0' => '9.0',
  730. '-9.0' => '-9.0',
  731. '+9.0' => '+9.0',
  732. '9.5' => '9.5',
  733. '-9.5' => '-9.5',
  734. '+9.5' => '+9.5',
  735. '12.0' => '12.0',
  736. '-12.0' => '-12.0',
  737. '+12.0' => '+12.0',
  738. '12.5' => '12.5',
  739. '-12.5' => '-12.5',
  740. '+12.5' => '+12.5',
  741. '13.0' => '13.0',
  742. '-13.0' => '-13.0',
  743. '+13.0' => '+13.0',
  744. '13.5' => '',
  745. '+13.5' => '',
  746. '-13.5' => '',
  747. '0.2' => '');
  748. foreach ($testvalues as $testvalue => $expectedvalue) {
  749. $actualvalue = clean_param($testvalue, PARAM_TIMEZONE);
  750. $this->assertEquals($expectedvalue, $actualvalue);
  751. }
  752. }
  753. public function test_validate_param() {
  754. try {
  755. $param = validate_param('11a', PARAM_INT);
  756. $this->fail('invalid_parameter_exception expected');
  757. } catch (moodle_exception $ex) {
  758. $this->assertInstanceOf('invalid_parameter_exception', $ex);
  759. }
  760. $param = validate_param('11', PARAM_INT);
  761. $this->assertSame(11, $param);
  762. try {
  763. $param = validate_param(null, PARAM_INT, false);
  764. $this->fail('invalid_parameter_exception expected');
  765. } catch (moodle_exception $ex) {
  766. $this->assertInstanceOf('invalid_parameter_exception', $ex);
  767. }
  768. $param = validate_param(null, PARAM_INT, true);
  769. $this->assertSame(null, $param);
  770. try {
  771. $param = validate_param(array(), PARAM_INT);
  772. $this->fail('invalid_parameter_exception expected');
  773. } catch (moodle_exception $ex) {
  774. $this->assertInstanceOf('invalid_parameter_exception', $ex);
  775. }
  776. try {
  777. $param = validate_param(new stdClass, PARAM_INT);
  778. $this->fail('invalid_parameter_exception expected');
  779. } catch (moodle_exception $ex) {
  780. $this->assertInstanceOf('invalid_parameter_exception', $ex);
  781. }
  782. $param = validate_param('1.0', PARAM_FLOAT);
  783. $this->assertSame(1.0, $param);
  784. // Make sure valid floats do not cause exception.
  785. validate_param(1.0, PARAM_FLOAT);
  786. validate_param(10, PARAM_FLOAT);
  787. validate_param('0', PARAM_FLOAT);
  788. validate_param('119813454.545464564564546564545646556564465465456465465465645645465645645645', PARAM_FLOAT);
  789. validate_param('011.1', PARAM_FLOAT);
  790. validate_param('11', PARAM_FLOAT);
  791. validate_param('+.1', PARAM_FLOAT);
  792. validate_param('-.1', PARAM_FLOAT);
  793. validate_param('1e10', PARAM_FLOAT);
  794. validate_param('.1e+10', PARAM_FLOAT);
  795. validate_param('1E-1', PARAM_FLOAT);
  796. try {
  797. $param = validate_param('1,2', PARAM_FLOAT);
  798. $this->fail('invalid_parameter_exception expected');
  799. } catch (moodle_exception $ex) {
  800. $this->assertInstanceOf('invalid_parameter_exception', $ex);
  801. }
  802. try {
  803. $param = validate_param('', PARAM_FLOAT);
  804. $this->fail('invalid_parameter_exception expected');
  805. } catch (moodle_exception $ex) {
  806. $this->assertInstanceOf('invalid_parameter_exception', $ex);
  807. }
  808. try {
  809. $param = validate_param('.', PARAM_FLOAT);
  810. $this->fail('invalid_parameter_exception expected');
  811. } catch (moodle_exception $ex) {
  812. $this->assertInstanceOf('invalid_parameter_exception', $ex);
  813. }
  814. try {
  815. $param = validate_param('e10', PARAM_FLOAT);
  816. $this->fail('invalid_parameter_exception expected');
  817. } catch (moodle_exception $ex) {
  818. $this->assertInstanceOf('invalid_parameter_exception', $ex);
  819. }
  820. try {
  821. $param = validate_param('abc', PARAM_FLOAT);
  822. $this->fail('invalid_parameter_exception expected');
  823. } catch (moodle_exception $ex) {
  824. $this->assertInstanceOf('invalid_parameter_exception', $ex);
  825. }
  826. }
  827. public function test_shorten_text_no_tags_already_short_enough() {
  828. // ......12345678901234567890123456.
  829. $text = "short text already no tags";
  830. $this->assertSame($text, shorten_text($text));
  831. }
  832. public fun

Large files files are truncated, but you can click here to view the full file