Browse Source

fix: `NullableTypeDeclarationFixer` - do not break syntax when there is no space before `?` (#8224)

Kuba Werłos 5 months ago
parent
commit
fa0938fd66

+ 5 - 1
src/Fixer/LanguageConstruct/NullableTypeDeclarationFixer.php

@@ -94,7 +94,7 @@ class ValueObject
      * {@inheritdoc}
      *
      * Must run before OrderedTypesFixer, TypesSpacesFixer.
-     * Must run after NullableTypeDeclarationForDefaultNullValueFixer, SingleSpaceAroundConstructFixer.
+     * Must run after NullableTypeDeclarationForDefaultNullValueFixer.
      */
     public function getPriority(): int
     {
@@ -273,6 +273,10 @@ class ValueObject
             $typeAnalysis->getEndIndex(),
             $this->createTypeDeclarationTokens($normalizedType, $isQuestionMarkSyntax)
         );
+
+        if (!$tokens[$typeAnalysis->getStartIndex() - 1]->equals('(')) {
+            $tokens->ensureWhitespaceAtIndex($typeAnalysis->getStartIndex() - 1, 1, ' ');
+        }
     }
 
     /**

+ 1 - 1
src/Fixer/LanguageConstruct/SingleSpaceAroundConstructFixer.php

@@ -221,7 +221,7 @@ yield  from  baz();
     /**
      * {@inheritdoc}
      *
-     * Must run before BracesFixer, FunctionDeclarationFixer, NullableTypeDeclarationFixer.
+     * Must run before BracesFixer, FunctionDeclarationFixer.
      * Must run after ArraySyntaxFixer, ModernizeStrposFixer.
      */
     public function getPriority(): int

+ 0 - 1
tests/AutoReview/FixerFactoryTest.php

@@ -919,7 +919,6 @@ final class FixerFactoryTest extends TestCase
             'single_space_around_construct' => [
                 'braces',
                 'function_declaration',
-                'nullable_type_declaration',
             ],
             'single_trait_insert_per_statement' => [
                 'braces',

+ 23 - 0
tests/Fixer/LanguageConstruct/NullableTypeDeclarationFixerTest.php

@@ -194,6 +194,29 @@ class Foo
         yield 'skips already fixed' => [
             "<?php\n\$bar = function (null | string \$input): int {};\n",
         ];
+
+        yield 'no space before ?' => [
+            <<<'PHP'
+                <?php
+                class Foo
+                {
+                    public null|int $a;
+                    protected null|array $b;
+                    private null|string $c;
+                    private static null|bool $d;
+                }
+                PHP,
+            <<<'PHP'
+                <?php
+                class Foo
+                {
+                    public?int $a;
+                    protected?array $b;
+                    private?string $c;
+                    private static?bool $d;
+                }
+                PHP,
+        ];
     }
 
     /**

+ 0 - 25
tests/Fixtures/Integration/priority/single_space_around_construct,nullable_type_declaration.test

@@ -1,25 +0,0 @@
---TEST--
-Integration of fixers: single_space_around_construct,nullable_type_declaration.
---RULESET--
-{"single_space_around_construct": true, "nullable_type_declaration": {"syntax": "union"}}
---REQUIREMENTS--
-{"php": 80000}
---EXPECT--
-<?php
-class Foo
-{
-    public null|int $a;
-    protected null|array $b;
-    private null|string $c;
-    private static null|bool $d;
-}
-
---INPUT--
-<?php
-class Foo
-{
-    public?int $a;
-    protected?array $b;
-    private?string $c;
-    private static?bool $d;
-}

+ 0 - 1
tests/IntegrationTest.php

@@ -62,7 +62,6 @@ final class IntegrationTest extends AbstractIntegrationTestCase
                     'priority'.\DIRECTORY_SEPARATOR.'backtick_to_shell_exec,string_implicit_backslashes.test',
                     'priority'.\DIRECTORY_SEPARATOR.'no_unused_imports,blank_line_after_namespace_2.test',
                     'priority'.\DIRECTORY_SEPARATOR.'single_import_per_statement,no_unused_imports.test',
-                    'priority'.\DIRECTORY_SEPARATOR.'single_space_around_construct,nullable_type_declaration.test',
                 ], true)) {
                     self::markTestIncomplete(\sprintf(
                         'Integration test `%s` was defined as explicit priority test, but no priority conflict was detected.'