Просмотр исходного кода

Concat*Fixer - unify concat fixers

SpacePossum 8 лет назад
Родитель
Сommit
bc324beef0

+ 3 - 5
README.rst

@@ -210,11 +210,9 @@ Choose from the list of available rules:
 * **combine_consecutive_unsets**
    | Calling unset on multiple items should be done in one call.
 
-* **concat_with_spaces**
-   | Concatenation should be used with at least one whitespace around.
-
-* **concat_without_spaces** [@Symfony]
-   | Concatenation should be used without spaces.
+* **concat_space** [@Symfony]
+   | Concatenation should be spaced according configuration.
+   | *Rule is: configurable.*
 
 * **declare_equal_normalize** [@Symfony]
    | Equal sign in declare statement should not be surrounded by spaces.

+ 138 - 0
src/Fixer/Operator/ConcatSpaceFixer.php

@@ -0,0 +1,138 @@
+<?php
+
+/*
+ * This file is part of PHP CS Fixer.
+ *
+ * (c) Fabien Potencier <fabien@symfony.com>
+ *     Dariusz Rumiński <dariusz.ruminski@gmail.com>
+ *
+ * This source file is subject to the MIT license that is bundled
+ * with this source code in the file LICENSE.
+ */
+
+namespace PhpCsFixer\Fixer\Operator;
+
+use PhpCsFixer\AbstractFixer;
+use PhpCsFixer\ConfigurationException\InvalidFixerConfigurationException;
+use PhpCsFixer\Tokenizer\Token;
+use PhpCsFixer\Tokenizer\Tokens;
+
+/**
+ * @author Dariusz Rumiński <dariusz.ruminski@gmail.com>
+ * @author SpacePossum
+ */
+final class ConcatSpaceFixer extends AbstractFixer
+{
+    private $fixCallback;
+
+    /**
+     * Configuration must have one element 'spacing' with value 'none' (default) or 'one'.
+     *
+     * @param null|array $configuration
+     */
+    public function configure(array $configuration = null)
+    {
+        if (null === $configuration) {
+            $this->fixCallback = 'fixConcatenationToNoSpace';
+
+            return;
+        }
+
+        if (!array_key_exists('spacing', $configuration)) {
+            throw new InvalidFixerConfigurationException($this->getName(), 'Missing "spacing" configuration.');
+        }
+
+        switch ($configuration['spacing']) {
+            case 'one':
+                $this->fixCallback = 'fixConcatenationToSingleSpace';
+
+                break;
+            case 'none':
+                $this->fixCallback = 'fixConcatenationToNoSpace';
+
+                break;
+            default:
+                throw new InvalidFixerConfigurationException($this->getName(), '"spacing" configuration must be "one" or "none".');
+        }
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function fix(\SplFileInfo $file, Tokens $tokens)
+    {
+        $callBack = $this->fixCallback;
+        for ($index = $tokens->count() - 1; $index >= 0; --$index) {
+            if ($tokens[$index]->equals('.')) {
+                $this->$callBack($tokens, $index);
+            }
+        }
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function getDescription()
+    {
+        return 'Concatenation should be spaced according configuration.';
+    }
+
+    /**
+     * {@inheritdoc}
+     */
+    public function isCandidate(Tokens $tokens)
+    {
+        return $tokens->isTokenKindFound('.');
+    }
+
+    /**
+     * @param Tokens $tokens
+     * @param int    $index  index of concatenation '.' token
+     */
+    private function fixConcatenationToNoSpace(Tokens $tokens, $index)
+    {
+        if (!$tokens[$tokens->getPrevNonWhitespace($index)]->isGivenKind(T_LNUMBER)) {
+            $tokens->removeLeadingWhitespace($index, " \t");
+        }
+
+        if (!$tokens[$tokens->getNextNonWhitespace($index)]->isGivenKind(array(T_LNUMBER, T_COMMENT, T_DOC_COMMENT))) {
+            $tokens->removeTrailingWhitespace($index, " \t");
+        }
+    }
+
+    /**
+     * @param Tokens $tokens
+     * @param int    $index  index of concatenation '.' token
+     */
+    private function fixConcatenationToSingleSpace(Tokens $tokens, $index)
+    {
+        $this->fixWhiteSpaceAroundConcatToken($tokens, $index, 1);
+        $this->fixWhiteSpaceAroundConcatToken($tokens, $index, -1);
+    }
+
+    /**
+     * @param Tokens $tokens
+     * @param int    $index  index of concatenation '.' token
+     * @param int    $offset 1 or -1
+     */
+    private function fixWhiteSpaceAroundConcatToken(Tokens $tokens, $index, $offset)
+    {
+        $offsetIndex = $index + $offset;
+
+        if (!$tokens[$offsetIndex]->isWhitespace()) {
+            $tokens->insertAt($index + (1 === $offset ?: 0), new Token(array(T_WHITESPACE, ' ')));
+
+            return;
+        }
+
+        if (false !== strpos($tokens[$offsetIndex]->getContent(), "\n")) {
+            return;
+        }
+
+        if ($tokens[$index + $offset * 2]->isComment()) {
+            return;
+        }
+
+        $tokens[$offsetIndex]->setContent(' ');
+    }
+}

+ 0 - 89
src/Fixer/Operator/ConcatWithSpacesFixer.php

@@ -1,89 +0,0 @@
-<?php
-
-/*
- * This file is part of PHP CS Fixer.
- *
- * (c) Fabien Potencier <fabien@symfony.com>
- *     Dariusz Rumiński <dariusz.ruminski@gmail.com>
- *
- * This source file is subject to the MIT license that is bundled
- * with this source code in the file LICENSE.
- */
-
-namespace PhpCsFixer\Fixer\Operator;
-
-use PhpCsFixer\AbstractFixer;
-use PhpCsFixer\Tokenizer\Token;
-use PhpCsFixer\Tokenizer\Tokens;
-
-/**
- * @author Dariusz Rumiński <dariusz.ruminski@gmail.com>
- */
-final class ConcatWithSpacesFixer extends AbstractFixer
-{
-    /**
-     * {@inheritdoc}
-     */
-    public function isCandidate(Tokens $tokens)
-    {
-        return $tokens->isTokenKindFound('.');
-    }
-
-    /**
-     * {@inheritdoc}
-     */
-    public function fix(\SplFileInfo $file, Tokens $tokens)
-    {
-        for ($index = $tokens->count() - 1; $index >= 0; --$index) {
-            if (!$tokens[$index]->equals('.')) {
-                continue;
-            }
-
-            $this->fixWhiteSpaceAroundConcatToken($tokens, $index, 1);
-            $this->fixWhiteSpaceAroundConcatToken($tokens, $index, -1);
-        }
-    }
-
-    /**
-     * {@inheritdoc}
-     */
-    public function getDescription()
-    {
-        return 'Concatenation should be used with at least one whitespace around.';
-    }
-
-    /**
-     * {@inheritdoc}
-     */
-    public function getPriority()
-    {
-        // should be run after the ConcatWithoutSpacesFixer
-        return -10;
-    }
-
-    /**
-     * @param Tokens $tokens
-     * @param int    $index  Index of concat token
-     * @param int    $offset 1 or -1
-     */
-    private function fixWhiteSpaceAroundConcatToken(Tokens $tokens, $index, $offset)
-    {
-        $offsetIndex = $index + $offset;
-
-        if (!$tokens[$offsetIndex]->isWhitespace()) {
-            $tokens->insertAt($index + (1 === $offset ?: 0), new Token(array(T_WHITESPACE, ' ')));
-
-            return;
-        }
-
-        if (false !== strpos($tokens[$offsetIndex]->getContent(), "\n")) {
-            return;
-        }
-
-        if ($tokens[$index + $offset * 2]->isComment()) {
-            return;
-        }
-
-        $tokens[$offsetIndex]->setContent(' ');
-    }
-}

+ 0 - 58
src/Fixer/Operator/ConcatWithoutSpacesFixer.php

@@ -1,58 +0,0 @@
-<?php
-
-/*
- * This file is part of PHP CS Fixer.
- *
- * (c) Fabien Potencier <fabien@symfony.com>
- *     Dariusz Rumiński <dariusz.ruminski@gmail.com>
- *
- * This source file is subject to the MIT license that is bundled
- * with this source code in the file LICENSE.
- */
-
-namespace PhpCsFixer\Fixer\Operator;
-
-use PhpCsFixer\AbstractFixer;
-use PhpCsFixer\Tokenizer\Tokens;
-
-/**
- * @author Dariusz Rumiński <dariusz.ruminski@gmail.com>
- */
-final class ConcatWithoutSpacesFixer extends AbstractFixer
-{
-    /**
-     * {@inheritdoc}
-     */
-    public function isCandidate(Tokens $tokens)
-    {
-        return $tokens->isTokenKindFound('.');
-    }
-
-    /**
-     * {@inheritdoc}
-     */
-    public function fix(\SplFileInfo $file, Tokens $tokens)
-    {
-        foreach ($tokens as $index => $token) {
-            if (!$token->equals('.')) {
-                continue;
-            }
-
-            if (!$tokens[$tokens->getPrevNonWhitespace($index)]->isGivenKind(T_LNUMBER)) {
-                $tokens->removeLeadingWhitespace($index, " \t");
-            }
-
-            if (!$tokens[$tokens->getNextNonWhitespace($index)]->isGivenKind(array(T_LNUMBER, T_COMMENT, T_DOC_COMMENT))) {
-                $tokens->removeTrailingWhitespace($index, " \t");
-            }
-        }
-    }
-
-    /**
-     * {@inheritdoc}
-     */
-    public function getDescription()
-    {
-        return 'Concatenation should be used without spaces.';
-    }
-}

+ 0 - 1
src/FixerFactory.php

@@ -231,7 +231,6 @@ final class FixerFactory
     private function getFixersConflicts(FixerInterface $fixer)
     {
         static $conflictMap = array(
-            'concat_with_spaces' => array('concat_without_spaces'),
             'echo_to_print' => array('print_to_echo'),
             'no_blank_lines_before_namespace' => array('single_blank_line_before_namespace'),
         );

+ 1 - 1
src/RuleSet.php

@@ -61,7 +61,7 @@ final class RuleSet implements RuleSetInterface
             'blank_line_before_return' => true,
             'cast_spaces' => true,
             'class_definition' => array('singleLine' => true),
-            'concat_without_spaces' => true,
+            'concat_space' => array('spacing' => 'none'),
             'declare_equal_normalize' => true,
             'function_typehint_space' => true,
             'hash_to_slash_comment' => true,

+ 92 - 4
tests/Fixer/Operator/ConcatWithoutSpacesFixerTest.php → tests/Fixer/Operator/ConcatSpaceFixerTest.php

@@ -16,23 +16,43 @@ use PhpCsFixer\Test\AbstractFixerTestCase;
 
 /**
  * @author Dariusz Rumiński <dariusz.ruminski@gmail.com>
+ * @author SpacePossum
  *
  * @internal
  */
-final class ConcatWithoutSpacesFixerTest extends AbstractFixerTestCase
+final class ConcatSpaceFixerTest extends AbstractFixerTestCase
 {
+    /**
+     * @expectedException \PhpCsFixer\ConfigurationException\InvalidFixerConfigurationException
+     * @expectedExceptionMessageRegExp #^\[concat_space\] Missing "spacing" configuration.$#
+     */
+    public function testInvalidConfigMissingKey()
+    {
+        $this->fixer->configure(array('a' => 1));
+    }
+
+    /**
+     * @expectedException \PhpCsFixer\ConfigurationException\InvalidFixerConfigurationException
+     * @expectedExceptionMessageRegExp #^\[concat_space\] "spacing" configuration must be "one" or "none".$#
+     */
+    public function testInvalidConfigValue()
+    {
+        $this->fixer->configure(array('spacing' => 'tabs'));
+    }
+
     /**
      * @param string      $expected
      * @param null|string $input
      *
-     * @dataProvider provideCases
+     * @dataProvider provideWithoutSpaceCases
      */
-    public function testFix($expected, $input = null)
+    public function testFixWithoutSpace($expected, $input = null)
     {
+        $this->fixer->configure(array('spacing' => 'none'));
         $this->doTest($expected, $input);
     }
 
-    public function provideCases()
+    public function provideWithoutSpaceCases()
     {
         return array(
             array(
@@ -121,4 +141,72 @@ final class ConcatWithoutSpacesFixerTest extends AbstractFixerTestCase
             ),
         );
     }
+
+    /**
+     * @param string      $expected
+     * @param null|string $input
+     *
+     * @dataProvider provideWithSpaceCases
+     */
+    public function testFixWithSpace($expected, $input = null)
+    {
+        $this->fixer->configure(array('spacing' => 'one'));
+        $this->doTest($expected, $input);
+    }
+
+    public function provideWithSpaceCases()
+    {
+        return array(
+            array(
+                '<?php
+                    $a =   //
+                    $c .   /**/
+                    $d     #
+                    . $e   /**  */
+                    . $f . //
+                    $z;
+                ',
+                '<?php
+                    $a =   //
+                    $c   .   /**/
+                    $d     #
+                    .   $e   /**  */
+                    .   $f   . //
+                    $z;
+                ',
+            ),
+            array(
+                '<?php $foo = "a" . \'b\' . "c" . "d" . $e . ($f + 1);',
+                '<?php $foo = "a" . \'b\' ."c". "d"    .  $e.($f + 1);',
+            ),
+            array(
+                '<?php $foo = "a" .
+"b";',
+                '<?php $foo = "a".
+"b";',
+            ),
+            array(
+                '<?php $a = "foobar"
+    . "baz";',
+                '<?php $a = "foobar"
+    ."baz";',
+            ),
+            array(
+                '<?php echo $a . $b;
+                    echo $d . $e .   //
+                        $f;
+                    echo $a . $b?>
+                 <?php
+                    echo $c;
+                ',
+                '<?php echo $a.$b;
+                    echo $d    .            $e          .   //
+                        $f;
+                    echo $a   .                  $b?>
+                 <?php
+                    echo $c;
+                ',
+            ),
+        );
+    }
 }

+ 0 - 90
tests/Fixer/Operator/ConcatWithSpacesFixerTest.php

@@ -1,90 +0,0 @@
-<?php
-
-/*
- * This file is part of PHP CS Fixer.
- *
- * (c) Fabien Potencier <fabien@symfony.com>
- *     Dariusz Rumiński <dariusz.ruminski@gmail.com>
- *
- * This source file is subject to the MIT license that is bundled
- * with this source code in the file LICENSE.
- */
-
-namespace PhpCsFixer\Tests\Fixer\Operator;
-
-use PhpCsFixer\Test\AbstractFixerTestCase;
-
-/**
- * @author Dariusz Rumiński <dariusz.ruminski@gmail.com>
- *
- * @internal
- */
-final class ConcatWithSpacesFixerTest extends AbstractFixerTestCase
-{
-    /**
-     * @param string      $expected
-     * @param null|string $input
-     *
-     * @dataProvider provideCases
-     */
-    public function testFix($expected, $input = null)
-    {
-        $this->doTest($expected, $input);
-    }
-
-    public function provideCases()
-    {
-        return array(
-            array(
-                '<?php
-                    $a =   //
-                    $c .   /**/
-                    $d     #
-                    . $e   /**  */
-                    . $f . //
-                    $z;
-                ',
-                '<?php
-                    $a =   //
-                    $c   .   /**/
-                    $d     #
-                    .   $e   /**  */
-                    .   $f   . //
-                    $z;
-                ',
-            ),
-            array(
-                '<?php $foo = "a" . \'b\' . "c" . "d" . $e . ($f + 1);',
-                '<?php $foo = "a" . \'b\' ."c". "d"    .  $e.($f + 1);',
-            ),
-            array(
-                '<?php $foo = "a" .
-"b";',
-                '<?php $foo = "a".
-"b";',
-            ),
-            array(
-                '<?php $a = "foobar"
-    . "baz";',
-                '<?php $a = "foobar"
-    ."baz";',
-            ),
-            array(
-                '<?php echo $a . $b;
-                    echo $d . $e .   //
-                        $f;
-                    echo $a . $b?>
-                 <?php
-                    echo $c;
-                ',
-                '<?php echo $a.$b;
-                    echo $d    .            $e          .   //
-                        $f;
-                    echo $a   .                  $b?>
-                 <?php
-                    echo $c;
-                ',
-            ),
-        );
-    }
-}

+ 2 - 3
tests/FixerFactoryTest.php

@@ -195,7 +195,6 @@ final class FixerFactoryTest extends \PHPUnit_Framework_TestCase
         }
 
         $cases = array(
-            array($fixers['concat_without_spaces'], $fixers['concat_with_spaces']),
             array($fixers['elseif'], $fixers['braces']),
             array($fixers['method_separation'], $fixers['braces']),
             array($fixers['method_separation'], $fixers['indentation_type']),
@@ -408,8 +407,8 @@ final class FixerFactoryTest extends \PHPUnit_Framework_TestCase
     public function provideConflictingFixersRules()
     {
         return array(
-            array(new RuleSet(array('concat_with_spaces' => true, 'concat_without_spaces' => true))),
-            array(new RuleSet(array('concat_without_spaces' => true, 'concat_with_spaces' => true))),
+            array(new RuleSet(array('echo_to_print' => true, 'print_to_echo' => true))),
+            array(new RuleSet(array('print_to_echo' => true, 'echo_to_print' => true))),
         );
     }
 

+ 1 - 1
tests/Fixtures/.php_cs_custom.php

@@ -108,7 +108,7 @@ final class CustomConfig implements ConfigInterface
      */
     public function getRules()
     {
-        return array('concat_without_spaces' => true);
+        return array('concat_space' => array('spacing' => 'none'));
     }
 
     /**

Некоторые файлы не были показаны из-за большого количества измененных файлов