diff --git a/.github/workflows/continuous-integration.yml b/.github/workflows/continuous-integration.yml index 2ad7f282..0c4ea23b 100644 --- a/.github/workflows/continuous-integration.yml +++ b/.github/workflows/continuous-integration.yml @@ -22,7 +22,7 @@ jobs: deps: - "highest" include: - - deps: "low" + - deps: "lowest" php-version: "7.2" steps: diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md new file mode 100644 index 00000000..268200ad --- /dev/null +++ b/CONTRIBUTING.md @@ -0,0 +1,11 @@ +# Circular dependency + +This package has a development dependency on `doctrine/common`, which has a +regular dependency on this package (`^2.0` at the time of writing). + +To be able to use Composer, one has to let it understand that this is version 2 +(even when developing on 3.0.x), as follows: + +```shell +COMPOSER_ROOT_VERSION=2.0 composer update -v +``` diff --git a/lib/Doctrine/Persistence/Event/LoadClassMetadataEventArgs.php b/lib/Doctrine/Persistence/Event/LoadClassMetadataEventArgs.php index b313f541..6a71fd11 100644 --- a/lib/Doctrine/Persistence/Event/LoadClassMetadataEventArgs.php +++ b/lib/Doctrine/Persistence/Event/LoadClassMetadataEventArgs.php @@ -13,7 +13,10 @@ */ class LoadClassMetadataEventArgs extends EventArgs { - /** @psalm-var ClassMetadata */ + /** + * @var ClassMetadata + * @psalm-var ClassMetadata + */ private $classMetadata; /** @var ObjectManager */ @@ -31,6 +34,7 @@ public function __construct(ClassMetadata $classMetadata, ObjectManager $objectM /** * Retrieves the associated ClassMetadata. * + * @return ClassMetadata * @psalm-return ClassMetadata */ public function getClassMetadata() diff --git a/lib/Doctrine/Persistence/Mapping/Driver/AnnotationDriver.php b/lib/Doctrine/Persistence/Mapping/Driver/AnnotationDriver.php index b607e379..a067606f 100644 --- a/lib/Doctrine/Persistence/Mapping/Driver/AnnotationDriver.php +++ b/lib/Doctrine/Persistence/Mapping/Driver/AnnotationDriver.php @@ -21,7 +21,6 @@ use function in_array; use function is_array; use function is_dir; -use function is_string; use function preg_match; use function preg_quote; use function realpath; @@ -235,10 +234,9 @@ public function getAllClassNames() } foreach ($this->excludePaths as $excludePath) { - $realpath = realpath($excludePath); - assert(is_string($realpath)); - - $exclude = str_replace('\\', '/', $realpath); + $realExcludePath = realpath($excludePath); + assert($realExcludePath !== false); + $exclude = str_replace('\\', '/', $realExcludePath); $current = str_replace('\\', '/', $sourceFile); if (strpos($current, $exclude) !== false) { diff --git a/lib/Doctrine/Persistence/Mapping/Driver/FileDriver.php b/lib/Doctrine/Persistence/Mapping/Driver/FileDriver.php index 5fd4e709..0b9ae8a6 100644 --- a/lib/Doctrine/Persistence/Mapping/Driver/FileDriver.php +++ b/lib/Doctrine/Persistence/Mapping/Driver/FileDriver.php @@ -26,7 +26,10 @@ abstract class FileDriver implements MappingDriver /** @var FileLocator */ protected $locator; - /** @psalm-var ClassMetadata[]|null */ + /** + * @var ClassMetadata[]|null + * @psalm-var ClassMetadata[]|null + */ protected $classCache; /** @var string */ @@ -72,7 +75,8 @@ public function getGlobalBasename() * Gets the element of schema meta data for the class from the mapping file. * This will lazily load the mapping file if it is not loaded yet. * - * @psalm-return ClassMetadata The element of schema meta data. + * @return ClassMetadata The element of schema meta data. + * @psalm-return ClassMetadata * * @throws MappingException */ diff --git a/lib/Doctrine/Persistence/Mapping/Driver/MappingDriver.php b/lib/Doctrine/Persistence/Mapping/Driver/MappingDriver.php index 423824e4..0a635d6b 100644 --- a/lib/Doctrine/Persistence/Mapping/Driver/MappingDriver.php +++ b/lib/Doctrine/Persistence/Mapping/Driver/MappingDriver.php @@ -14,7 +14,7 @@ interface MappingDriver /** * Loads the metadata for the specified class into the provided container. * - * @param ClassMetadata $metadata + * @psalm-param ClassMetadata $metadata * * @return void */ diff --git a/lib/Doctrine/Persistence/Mapping/Driver/PHPDriver.php b/lib/Doctrine/Persistence/Mapping/Driver/PHPDriver.php index dbbbfc27..cd74e9ff 100644 --- a/lib/Doctrine/Persistence/Mapping/Driver/PHPDriver.php +++ b/lib/Doctrine/Persistence/Mapping/Driver/PHPDriver.php @@ -12,7 +12,10 @@ */ class PHPDriver extends FileDriver { - /** @var ClassMetadata */ + /** + * @var ClassMetadata + * @psalm-var ClassMetadata + */ protected $metadata; /** diff --git a/lib/Doctrine/Persistence/Mapping/ReflectionService.php b/lib/Doctrine/Persistence/Mapping/ReflectionService.php index d955a0e7..9484e1f3 100644 --- a/lib/Doctrine/Persistence/Mapping/ReflectionService.php +++ b/lib/Doctrine/Persistence/Mapping/ReflectionService.php @@ -48,7 +48,8 @@ public function getClassNamespace(string $class); * * @psalm-param class-string $class * - * @return ReflectionClass|null + * @return ReflectionClass|null + * @psalm-return ReflectionClass|null * * @template T of object */ diff --git a/lib/Doctrine/Persistence/Mapping/RuntimeReflectionService.php b/lib/Doctrine/Persistence/Mapping/RuntimeReflectionService.php index 17bc743a..4ad42e17 100644 --- a/lib/Doctrine/Persistence/Mapping/RuntimeReflectionService.php +++ b/lib/Doctrine/Persistence/Mapping/RuntimeReflectionService.php @@ -70,7 +70,8 @@ public function getClassNamespace(string $class) /** * @psalm-param class-string $class * - * @return ReflectionClass + * @return ReflectionClass + * @psalm-return ReflectionClass * * @template T of object */ diff --git a/lib/Doctrine/Persistence/Reflection/RuntimePublicReflectionProperty.php b/lib/Doctrine/Persistence/Reflection/RuntimePublicReflectionProperty.php index 6939d0d0..049abcd4 100644 --- a/lib/Doctrine/Persistence/Reflection/RuntimePublicReflectionProperty.php +++ b/lib/Doctrine/Persistence/Reflection/RuntimePublicReflectionProperty.php @@ -44,6 +44,7 @@ public function getValue($object = null) * @link https://bugs.php.net/bug.php?id=63463 * * @param object|null $object + * @param mixed $value */ public function setValue($object, $value = null) { diff --git a/lib/Doctrine/Persistence/Reflection/TypedNoDefaultReflectionProperty.php b/lib/Doctrine/Persistence/Reflection/TypedNoDefaultReflectionProperty.php index bf7d1029..5efb6085 100644 --- a/lib/Doctrine/Persistence/Reflection/TypedNoDefaultReflectionProperty.php +++ b/lib/Doctrine/Persistence/Reflection/TypedNoDefaultReflectionProperty.php @@ -20,6 +20,8 @@ class TypedNoDefaultReflectionProperty extends ReflectionProperty * Checks that a typed property is initialized before accessing its value. * This is necessary to avoid PHP error "Error: Typed property must not be accessed before initialization". * Should be used only for reflecting typed properties without a default value. + * + * @param object|null $object */ public function getValue($object = null) { @@ -45,6 +47,7 @@ public function setValue($object, $value = null) unset($this->$propertyName); }; $unsetter = $unsetter->bindTo($object, $this->getDeclaringClass()->getName()); + assert($unsetter instanceof Closure); $unsetter(); diff --git a/phpstan.neon b/phpstan.neon index 9109baea..0647fd61 100644 --- a/phpstan.neon +++ b/phpstan.neon @@ -11,7 +11,7 @@ parameters: - tests excludes_analyse: - - %currentWorkingDirectory%/tests/Doctrine/Tests/Persistence/Mapping/_files/TestEntity.php + - tests/Doctrine/Tests/Persistence/Mapping/_files/TestEntity.php ignoreErrors: - '#Variable property access on \$this\(Doctrine\\Persistence\\Reflection\\TypedNoDefaultReflectionProperty\)\.#' @@ -33,3 +33,12 @@ parameters: - message: '#Call to static method PHPUnit\\Framework\\Assert\:\:assertSame\(\) with Symfony\\Component\\Cache\\Adapter\\ArrayAdapter and null will always evaluate to false\.#' path: 'tests/Doctrine/Tests/Persistence/Mapping/ClassMetadataFactoryTest.php' + + # https://github.com/phpstan/phpstan/issues/5009 + - + message: '#Call to function assert\(\) with true will always evaluate to true\.#' + path: 'lib/Doctrine/Persistence/Reflection/TypedNoDefaultReflectionProperty.php' + + - + message: '#Instanceof between Closure\(\)\: void and Closure will always evaluate to true\.#' + path: 'lib/Doctrine/Persistence/Reflection/TypedNoDefaultReflectionProperty.php' diff --git a/tests/Doctrine/Tests/Persistence/Mapping/ClassMetadataFactoryTest.php b/tests/Doctrine/Tests/Persistence/Mapping/ClassMetadataFactoryTest.php index 473768bf..0ab8b268 100644 --- a/tests/Doctrine/Tests/Persistence/Mapping/ClassMetadataFactoryTest.php +++ b/tests/Doctrine/Tests/Persistence/Mapping/ClassMetadataFactoryTest.php @@ -26,12 +26,15 @@ */ class ClassMetadataFactoryTest extends DoctrineTestCase { - /** @var TestClassMetadataFactory> */ + /** + * @var TestClassMetadataFactory + * @psalm-var TestClassMetadataFactory> + */ private $cmf; protected function setUp(): void { - $driver = $this->createMock(MappingDriver::class); + $driver = $this->createMock(MappingDriver::class); /** @psalm-var ClassMetadata */ $metadata = $this->createMock(ClassMetadata::class); diff --git a/tests/Doctrine/Tests/Persistence/Mapping/Fixtures/TestClassMetadata.php b/tests/Doctrine/Tests/Persistence/Mapping/Fixtures/TestClassMetadata.php index e3ddd2d5..355511b7 100644 --- a/tests/Doctrine/Tests/Persistence/Mapping/Fixtures/TestClassMetadata.php +++ b/tests/Doctrine/Tests/Persistence/Mapping/Fixtures/TestClassMetadata.php @@ -46,17 +46,11 @@ public function getReflectionClass(): ReflectionClass return new ReflectionClass($this->getName()); } - /** - * {@inheritDoc} - */ public function isIdentifier(string $fieldName): bool { return false; } - /** - * {@inheritDoc} - */ public function hasField(string $fieldName): bool { return false;