TestTaskTest.php 17 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621
  1. <?php
  2. /**
  3. * CakePHP : Rapid Development Framework (http://cakephp.org)
  4. * Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
  5. *
  6. * Licensed under The MIT License
  7. * For full copyright and license information, please see the LICENSE.txt
  8. * Redistributions of files must retain the above copyright notice.
  9. *
  10. * @copyright Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
  11. * @link http://cakephp.org CakePHP Project
  12. * @since 1.2.0
  13. * @license http://www.opensource.org/licenses/mit-license.php MIT License
  14. */
  15. namespace Cake\Test\TestCase\Shell\Task;
  16. use Cake\Controller\Controller;
  17. use Cake\Core\App;
  18. use Cake\Core\Configure;
  19. use Cake\Core\Plugin;
  20. use Cake\Network\Request;
  21. use Cake\Network\Response;
  22. use Cake\ORM\Table;
  23. use Cake\ORM\TableRegistry;
  24. use Cake\Shell\Task\TemplateTask;
  25. use Cake\Shell\Task\TestTask;
  26. use Cake\TestSuite\StringCompareTrait;
  27. use Cake\TestSuite\TestCase;
  28. use TestApp\Controller\PostsController;
  29. use TestApp\Model\Table\ArticlesTable;
  30. use TestApp\Model\Table\CategoryThreadsTable;
  31. /**
  32. * TestTaskTest class
  33. *
  34. */
  35. class TestTaskTest extends TestCase {
  36. use StringCompareTrait;
  37. /**
  38. * Fixtures
  39. *
  40. * @var string
  41. */
  42. public $fixtures = [
  43. 'core.articles',
  44. 'core.authors',
  45. 'core.comments',
  46. 'core.tags',
  47. 'core.articles_tags',
  48. ];
  49. /**
  50. * setUp method
  51. *
  52. * @return void
  53. */
  54. public function setUp() {
  55. parent::setUp();
  56. $this->_compareBasePath = CORE_TESTS . 'bake_compare' . DS . 'Test' . DS;
  57. $this->io = $this->getMock('Cake\Console\ConsoleIo', [], [], '', false);
  58. $this->Task = $this->getMock('Cake\Shell\Task\TestTask',
  59. array('in', 'err', 'createFile', '_stop', 'isLoadableClass'),
  60. array($this->io)
  61. );
  62. $this->Task->name = 'Test';
  63. $this->Task->Template = new TemplateTask($this->io);
  64. $this->Task->Template->interactive = false;
  65. }
  66. /**
  67. * tearDown method
  68. *
  69. * @return void
  70. */
  71. public function tearDown() {
  72. parent::tearDown();
  73. unset($this->Task);
  74. Plugin::unload();
  75. }
  76. /**
  77. * Test that with no args execute() outputs the types you can generate
  78. * tests for.
  79. *
  80. * @return void
  81. */
  82. public function testExecuteNoArgsPrintsTypeOptions() {
  83. $this->Task = $this->getMockBuilder('Cake\Shell\Task\TestTask')
  84. ->disableOriginalConstructor()
  85. ->setMethods(['outputTypeChoices'])
  86. ->getMock();
  87. $this->Task->expects($this->once())
  88. ->method('outputTypeChoices');
  89. $this->Task->main();
  90. }
  91. /**
  92. * Test outputTypeChoices method
  93. *
  94. * @return void
  95. */
  96. public function testOutputTypeChoices() {
  97. $this->io->expects($this->at(0))
  98. ->method('out')
  99. ->with($this->stringContains('You must provide'));
  100. $this->io->expects($this->at(1))
  101. ->method('out')
  102. ->with($this->stringContains('1. Entity'));
  103. $this->io->expects($this->at(2))
  104. ->method('out')
  105. ->with($this->stringContains('2. Table'));
  106. $this->io->expects($this->at(3))
  107. ->method('out')
  108. ->with($this->stringContains('3. Controller'));
  109. $this->Task->outputTypeChoices();
  110. }
  111. /**
  112. * Test that with no args execute() outputs the types you can generate
  113. * tests for.
  114. *
  115. * @return void
  116. */
  117. public function testExecuteOneArgPrintsClassOptions() {
  118. $this->Task = $this->getMockBuilder('Cake\Shell\Task\TestTask')
  119. ->disableOriginalConstructor()
  120. ->setMethods(['outputClassChoices'])
  121. ->getMock();
  122. $this->Task->expects($this->once())
  123. ->method('outputClassChoices');
  124. $this->Task->main('Entity');
  125. }
  126. /**
  127. * test execute with type and class name defined
  128. *
  129. * @return void
  130. */
  131. public function testExecuteWithTwoArgs() {
  132. $this->Task->expects($this->once())->method('createFile')
  133. ->with(
  134. $this->stringContains('TestCase' . DS . 'Model' . DS . 'Table' . DS . 'TestTaskTagTableTest.php'),
  135. $this->stringContains('class TestTaskTagTableTest extends TestCase')
  136. );
  137. $this->Task->main('Table', 'TestTaskTag');
  138. }
  139. /**
  140. * Test generating class options for table.
  141. *
  142. * @return void
  143. */
  144. public function testOutputClassOptionsForTable() {
  145. $this->io->expects($this->at(0))
  146. ->method('out')
  147. ->with($this->stringContains('You must provide'));
  148. $this->io->expects($this->at(1))
  149. ->method('out')
  150. ->with($this->stringContains('1. ArticlesTable'));
  151. $this->io->expects($this->at(2))
  152. ->method('out')
  153. ->with($this->stringContains('2. ArticlesTagsTable'));
  154. $this->io->expects($this->at(3))
  155. ->method('out')
  156. ->with($this->stringContains('3. AuthUsersTable'));
  157. $this->io->expects($this->at(4))
  158. ->method('out')
  159. ->with($this->stringContains('4. AuthorsTable'));
  160. $this->Task->outputClassChoices('Table');
  161. }
  162. /**
  163. * Test generating class options for table.
  164. *
  165. * @return void
  166. */
  167. public function testOutputClassOptionsForTablePlugin() {
  168. Plugin::load('TestPlugin');
  169. $this->Task->plugin = 'TestPlugin';
  170. $this->io->expects($this->at(0))
  171. ->method('out')
  172. ->with($this->stringContains('You must provide'));
  173. $this->io->expects($this->at(1))
  174. ->method('out')
  175. ->with($this->stringContains('1. AuthorsTable'));
  176. $this->io->expects($this->at(2))
  177. ->method('out')
  178. ->with($this->stringContains('2. CommentsTable'));
  179. $this->io->expects($this->at(3))
  180. ->method('out')
  181. ->with($this->stringContains('3. TestPluginCommentsTable'));
  182. $this->Task->outputClassChoices('Table');
  183. }
  184. /**
  185. * Test that method introspection pulls all relevant non parent class
  186. * methods into the test case.
  187. *
  188. * @return void
  189. */
  190. public function testMethodIntrospection() {
  191. $result = $this->Task->getTestableMethods('TestApp\Model\Table\ArticlesTable');
  192. $expected = ['initialize', 'findpublished', 'dosomething', 'dosomethingelse'];
  193. $this->assertEquals($expected, array_map('strtolower', $result));
  194. }
  195. /**
  196. * test that the generation of fixtures works correctly.
  197. *
  198. * @return void
  199. */
  200. public function testFixtureArrayGenerationFromModel() {
  201. $subject = new ArticlesTable();
  202. $result = $this->Task->generateFixtureList($subject);
  203. $expected = [
  204. 'app.articles',
  205. 'app.authors',
  206. 'app.tags',
  207. 'app.articles_tags'
  208. ];
  209. $this->assertEquals($expected, $result);
  210. }
  211. /**
  212. * test that the generation of fixtures works correctly.
  213. *
  214. * @return void
  215. */
  216. public function testFixtureArrayGenerationIgnoreSelfAssociation() {
  217. TableRegistry::clear();
  218. $subject = new CategoryThreadsTable();
  219. $result = $this->Task->generateFixtureList($subject);
  220. $expected = [
  221. 'app.category_threads',
  222. ];
  223. $this->assertEquals($expected, $result);
  224. }
  225. /**
  226. * test that the generation of fixtures works correctly.
  227. *
  228. * @return void
  229. */
  230. public function testFixtureArrayGenerationFromController() {
  231. $subject = new PostsController(new Request(), new Response());
  232. $result = $this->Task->generateFixtureList($subject);
  233. $expected = [
  234. 'app.posts',
  235. ];
  236. $this->assertEquals($expected, $result);
  237. }
  238. /**
  239. * Dataprovider for class name generation.
  240. *
  241. * @return array
  242. */
  243. public static function realClassProvider() {
  244. return [
  245. ['Entity', 'Article', 'App\Model\Entity\Article'],
  246. ['entity', 'ArticleEntity', 'App\Model\Entity\ArticleEntity'],
  247. ['Table', 'Posts', 'App\Model\Table\PostsTable'],
  248. ['table', 'PostsTable', 'App\Model\Table\PostsTable'],
  249. ['Controller', 'Posts', 'App\Controller\PostsController'],
  250. ['controller', 'PostsController', 'App\Controller\PostsController'],
  251. ['Behavior', 'Timestamp', 'App\Model\Behavior\TimestampBehavior'],
  252. ['behavior', 'TimestampBehavior', 'App\Model\Behavior\TimestampBehavior'],
  253. ['Helper', 'Form', 'App\View\Helper\FormHelper'],
  254. ['helper', 'FormHelper', 'App\View\Helper\FormHelper'],
  255. ['Component', 'Auth', 'App\Controller\Component\AuthComponent'],
  256. ['component', 'AuthComponent', 'App\Controller\Component\AuthComponent'],
  257. ['Shell', 'Example', 'App\Shell\ExampleShell'],
  258. ['shell', 'Example', 'App\Shell\ExampleShell'],
  259. ['Cell', 'Example', 'App\View\Cell\ExampleCell'],
  260. ['cell', 'Example', 'App\View\Cell\ExampleCell'],
  261. ];
  262. }
  263. /**
  264. * test that resolving class names works
  265. *
  266. * @dataProvider realClassProvider
  267. * @return void
  268. */
  269. public function testGetRealClassname($type, $name, $expected) {
  270. $result = $this->Task->getRealClassname($type, $name);
  271. $this->assertEquals($expected, $result);
  272. }
  273. /**
  274. * test resolving class names with plugins
  275. *
  276. * @return void
  277. */
  278. public function testGetRealClassnamePlugin() {
  279. Plugin::load('TestPlugin');
  280. $this->Task->plugin = 'TestPlugin';
  281. $result = $this->Task->getRealClassname('Helper', 'Asset');
  282. $expected = 'TestPlugin\View\Helper\AssetHelper';
  283. $this->assertEquals($expected, $result);
  284. }
  285. /**
  286. * Test baking a test for a concrete model with fixtures arg
  287. *
  288. * @return void
  289. */
  290. public function testBakeFixturesParam() {
  291. $this->Task->expects($this->once())
  292. ->method('createFile')
  293. ->will($this->returnValue(true));
  294. $this->Task->params['fixtures'] = 'app.posts, app.comments , app.users ,';
  295. $result = $this->Task->bake('Table', 'Articles');
  296. $this->assertSameAsFile(__FUNCTION__ . '.php', $result);
  297. }
  298. /**
  299. * Test baking a test for a cell.
  300. *
  301. * @return void
  302. */
  303. public function testBakeCellTest() {
  304. $this->Task->expects($this->once())
  305. ->method('createFile')
  306. ->will($this->returnValue(true));
  307. $result = $this->Task->bake('Cell', 'Articles');
  308. $this->assertSameAsFile(__FUNCTION__ . '.php', $result);
  309. }
  310. /**
  311. * Test baking a test for a concrete model.
  312. *
  313. * @return void
  314. */
  315. public function testBakeModelTest() {
  316. $this->Task->expects($this->once())
  317. ->method('createFile')
  318. ->will($this->returnValue(true));
  319. $result = $this->Task->bake('Table', 'Articles');
  320. $this->assertSameAsFile(__FUNCTION__ . '.php', $result);
  321. }
  322. /**
  323. * test baking controller test files
  324. *
  325. * @return void
  326. */
  327. public function testBakeControllerTest() {
  328. Configure::write('App.namespace', 'TestApp');
  329. $this->Task->expects($this->once())
  330. ->method('createFile')
  331. ->will($this->returnValue(true));
  332. $result = $this->Task->bake('Controller', 'PostsController');
  333. $this->assertSameAsFile(__FUNCTION__ . '.php', $result);
  334. }
  335. /**
  336. * test baking controller test files
  337. *
  338. * @return void
  339. */
  340. public function testBakePrefixControllerTest() {
  341. Configure::write('App.namespace', 'TestApp');
  342. $this->Task->expects($this->once())
  343. ->method('createFile')
  344. ->with($this->stringContains('Controller' . DS . 'Admin' . DS . 'PostsControllerTest.php'))
  345. ->will($this->returnValue(true));
  346. $result = $this->Task->bake('controller', 'Admin\Posts');
  347. $this->assertSameAsFile(__FUNCTION__ . '.php', $result);
  348. }
  349. /**
  350. * test baking component test files,
  351. *
  352. * @return void
  353. */
  354. public function testBakeComponentTest() {
  355. Configure::write('App.namespace', 'TestApp');
  356. $this->Task->expects($this->once())
  357. ->method('createFile')
  358. ->will($this->returnValue(true));
  359. $result = $this->Task->bake('Component', 'Apple');
  360. $this->assertSameAsFile(__FUNCTION__ . '.php', $result);
  361. }
  362. /**
  363. * test baking behavior test files,
  364. *
  365. * @return void
  366. */
  367. public function testBakeBehaviorTest() {
  368. $this->Task->expects($this->once())
  369. ->method('createFile')
  370. ->will($this->returnValue(true));
  371. $result = $this->Task->bake('Behavior', 'Example');
  372. $this->assertSameAsFile(__FUNCTION__ . '.php', $result);
  373. }
  374. /**
  375. * test baking helper test files,
  376. *
  377. * @return void
  378. */
  379. public function testBakeHelperTest() {
  380. $this->Task->expects($this->once())
  381. ->method('createFile')
  382. ->will($this->returnValue(true));
  383. $result = $this->Task->bake('Helper', 'Example');
  384. $this->assertSameAsFile(__FUNCTION__ . '.php', $result);
  385. }
  386. /**
  387. * Test baking a test for a concrete model.
  388. *
  389. * @return void
  390. */
  391. public function testBakeShellTest() {
  392. $this->Task->expects($this->once())
  393. ->method('createFile')
  394. ->will($this->returnValue(true));
  395. $result = $this->Task->bake('Shell', 'Articles');
  396. $this->assertSameAsFile(__FUNCTION__ . '.php', $result);
  397. }
  398. /**
  399. * test Constructor generation ensure that constructClasses is called for controllers
  400. *
  401. * @return void
  402. */
  403. public function testGenerateConstructor() {
  404. $result = $this->Task->generateConstructor('controller', 'PostsController');
  405. $expected = ['', '', ''];
  406. $this->assertEquals($expected, $result);
  407. $result = $this->Task->generateConstructor('table', 'App\Model\\Table\PostsTable');
  408. $expected = [
  409. "\$config = TableRegistry::exists('Posts') ? [] : ['className' => 'App\Model\\Table\PostsTable'];",
  410. "TableRegistry::get('Posts', \$config);",
  411. ''
  412. ];
  413. $this->assertEquals($expected, $result);
  414. $result = $this->Task->generateConstructor('helper', 'FormHelper');
  415. $expected = ["\$view = new View();", "new FormHelper(\$view);", ''];
  416. $this->assertEquals($expected, $result);
  417. $result = $this->Task->generateConstructor('entity', 'TestPlugin\Model\Entity\Article');
  418. $expected = ["", "new Article();", ''];
  419. $this->assertEquals($expected, $result);
  420. }
  421. /**
  422. * Test generateUses()
  423. *
  424. * @return void
  425. */
  426. public function testGenerateUses() {
  427. $result = $this->Task->generateUses('table', 'App\Model\Table\PostsTable');
  428. $expected = array(
  429. 'Cake\ORM\TableRegistry',
  430. 'App\Model\Table\PostsTable',
  431. );
  432. $this->assertEquals($expected, $result);
  433. $result = $this->Task->generateUses('controller', 'App\Controller\PostsController');
  434. $expected = array(
  435. 'App\Controller\PostsController',
  436. );
  437. $this->assertEquals($expected, $result);
  438. $result = $this->Task->generateUses('helper', 'App\View\Helper\FormHelper');
  439. $expected = array(
  440. 'Cake\View\View',
  441. 'App\View\Helper\FormHelper',
  442. );
  443. $this->assertEquals($expected, $result);
  444. $result = $this->Task->generateUses('component', 'App\Controller\Component\AuthComponent');
  445. $expected = array(
  446. 'Cake\Controller\ComponentRegistry',
  447. 'App\Controller\Component\AuthComponent',
  448. );
  449. $this->assertEquals($expected, $result);
  450. }
  451. /**
  452. * Test that mock class generation works for the appropriate classes
  453. *
  454. * @return void
  455. */
  456. public function testMockClassGeneration() {
  457. $result = $this->Task->hasMockClass('controller');
  458. $this->assertTrue($result);
  459. }
  460. /**
  461. * test bake() with a -plugin param
  462. *
  463. * @return void
  464. */
  465. public function testBakeWithPlugin() {
  466. $this->Task->plugin = 'TestPlugin';
  467. Plugin::load('TestPlugin');
  468. $path = TEST_APP . 'Plugin/TestPlugin/tests/TestCase/View/Helper/FormHelperTest.php';
  469. $path = str_replace('/', DS, $path);
  470. $this->Task->expects($this->once())->method('createFile')
  471. ->with($path, $this->anything());
  472. $this->Task->bake('Helper', 'Form');
  473. }
  474. /**
  475. * Provider for test case file names.
  476. *
  477. * @return array
  478. */
  479. public static function caseFileNameProvider() {
  480. return array(
  481. array('Table', 'App\Model\Table\PostsTable', 'TestCase/Model/Table/PostsTableTest.php'),
  482. array('Entity', 'App\Model\Entity\Article', 'TestCase/Model/Entity/ArticleTest.php'),
  483. array('Helper', 'App\View\Helper\FormHelper', 'TestCase/View/Helper/FormHelperTest.php'),
  484. array('Controller', 'App\Controller\PostsController', 'TestCase/Controller/PostsControllerTest.php'),
  485. array('Controller', 'App\Controller\Admin\PostsController', 'TestCase/Controller/Admin/PostsControllerTest.php'),
  486. array('Behavior', 'App\Model\Behavior\TreeBehavior', 'TestCase/Model/Behavior/TreeBehaviorTest.php'),
  487. array('Component', 'App\Controller\Component\AuthComponent', 'TestCase/Controller/Component/AuthComponentTest.php'),
  488. array('entity', 'App\Model\Entity\Article', 'TestCase/Model/Entity/ArticleTest.php'),
  489. array('table', 'App\Model\Table\PostsTable', 'TestCase/Model/Table/PostsTableTest.php'),
  490. array('helper', 'App\View\Helper\FormHelper', 'TestCase/View/Helper/FormHelperTest.php'),
  491. array('controller', 'App\Controller\PostsController', 'TestCase/Controller/PostsControllerTest.php'),
  492. array('behavior', 'App\Model\Behavior\TreeBehavior', 'TestCase/Model/Behavior/TreeBehaviorTest.php'),
  493. array('component', 'App\Controller\Component\AuthComponent', 'TestCase/Controller/Component/AuthComponentTest.php'),
  494. ['Shell', 'App\Shell\ExampleShell', 'TestCase/Shell/ExampleShellTest.php'],
  495. ['shell', 'App\Shell\ExampleShell', 'TestCase/Shell/ExampleShellTest.php'],
  496. );
  497. }
  498. /**
  499. * Test filename generation for each type + plugins
  500. *
  501. * @dataProvider caseFileNameProvider
  502. * @return void
  503. */
  504. public function testTestCaseFileName($type, $class, $expected) {
  505. $result = $this->Task->testCaseFileName($type, $class);
  506. $expected = ROOT . DS . 'tests/' . $expected;
  507. $this->assertPathEquals($expected, $result);
  508. }
  509. /**
  510. * Test filename generation for plugins.
  511. *
  512. * @return void
  513. */
  514. public function testTestCaseFileNamePlugin() {
  515. $this->Task->path = DS . 'my/path/tests/';
  516. Plugin::load('TestPlugin');
  517. $this->Task->plugin = 'TestPlugin';
  518. $class = 'TestPlugin\Model\Entity\Post';
  519. $result = $this->Task->testCaseFileName('entity', $class);
  520. $expected = TEST_APP . 'Plugin/TestPlugin/tests/TestCase/Model/Entity/PostTest.php';
  521. $this->assertPathEquals($expected, $result);
  522. }
  523. /**
  524. * Data provider for mapType() tests.
  525. *
  526. * @return array
  527. */
  528. public static function mapTypeProvider() {
  529. return array(
  530. array('controller', 'Controller'),
  531. array('Controller', 'Controller'),
  532. array('component', 'Controller\Component'),
  533. array('Component', 'Controller\Component'),
  534. array('table', 'Model\Table'),
  535. array('Table', 'Model\Table'),
  536. array('entity', 'Model\Entity'),
  537. array('Entity', 'Model\Entity'),
  538. array('behavior', 'Model\Behavior'),
  539. array('Behavior', 'Model\Behavior'),
  540. array('helper', 'View\Helper'),
  541. array('Helper', 'View\Helper'),
  542. array('Helper', 'View\Helper'),
  543. );
  544. }
  545. /**
  546. * Test that mapType returns the correct package names.
  547. *
  548. * @dataProvider mapTypeProvider
  549. * @return void
  550. */
  551. public function testMapType($original, $expected) {
  552. $this->assertEquals($expected, $this->Task->mapType($original));
  553. }
  554. }