/backup/util/structure/tests/basenestedelement_test.php

https://bitbucket.org/kudutest1/moodlegit · PHP · 395 lines · 297 code · 35 blank · 63 comment · 1 complexity · 786a7648d51b966f23c502a3352be520 MD5 · raw 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. * @package core_backup
  18. * @category phpunit
  19. * @copyright 2010 onwards Eloy Lafuente (stronk7) {@link http://stronk7.com}
  20. * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
  21. */
  22. defined('MOODLE_INTERNAL') || die();
  23. // Include all the needed stuff
  24. require_once(__DIR__.'/fixtures/structure_fixtures.php');
  25. /**
  26. * Unit test case the base_nested_element class. Note: highly imbricated with base_final_element class
  27. */
  28. class backup_base_nested_element_testcase extends basic_testcase {
  29. /**
  30. * Correct creation tests (attributes and final elements)
  31. */
  32. public function test_creation() {
  33. // Create instance with name, attributes and values and check all them
  34. $instance = new mock_base_nested_element('NAME', array('ATTR1', 'ATTR2'), array('VAL1', 'VAL2', 'VAL3'));
  35. $this->assertInstanceOf('base_nested_element', $instance);
  36. $this->assertEquals($instance->get_name(), 'NAME');
  37. $attrs = $instance->get_attributes();
  38. $this->assertTrue(is_array($attrs));
  39. $this->assertEquals(count($attrs), 2);
  40. $this->assertInstanceOf('base_attribute', $attrs['ATTR1']);
  41. $this->assertEquals($attrs['ATTR1']->get_name(), 'ATTR1');
  42. $this->assertNull($attrs['ATTR1']->get_value());
  43. $this->assertEquals($attrs['ATTR2']->get_name(), 'ATTR2');
  44. $this->assertNull($attrs['ATTR2']->get_value());
  45. $finals = $instance->get_final_elements();
  46. $this->assertTrue(is_array($finals));
  47. $this->assertEquals(count($finals), 3);
  48. $this->assertInstanceOf('base_final_element', $finals['VAL1']);
  49. $this->assertEquals($finals['VAL1']->get_name(), 'VAL1');
  50. $this->assertNull($finals['VAL1']->get_value());
  51. $this->assertEquals($finals['VAL1']->get_level(), 2);
  52. $this->assertInstanceOf('base_nested_element', $finals['VAL1']->get_parent());
  53. $this->assertEquals($finals['VAL2']->get_name(), 'VAL2');
  54. $this->assertNull($finals['VAL2']->get_value());
  55. $this->assertEquals($finals['VAL2']->get_level(), 2);
  56. $this->assertInstanceOf('base_nested_element', $finals['VAL1']->get_parent());
  57. $this->assertEquals($finals['VAL3']->get_name(), 'VAL3');
  58. $this->assertNull($finals['VAL3']->get_value());
  59. $this->assertEquals($finals['VAL3']->get_level(), 2);
  60. $this->assertInstanceOf('base_nested_element', $finals['VAL1']->get_parent());
  61. $this->assertNull($instance->get_parent());
  62. $this->assertEquals($instance->get_children(), array());
  63. $this->assertEquals($instance->get_level(), 1);
  64. // Create instance with name only
  65. $instance = new mock_base_nested_element('NAME');
  66. $this->assertInstanceOf('base_nested_element', $instance);
  67. $this->assertEquals($instance->get_name(), 'NAME');
  68. $this->assertEquals($instance->get_attributes(), array());
  69. $this->assertEquals($instance->get_final_elements(), array());
  70. $this->assertNull($instance->get_parent());
  71. $this->assertEquals($instance->get_children(), array());
  72. $this->assertEquals($instance->get_level(), 1);
  73. // Add some attributes
  74. $instance->add_attributes(array('ATTR1', 'ATTR2'));
  75. $attrs = $instance->get_attributes();
  76. $this->assertTrue(is_array($attrs));
  77. $this->assertEquals(count($attrs), 2);
  78. $this->assertEquals($attrs['ATTR1']->get_name(), 'ATTR1');
  79. $this->assertNull($attrs['ATTR1']->get_value());
  80. $this->assertEquals($attrs['ATTR2']->get_name(), 'ATTR2');
  81. $this->assertNull($attrs['ATTR2']->get_value());
  82. // And some more atributes
  83. $instance->add_attributes(array('ATTR3', 'ATTR4'));
  84. $attrs = $instance->get_attributes();
  85. $this->assertTrue(is_array($attrs));
  86. $this->assertEquals(count($attrs), 4);
  87. $this->assertEquals($attrs['ATTR1']->get_name(), 'ATTR1');
  88. $this->assertNull($attrs['ATTR1']->get_value());
  89. $this->assertEquals($attrs['ATTR2']->get_name(), 'ATTR2');
  90. $this->assertNull($attrs['ATTR2']->get_value());
  91. $this->assertEquals($attrs['ATTR3']->get_name(), 'ATTR3');
  92. $this->assertNull($attrs['ATTR3']->get_value());
  93. $this->assertEquals($attrs['ATTR4']->get_name(), 'ATTR4');
  94. $this->assertNull($attrs['ATTR4']->get_value());
  95. // Add some final elements
  96. $instance->add_final_elements(array('VAL1', 'VAL2', 'VAL3'));
  97. $finals = $instance->get_final_elements();
  98. $this->assertTrue(is_array($finals));
  99. $this->assertEquals(count($finals), 3);
  100. $this->assertEquals($finals['VAL1']->get_name(), 'VAL1');
  101. $this->assertNull($finals['VAL1']->get_value());
  102. $this->assertEquals($finals['VAL2']->get_name(), 'VAL2');
  103. $this->assertNull($finals['VAL2']->get_value());
  104. $this->assertEquals($finals['VAL3']->get_name(), 'VAL3');
  105. $this->assertNull($finals['VAL3']->get_value());
  106. // Add some more final elements
  107. $instance->add_final_elements('VAL4');
  108. $finals = $instance->get_final_elements();
  109. $this->assertTrue(is_array($finals));
  110. $this->assertEquals(count($finals), 4);
  111. $this->assertEquals($finals['VAL1']->get_name(), 'VAL1');
  112. $this->assertNull($finals['VAL1']->get_value());
  113. $this->assertEquals($finals['VAL2']->get_name(), 'VAL2');
  114. $this->assertNull($finals['VAL2']->get_value());
  115. $this->assertEquals($finals['VAL3']->get_name(), 'VAL3');
  116. $this->assertNull($finals['VAL3']->get_value());
  117. $this->assertEquals($finals['VAL4']->get_name(), 'VAL4');
  118. $this->assertNull($finals['VAL4']->get_value());
  119. // Get to_string() results (with values)
  120. $instance = new mock_base_nested_element('PARENT', array('ATTR1', 'ATTR2'), array('FINAL1', 'FINAL2', 'FINAL3'));
  121. $child1 = new mock_base_nested_element('CHILD1', null, new mock_base_final_element('FINAL4'));
  122. $child2 = new mock_base_nested_element('CHILD2', null, new mock_base_final_element('FINAL5'));
  123. $instance->add_child($child1);
  124. $instance->add_child($child2);
  125. $children = $instance->get_children();
  126. $final_elements = $children['CHILD1']->get_final_elements();
  127. $final_elements['FINAL4']->set_value('final4value');
  128. $final_elements['FINAL4']->add_attributes('ATTR4');
  129. $grandchild = new mock_base_nested_element('GRANDCHILD', new mock_base_attribute('ATTR5'));
  130. $child2->add_child($grandchild);
  131. $attrs = $grandchild->get_attributes();
  132. $attrs['ATTR5']->set_value('attr5value');
  133. $tostring = $instance->to_string(true);
  134. $this->assertTrue(strpos($tostring, 'PARENT (level: 1)') !== false);
  135. $this->assertTrue(strpos($tostring, ' => ') !== false);
  136. $this->assertTrue(strpos($tostring, '#FINAL4 (level: 3) => final4value') !== false);
  137. $this->assertTrue(strpos($tostring, '@ATTR5 => attr5value') !== false);
  138. $this->assertTrue(strpos($tostring, '#FINAL5 (level: 3) => not set') !== false);
  139. // Clean values
  140. $instance = new mock_base_nested_element('PARENT', array('ATTR1', 'ATTR2'), array('FINAL1', 'FINAL2', 'FINAL3'));
  141. $child1 = new mock_base_nested_element('CHILD1', null, new mock_base_final_element('FINAL4'));
  142. $child2 = new mock_base_nested_element('CHILD2', null, new mock_base_final_element('FINAL4'));
  143. $instance->add_child($child1);
  144. $instance->add_child($child2);
  145. $children = $instance->get_children();
  146. $final_elements = $children['CHILD1']->get_final_elements();
  147. $final_elements['FINAL4']->set_value('final4value');
  148. $final_elements['FINAL4']->add_attributes('ATTR4');
  149. $grandchild = new mock_base_nested_element('GRANDCHILD', new mock_base_attribute('ATTR4'));
  150. $child2->add_child($grandchild);
  151. $attrs = $grandchild->get_attributes();
  152. $attrs['ATTR4']->set_value('attr4value');
  153. $this->assertEquals($final_elements['FINAL4']->get_value(), 'final4value');
  154. $this->assertEquals($attrs['ATTR4']->get_value(), 'attr4value');
  155. $instance->clean_values();
  156. $this->assertNull($final_elements['FINAL4']->get_value());
  157. $this->assertNull($attrs['ATTR4']->get_value());
  158. }
  159. /**
  160. * Incorrect creation tests (attributes and final elements)
  161. */
  162. function test_wrong_creation() {
  163. // Create instance with invalid name
  164. try {
  165. $instance = new mock_base_nested_element('');
  166. $this->fail("Expecting base_atom_struct_exception exception, none occurred");
  167. } catch (Exception $e) {
  168. $this->assertTrue($e instanceof base_atom_struct_exception);
  169. }
  170. // Create instance with incorrect (object) final element
  171. try {
  172. $obj = new stdClass;
  173. $obj->name = 'test_attr';
  174. $instance = new mock_base_nested_element('TEST', null, $obj);
  175. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  176. } catch (Exception $e) {
  177. $this->assertTrue($e instanceof base_element_struct_exception);
  178. }
  179. // Create instance with array containing incorrect (object) final element
  180. try {
  181. $obj = new stdClass;
  182. $obj->name = 'test_attr';
  183. $instance = new mock_base_nested_element('TEST', null, array($obj));
  184. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  185. } catch (Exception $e) {
  186. $this->assertTrue($e instanceof base_element_struct_exception);
  187. }
  188. // Create instance with array containing duplicate final elements
  189. try {
  190. $instance = new mock_base_nested_element('TEST', null, array('VAL1', 'VAL2', 'VAL1'));
  191. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  192. } catch (Exception $e) {
  193. $this->assertTrue($e instanceof base_element_struct_exception);
  194. }
  195. // Try to get value of base_nested_element
  196. $instance = new mock_base_nested_element('TEST');
  197. try {
  198. $instance->get_value();
  199. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  200. } catch (Exception $e) {
  201. $this->assertTrue($e instanceof base_element_struct_exception);
  202. }
  203. // Try to set value of base_nested_element
  204. $instance = new mock_base_nested_element('TEST');
  205. try {
  206. $instance->set_value('some_value');
  207. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  208. } catch (Exception $e) {
  209. $this->assertTrue($e instanceof base_element_struct_exception);
  210. }
  211. // Try to clean one value of base_nested_element
  212. $instance = new mock_base_nested_element('TEST');
  213. try {
  214. $instance->clean_value('some_value');
  215. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  216. } catch (Exception $e) {
  217. $this->assertTrue($e instanceof base_element_struct_exception);
  218. }
  219. }
  220. /**
  221. * Correct tree tests (children stuff)
  222. */
  223. function test_tree() {
  224. // Create parent and child instances, tree-ing them
  225. $parent = new mock_base_nested_element('PARENT');
  226. $child = new mock_base_nested_element('CHILD');
  227. $parent->add_child($child);
  228. $this->assertEquals($parent->get_children(), array('CHILD' => $child));
  229. $this->assertEquals($child->get_parent(), $parent);
  230. $check_children = $parent->get_children();
  231. $check_child = $check_children['CHILD'];
  232. $check_parent = $check_child->get_parent();
  233. $this->assertEquals($check_child->get_name(), 'CHILD');
  234. $this->assertEquals($check_parent->get_name(), 'PARENT');
  235. $this->assertEquals($check_child->get_level(), 2);
  236. $this->assertEquals($check_parent->get_level(), 1);
  237. $this->assertEquals($check_parent->get_children(), array('CHILD' => $child));
  238. $this->assertEquals($check_child->get_parent(), $parent);
  239. // Add parent to grandparent
  240. $grandparent = new mock_base_nested_element('GRANDPARENT');
  241. $grandparent->add_child($parent);
  242. $this->assertEquals($grandparent->get_children(), array('PARENT' => $parent));
  243. $this->assertEquals($parent->get_parent(), $grandparent);
  244. $this->assertEquals($parent->get_children(), array('CHILD' => $child));
  245. $this->assertEquals($child->get_parent(), $parent);
  246. $this->assertEquals($child->get_level(), 3);
  247. $this->assertEquals($parent->get_level(), 2);
  248. $this->assertEquals($grandparent->get_level(), 1);
  249. // Add grandchild to child
  250. $grandchild = new mock_base_nested_element('GRANDCHILD');
  251. $child->add_child($grandchild);
  252. $this->assertEquals($child->get_children(), array('GRANDCHILD' => $grandchild));
  253. $this->assertEquals($grandchild->get_parent(), $child);
  254. $this->assertEquals($grandchild->get_level(), 4);
  255. $this->assertEquals($child->get_level(), 3);
  256. $this->assertEquals($parent->get_level(), 2);
  257. $this->assertEquals($grandparent->get_level(), 1);
  258. // Add another child to parent
  259. $child2 = new mock_base_nested_element('CHILD2');
  260. $parent->add_child($child2);
  261. $this->assertEquals($parent->get_children(), array('CHILD' => $child, 'CHILD2' => $child2));
  262. $this->assertEquals($child2->get_parent(), $parent);
  263. $this->assertEquals($grandchild->get_level(), 4);
  264. $this->assertEquals($child->get_level(), 3);
  265. $this->assertEquals($child2->get_level(), 3);
  266. $this->assertEquals($parent->get_level(), 2);
  267. $this->assertEquals($grandparent->get_level(), 1);
  268. }
  269. /**
  270. * Incorrect tree tests (children stuff)
  271. */
  272. function test_wrong_tree() {
  273. // Add null object child
  274. $parent = new mock_base_nested_element('PARENT');
  275. $child = null;
  276. try {
  277. $parent->add_child($child);
  278. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  279. } catch (Exception $e) {
  280. $this->assertTrue($e instanceof base_element_struct_exception);
  281. }
  282. // Add non base_element object child
  283. $parent = new mock_base_nested_element('PARENT');
  284. $child = new stdClass();
  285. try {
  286. $parent->add_child($child);
  287. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  288. } catch (Exception $e) {
  289. $this->assertTrue($e instanceof base_element_struct_exception);
  290. }
  291. // Add existing element (being parent)
  292. $parent = new mock_base_nested_element('PARENT');
  293. $child = new mock_base_nested_element('PARENT');
  294. try {
  295. $parent->add_child($child);
  296. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  297. } catch (Exception $e) {
  298. $this->assertTrue($e instanceof base_element_struct_exception);
  299. }
  300. // Add existing element (being grandparent)
  301. $grandparent = new mock_base_nested_element('GRANDPARENT');
  302. $parent = new mock_base_nested_element('PARENT');
  303. $child = new mock_base_nested_element('GRANDPARENT');
  304. $grandparent->add_child($parent);
  305. try {
  306. $parent->add_child($child);
  307. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  308. } catch (Exception $e) {
  309. $this->assertTrue($e instanceof base_element_struct_exception);
  310. }
  311. // Add existing element (being grandchild)
  312. $grandparent = new mock_base_nested_element('GRANDPARENT');
  313. $parent = new mock_base_nested_element('PARENT');
  314. $child = new mock_base_nested_element('GRANDPARENT');
  315. $parent->add_child($child);
  316. try {
  317. $grandparent->add_child($parent);
  318. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  319. } catch (Exception $e) {
  320. $this->assertTrue($e instanceof base_element_struct_exception);
  321. }
  322. // Add existing element (being cousin)
  323. $grandparent = new mock_base_nested_element('GRANDPARENT');
  324. $parent1 = new mock_base_nested_element('PARENT1');
  325. $parent2 = new mock_base_nested_element('PARENT2');
  326. $child1 = new mock_base_nested_element('CHILD1');
  327. $child2 = new mock_base_nested_element('CHILD1');
  328. $grandparent->add_child($parent1);
  329. $parent1->add_child($child1);
  330. $parent2->add_child($child2);
  331. try {
  332. $grandparent->add_child($parent2);
  333. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  334. } catch (Exception $e) {
  335. $this->assertTrue($e instanceof base_element_struct_exception);
  336. }
  337. // Add element to two parents
  338. $parent1 = new mock_base_nested_element('PARENT1');
  339. $parent2 = new mock_base_nested_element('PARENT2');
  340. $child = new mock_base_nested_element('CHILD');
  341. $parent1->add_child($child);
  342. try {
  343. $parent2->add_child($child);
  344. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  345. } catch (Exception $e) {
  346. $this->assertTrue($e instanceof base_element_parent_exception);
  347. }
  348. // Add child element already used by own final elements
  349. $nested = new mock_base_nested_element('PARENT1', null, array('FINAL1', 'FINAL2'));
  350. $child = new mock_base_nested_element('FINAL2', null, array('FINAL3', 'FINAL4'));
  351. try {
  352. $nested->add_child($child);
  353. $this->fail("Expecting base_element_struct_exception exception, none occurred");
  354. } catch (Exception $e) {
  355. $this->assertTrue($e instanceof base_element_struct_exception);
  356. $this->assertEquals($e->errorcode, 'baseelementchildnameconflict');
  357. $this->assertEquals($e->a, 'FINAL2');
  358. }
  359. }
  360. }