MethodSeparationFixerTest.php 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878
  1. <?php
  2. /*
  3. * This file is part of PHP CS Fixer.
  4. *
  5. * (c) Fabien Potencier <fabien@symfony.com>
  6. * Dariusz Rumiński <dariusz.ruminski@gmail.com>
  7. *
  8. * This source file is subject to the MIT license that is bundled
  9. * with this source code in the file LICENSE.
  10. */
  11. namespace PhpCsFixer\Tests\Fixer\ClassNotation;
  12. use PhpCsFixer\Test\AbstractFixerTestCase;
  13. use PhpCsFixer\Tokenizer\Tokens;
  14. use PhpCsFixer\WhitespacesFixerConfig;
  15. /**
  16. * @internal
  17. *
  18. * @covers \PhpCsFixer\Fixer\ClassNotation\MethodSeparationFixer
  19. */
  20. final class MethodSeparationFixerTest extends AbstractFixerTestCase
  21. {
  22. /**
  23. * @param int $expected
  24. * @param string $code
  25. * @param int $index
  26. *
  27. * @dataProvider provideCommentBlockStartDetectionCases
  28. */
  29. public function testCommentBlockStartDetection($expected, $code, $index)
  30. {
  31. Tokens::clearCache();
  32. $tokens = Tokens::fromCode($code);
  33. $method = new \ReflectionMethod($this->fixer, 'findCommentBlockStart');
  34. $method->setAccessible(true);
  35. if ($expected !== $result = $method->invoke($this->fixer, $tokens, $index)) {
  36. $this->fail(sprintf('Expected index %d (%s) got index %d (%s).', $expected, $tokens[$expected]->toJson(), $result, $tokens[$result]->toJson()));
  37. }
  38. }
  39. public function provideCommentBlockStartDetectionCases()
  40. {
  41. return array(
  42. array(
  43. 4,
  44. '<?php
  45. //ui
  46. //j1
  47. //k2
  48. ',
  49. 6,
  50. ),
  51. array(
  52. 4,
  53. '<?php
  54. //ui
  55. //j1
  56. //k2
  57. ',
  58. 5,
  59. ),
  60. array(
  61. 4,
  62. '<?php
  63. /**/
  64. //j1
  65. //k2
  66. ',
  67. 6,
  68. ),
  69. array(
  70. 4,
  71. '<?php
  72. $a;//j
  73. //k
  74. ',
  75. 6,
  76. ),
  77. array(
  78. 2,
  79. '<?php
  80. //a
  81. ',
  82. 2,
  83. ),
  84. array(
  85. 2,
  86. '<?php
  87. //b
  88. //c
  89. ',
  90. 2,
  91. ),
  92. array(
  93. 2,
  94. '<?php
  95. //d
  96. //e
  97. ',
  98. 4,
  99. ),
  100. array(
  101. 2,
  102. '<?php
  103. /**/
  104. //f
  105. //g
  106. //h
  107. ',
  108. 8,
  109. ),
  110. );
  111. }
  112. /**
  113. * @param string $expected
  114. * @param null|string $input
  115. *
  116. * @dataProvider provideFixClassesCases
  117. */
  118. public function testFixClasses($expected, $input = null)
  119. {
  120. $this->doTest($expected, $input);
  121. }
  122. public function provideFixClassesCases()
  123. {
  124. $cases = array();
  125. $cases[] = array('<?php
  126. class SomeClass1
  127. {
  128. // This comment
  129. // is multiline.
  130. public function echoA()
  131. {
  132. echo "a";
  133. }
  134. }
  135. ');
  136. $cases[] = array(
  137. '<?php
  138. class SomeClass2
  139. {
  140. // This comment
  141. /* is multiline. */
  142. public function echoA()
  143. {
  144. echo "a";
  145. }
  146. }
  147. ',
  148. '<?php
  149. class SomeClass2
  150. {
  151. // This comment
  152. /* is multiline. */public function echoA()
  153. {
  154. echo "a";
  155. }
  156. }
  157. ',
  158. );
  159. $cases[] = array(
  160. '<?php
  161. class SomeClass3
  162. {
  163. // This comment
  164. // is multiline.
  165. public function echoA()
  166. {
  167. echo "a";
  168. }
  169. }
  170. ', );
  171. $cases[] = array(
  172. '<?php
  173. class SomeClass1
  174. {
  175. private $a; //
  176. public function methodA()
  177. {
  178. }
  179. private $b;
  180. //
  181. public function methodB()
  182. {
  183. }
  184. // C
  185. public function methodC()
  186. {
  187. }
  188. // D
  189. public function methodD()
  190. {
  191. }
  192. /* E */
  193. public function methodE()
  194. {
  195. }
  196. /* F */
  197. public function methodF()
  198. {
  199. }
  200. }
  201. ',
  202. '<?php
  203. class SomeClass1
  204. {
  205. private $a; //
  206. public function methodA()
  207. {
  208. }
  209. private $b;
  210. //
  211. public function methodB()
  212. {
  213. }
  214. // C
  215. public function methodC()
  216. {
  217. }
  218. // D
  219. public function methodD()
  220. {
  221. }
  222. /* E */
  223. public function methodE()
  224. {
  225. }
  226. /* F */
  227. public function methodF()
  228. {
  229. }
  230. }
  231. ', );
  232. $cases[] = array('<?php
  233. class SomeClass
  234. {
  235. // comment
  236. public function echoA()
  237. {
  238. echo "a";
  239. }
  240. }
  241. ');
  242. $cases[] = array('<?php
  243. class SomeClass
  244. {
  245. // This comment
  246. // is multiline.
  247. public function echoA()
  248. {
  249. echo "a";
  250. }
  251. }
  252. ');
  253. $cases[] = array(
  254. '<?php
  255. class SomeClass
  256. {
  257. // comment
  258. public function echoA()
  259. {
  260. echo "a";
  261. }
  262. }
  263. ',
  264. '<?php
  265. class SomeClass
  266. {
  267. // comment
  268. public function echoA()
  269. {
  270. echo "a";
  271. }
  272. }
  273. ',
  274. );
  275. $cases[] = array(
  276. '<?php
  277. class SomeClass
  278. {
  279. /* comment */
  280. public function echoB()
  281. {
  282. echo "a";
  283. }
  284. }
  285. ',
  286. '<?php
  287. class SomeClass
  288. {
  289. /* comment */public function echoB()
  290. {
  291. echo "a";
  292. }
  293. }
  294. ',
  295. );
  296. $cases[] = array(
  297. '<?php
  298. class SomeClass
  299. {
  300. /* comment */
  301. public function echoC()
  302. {
  303. echo "a";
  304. }
  305. }
  306. ',
  307. '<?php
  308. class SomeClass
  309. {
  310. /* comment */ public function echoC()
  311. {
  312. echo "a";
  313. }
  314. }
  315. ',
  316. );
  317. $cases[] = array(
  318. '<?php
  319. abstract class MethodTest2
  320. {
  321. public function method045()
  322. {
  323. $files = null;
  324. if (!empty($files)) {
  325. $this->filter(
  326. function (\SplFileInfo $file) use ($files) {
  327. return !in_array($file->getRelativePathname(), $files, true);
  328. }
  329. );
  330. }
  331. }
  332. private $a;
  333. public static function method145()
  334. {
  335. }
  336. abstract protected function method245();
  337. // comment
  338. final private function method345()
  339. {
  340. }
  341. }
  342. function test1(){ echo 1;}
  343. function test2(){ echo 2;}',
  344. '<?php
  345. abstract class MethodTest2
  346. {
  347. public function method045()
  348. {
  349. $files = null;
  350. if (!empty($files)) {
  351. $this->filter(
  352. function (\SplFileInfo $file) use ($files) {
  353. return !in_array($file->getRelativePathname(), $files, true);
  354. }
  355. );
  356. }
  357. }
  358. private $a;
  359. public static function method145()
  360. {
  361. }
  362. abstract protected function method245();
  363. // comment
  364. final private function method345()
  365. {
  366. }
  367. }
  368. function test1(){ echo 1;}
  369. function test2(){ echo 2;}',
  370. );
  371. $cases[] = array(
  372. '<?php
  373. /*
  374. * This file is part of the PHP CS utility.
  375. *
  376. * (c) Fabien Potencier <fabien@symfony.com>
  377. *
  378. * This source file is subject to the MIT license that is bundled
  379. * with this source code in the file LICENSE.
  380. */
  381. namespace PhpCsFixer\Linter;
  382. /**
  383. * Dummy linter. No linting is performed. No error is raised.
  384. *
  385. * @author Dariusz Rumiński <dariusz.ruminski@gmail.com>
  386. *
  387. * @internal
  388. */
  389. final class NullLinter implements LinterInterface
  390. {
  391. /**
  392. * {@inheritdoc}
  393. */
  394. public function lintFile($path)
  395. {
  396. unset($path);
  397. }
  398. /**
  399. * {@inheritdoc}
  400. */
  401. public function lintSource($source)
  402. {
  403. unset($source);
  404. }
  405. }
  406. ',
  407. );
  408. // do not touch anonymous functions (since PHP doesn't allow
  409. // for class attributes being functions :(, we only have to test
  410. // those used within methods)
  411. $cases[] = array(
  412. '<?php
  413. class MethodTestAnonymous
  414. {
  415. public function method444a()
  416. {
  417. $text = "hello";
  418. $example = function ($arg) use ($message) {
  419. var_dump($arg . " " . $message);
  420. };
  421. $example($text);
  422. $example = function($arg) use ($message) {
  423. var_dump($arg . " " . $message);
  424. };
  425. $example = function /*test*/ ($arg) use ($message) {
  426. var_dump($arg . " " . $message);
  427. };
  428. }
  429. }',
  430. );
  431. $cases[] = array(
  432. '<?php
  433. class MethodTest1
  434. {
  435. private $c; //
  436. public function method444a()
  437. {
  438. }
  439. /**
  440. *
  441. */
  442. public function method444b()
  443. {
  444. }
  445. //
  446. public function method444c()
  447. {
  448. }
  449. private $a;
  450. public function method444d()
  451. {
  452. }
  453. private $b;
  454. //
  455. public function method444e()
  456. {
  457. }
  458. public function method444f()
  459. {
  460. }
  461. private $d; //
  462. public function method444f1()
  463. {
  464. }
  465. /**/
  466. public function method444g()
  467. {
  468. }
  469. }',
  470. '<?php
  471. class MethodTest1
  472. {
  473. private $c; //
  474. public function method444a()
  475. {
  476. }
  477. /**
  478. *
  479. */
  480. public function method444b()
  481. {
  482. }
  483. //
  484. public function method444c()
  485. {
  486. }
  487. private $a;
  488. public function method444d()
  489. {
  490. }
  491. private $b;
  492. //
  493. public function method444e()
  494. {
  495. }
  496. public function method444f()
  497. {
  498. }
  499. private $d; //
  500. public function method444f1()
  501. {
  502. }
  503. /**/
  504. public function method444g()
  505. {
  506. }
  507. }',
  508. );
  509. // spaces between methods
  510. $cases[] = array(
  511. '<?php
  512. abstract class MethodTest3
  513. {
  514. public function method021()
  515. {
  516. }
  517. public static function method121()
  518. {
  519. }
  520. abstract protected function method221(); '.'
  521. final private function method321a()
  522. {
  523. }
  524. }',
  525. '<?php
  526. abstract class MethodTest3
  527. {
  528. public function method021()
  529. {
  530. }
  531. public static function method121()
  532. {
  533. }
  534. abstract protected function method221();
  535. '.'
  536. final private function method321a()
  537. {
  538. }
  539. }', );
  540. // don't change correct code
  541. $cases[] = array(
  542. '<?php
  543. class SmallHelperException extends \Exception
  544. {
  545. public function getId111()
  546. {
  547. return 1;
  548. }
  549. public function getMessage111()
  550. {
  551. return \'message\';
  552. }
  553. }
  554. class MethodTest123124124
  555. {
  556. public function method111a(){}
  557. public function method211a(){}
  558. }',
  559. );
  560. // do not touch function out of class scope
  561. $cases[] = array(
  562. '<?php
  563. function test0() {
  564. }
  565. class MethodTest4
  566. {
  567. public function method122b()
  568. {
  569. }
  570. public function method222b()
  571. {
  572. }
  573. }
  574. function test() {
  575. }
  576. function test2() {
  577. }
  578. ',
  579. );
  580. return $cases;
  581. }
  582. /**
  583. * @param string $expected
  584. * @param null|string $input
  585. *
  586. * @requires PHP 5.4
  587. * @dataProvider provideFixTraitsCases
  588. */
  589. public function testFixTraits($expected, $input = null)
  590. {
  591. $this->doTest($expected, $input);
  592. }
  593. public function provideFixTraitsCases()
  594. {
  595. $cases = array();
  596. // do not touch well formatted traits
  597. $cases[] = array(
  598. '<?php
  599. trait OkTrait
  600. {
  601. function getReturnTypeOk()
  602. {
  603. }
  604. /**
  605. *
  606. */
  607. function getReturnDescriptionOk()
  608. {
  609. }
  610. }',
  611. );
  612. $cases[] = array(
  613. '<?php
  614. trait ezcReflectionReturnInfo {
  615. public $x = 1;
  616. protected function getA(){echo 1;}
  617. function getB(){echo 2;}
  618. protected function getC(){echo 3;}
  619. /** Description */
  620. function getD(){echo 4;}
  621. protected function getE(){echo 3;}
  622. private $a;
  623. function getF(){echo 4;}
  624. }',
  625. '<?php
  626. trait ezcReflectionReturnInfo {
  627. public $x = 1;
  628. protected function getA(){echo 1;}function getB(){echo 2;}
  629. protected function getC(){echo 3;}/** Description */function getD(){echo 4;}
  630. protected function getE(){echo 3;}private $a;function getF(){echo 4;}
  631. }',
  632. );
  633. $cases[] = array(
  634. '<?php
  635. trait SomeReturnInfo {
  636. function getReturnType()
  637. {
  638. }
  639. function getReturnDescription()
  640. {
  641. }
  642. function getReturnDescription2()
  643. {
  644. }
  645. abstract public function getWorld();
  646. }',
  647. '<?php
  648. trait SomeReturnInfo {
  649. function getReturnType()
  650. {
  651. }
  652. function getReturnDescription()
  653. {
  654. } function getReturnDescription2()
  655. {
  656. }
  657. abstract public function getWorld();
  658. }',
  659. );
  660. return $cases;
  661. }
  662. /**
  663. * @param string $expected
  664. * @param null|string $input
  665. *
  666. * @dataProvider provideFixInterfaces
  667. */
  668. public function testFixInterfaces($expected, $input = null)
  669. {
  670. $this->doTest($expected, $input);
  671. }
  672. public function provideFixInterfaces()
  673. {
  674. $cases = array();
  675. $cases[] = array(
  676. '<?php
  677. interface TestInterface
  678. {
  679. public function testInterfaceMethod4();
  680. public function testInterfaceMethod5();
  681. /**
  682. * {@link}
  683. */ '.'
  684. public function testInterfaceMethod6();
  685. public function testInterfaceMethod7();
  686. public function testInterfaceMethod8();
  687. }',
  688. '<?php
  689. interface TestInterface
  690. { public function testInterfaceMethod4();
  691. public function testInterfaceMethod5();
  692. /**
  693. * {@link}
  694. */ '.'
  695. public function testInterfaceMethod6();
  696. public function testInterfaceMethod7(); public function testInterfaceMethod8();
  697. }',
  698. );
  699. // do not touch well formatted interfaces
  700. $cases[] = array(
  701. '<?php
  702. interface TestInterfaceOK
  703. {
  704. public function testMethod1();
  705. public function testMethod2();
  706. }',
  707. );
  708. // method after trait use
  709. $cases[] = array(
  710. '<?php
  711. trait ezcReflectionReturnInfo {
  712. function getReturnDescription() {}
  713. }
  714. class ezcReflectionMethod extends ReflectionMethod {
  715. use ezcReflectionReturnInfo;
  716. function afterUseTrait(){}
  717. function afterUseTrait2(){}
  718. }',
  719. '<?php
  720. trait ezcReflectionReturnInfo {
  721. function getReturnDescription() {}
  722. }
  723. class ezcReflectionMethod extends ReflectionMethod {
  724. use ezcReflectionReturnInfo;function afterUseTrait(){}function afterUseTrait2(){}
  725. }',
  726. );
  727. return $cases;
  728. }
  729. /**
  730. * @param string $expected
  731. * @param null|string $input
  732. *
  733. * @dataProvider provideMessyWhitespacesCases
  734. */
  735. public function testMessyWhitespaces($expected, $input = null)
  736. {
  737. $this->fixer->setWhitespacesConfig(new WhitespacesFixerConfig("\t", "\r\n"));
  738. $this->doTest($expected, $input);
  739. }
  740. public function provideMessyWhitespacesCases()
  741. {
  742. return array(
  743. array(
  744. "<?php\r\nclass SomeClass\r\n{\r\n // comment\n\n public function echoA()\r\n {\r\n echo 'a';\r\n }\r\n}\r\n",
  745. "<?php\r\nclass SomeClass\r\n{\r\n // comment\n\n\n public function echoA()\r\n {\r\n echo 'a';\r\n }\r\n}\r\n",
  746. ),
  747. array(
  748. "<?php\r\nclass SomeClass\r\n{\r\n // comment\r\n\r\n public function echoA()\r\n {\r\n echo 'a';\r\n }\r\n}\r\n",
  749. "<?php\r\nclass SomeClass\r\n{\r\n // comment\r\n\r\n\r\n public function echoA()\r\n {\r\n echo 'a';\r\n }\r\n}\r\n",
  750. ),
  751. );
  752. }
  753. }