Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
14 changes: 14 additions & 0 deletions extension.neon
Original file line number Diff line number Diff line change
Expand Up @@ -156,6 +156,20 @@ services:
descriptorRegistry: @doctrineTypeDescriptorRegistry
tags:
- phpstan.broker.dynamicMethodReturnTypeExtension
-
class: PHPStan\Type\Doctrine\UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension
arguments:
metadataResolver: @PHPStan\Type\Doctrine\ObjectMetadataResolver
descriptorRegistry: @doctrineTypeDescriptorRegistry
tags:
- phpstan.broker.dynamicMethodReturnTypeExtension
-
class: PHPStan\Type\Doctrine\UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension
arguments:
metadataResolver: @PHPStan\Type\Doctrine\ObjectMetadataResolver
descriptorRegistry: @doctrineTypeDescriptorRegistry
tags:
- phpstan.broker.dynamicMethodReturnTypeExtension
-
class: PHPStan\Type\Doctrine\Query\QueryResultDynamicReturnTypeExtension
tags:
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,186 @@
<?php declare(strict_types = 1);

namespace PHPStan\Type\Doctrine;

use Doctrine\ORM\Mapping\ClassMetadata;
use Doctrine\ORM\PersistentCollection;
use Doctrine\ORM\UnitOfWork;
use PhpParser\Node\Expr\MethodCall;
use PHPStan\Analyser\Scope;
use PHPStan\Reflection\MethodReflection;
use PHPStan\Reflection\ParametersAcceptorSelector;
use PHPStan\Type\Constant\ConstantArrayTypeBuilder;
use PHPStan\Type\Constant\ConstantIntegerType;
use PHPStan\Type\Constant\ConstantStringType;
use PHPStan\Type\DynamicMethodReturnTypeExtension;
use PHPStan\Type\MixedType;
use PHPStan\Type\ObjectType;
use PHPStan\Type\Type;
use PHPStan\Type\TypeCombinator;
use function count;
use function is_array;
use function is_string;

final class UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension implements DynamicMethodReturnTypeExtension
{

private ObjectMetadataResolver $metadataResolver;

private DescriptorRegistry $descriptorRegistry;

public function __construct(
ObjectMetadataResolver $metadataResolver,
DescriptorRegistry $descriptorRegistry
)
{
$this->metadataResolver = $metadataResolver;
$this->descriptorRegistry = $descriptorRegistry;
}

public function getClass(): string
{
return UnitOfWork::class;
}

public function isMethodSupported(MethodReflection $methodReflection): bool
{
return $methodReflection->getName() === 'getEntityChangeSet';
}

public function getTypeFromMethodCall(
MethodReflection $methodReflection,
MethodCall $methodCall,
Scope $scope
): Type
{
if (count($methodCall->getArgs()) === 0) {
return $this->getDefaultReturnType($methodReflection, $scope, $methodCall);
}

$entityType = $scope->getType($methodCall->getArgs()[0]->value);
$objectClassNames = $entityType->getObjectClassNames();

if (count($objectClassNames) === 0) {
return $this->getDefaultReturnType($methodReflection, $scope, $methodCall);
}

$changeSetTypes = [];

foreach ($objectClassNames as $className) {
$metadata = $this->metadataResolver->getClassMetadata($className);

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3, composer require --dev doctrine/orm:^3.0 doctrine/dbal:^4.0 carbonphp/carbon-doctri...

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3, composer require --dev doctrine/orm:^3.0 doctrine/dbal:^4.0 carbonphp/carbon-doctri...

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 70 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.
if ($metadata === null) {
return $this->getDefaultReturnType($methodReflection, $scope, $methodCall);
}

$changeSetTypes[] = $this->createChangeSetType($metadata);
}

return TypeCombinator::union(...$changeSetTypes);
}

private function createChangeSetType(ClassMetadata $metadata): Type

Check failure on line 81 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Method PHPStan\Type\Doctrine\UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension::createChangeSetType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 81 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Method PHPStan\Type\Doctrine\UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension::createChangeSetType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 81 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Method PHPStan\Type\Doctrine\UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension::createChangeSetType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 81 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Method PHPStan\Type\Doctrine\UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension::createChangeSetType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 81 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Method PHPStan\Type\Doctrine\UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension::createChangeSetType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 81 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3, composer require --dev doctrine/orm:^3.0 doctrine/dbal:^4.0 carbonphp/carbon-doctri...

Method PHPStan\Type\Doctrine\UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension::createChangeSetType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 81 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Method PHPStan\Type\Doctrine\UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension::createChangeSetType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T
{
$builder = ConstantArrayTypeBuilder::createEmpty();
$collectionType = new ObjectType(PersistentCollection::class);

foreach ($metadata->fieldMappings as $fieldName => $mapping) {
if ($metadata->isIdentifier($fieldName)) {
continue;
}

if (!isset($mapping['type'])) {

Check failure on line 91 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 91 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 91 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 91 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 91 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 91 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.
continue;
}

try {
$type = $this->descriptorRegistry->get($mapping['type'])->getWritableToPropertyType();
} catch (DescriptorNotRegisteredException $exception) {
$type = new MixedType();
}

if (($mapping['nullable'] ?? false) === true) {
$type = TypeCombinator::addNull($type);
}

$fieldBuilder = ConstantArrayTypeBuilder::createEmpty();
$fieldBuilder->setOffsetValueType(new ConstantIntegerType(0), $type);
$fieldBuilder->setOffsetValueType(new ConstantIntegerType(1), $type);

$builder->setOffsetValueType(
new ConstantStringType($fieldName),
$fieldBuilder->getArray(),
);
}

foreach ($metadata->associationMappings as $fieldName => $mapping) {
if (($mapping['type'] & ClassMetadata::TO_ONE) !== 0) {
$targetEntity = $mapping['targetEntity'] ?? null;

Check failure on line 117 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Offset 'targetEntity' on array{cache?: array<mixed>, cascade: array<string>, declared?: class-string, fetch: mixed, fieldName: string, id?: bool, inherited?: class-string, indexBy?: string, ...} on left side of ?? always exists and is not nullable.

Check failure on line 117 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Offset 'targetEntity' on array{cache?: array<mixed>, cascade: array<string>, declared?: class-string, fetch: mixed, fieldName: string, id?: bool, inherited?: class-string, indexBy?: string, ...} on left side of ?? always exists and is not nullable.

Check failure on line 117 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Offset 'targetEntity' on array{cache?: array<mixed>, cascade: array<string>, declared?: class-string, fetch: mixed, fieldName: string, id?: bool, inherited?: class-string, indexBy?: string, ...} on left side of ?? always exists and is not nullable.

Check failure on line 117 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Offset 'targetEntity' on array{cache?: array<mixed>, cascade: array<string>, declared?: class-string, fetch: mixed, fieldName: string, id?: bool, inherited?: class-string, indexBy?: string, ...} on left side of ?? always exists and is not nullable.

Check failure on line 117 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Offset 'targetEntity' on array{cache?: array<mixed>, cascade: array<string>, declared?: class-string, fetch: mixed, fieldName: string, id?: bool, inherited?: class-string, indexBy?: string, ...} on left side of ?? always exists and is not nullable.

Check failure on line 117 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Offset 'targetEntity' on array{cache?: array<mixed>, cascade: array<string>, declared?: class-string, fetch: mixed, fieldName: string, id?: bool, inherited?: class-string, indexBy?: string, ...} on left side of ?? always exists and is not nullable.
if (!is_string($targetEntity)) {

Check failure on line 118 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Call to function is_string() with class-string will always evaluate to true.

Check failure on line 118 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Call to function is_string() with class-string will always evaluate to true.

Check failure on line 118 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Call to function is_string() with class-string will always evaluate to true.

Check failure on line 118 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Call to function is_string() with class-string will always evaluate to true.

Check failure on line 118 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Call to function is_string() with class-string will always evaluate to true.

Check failure on line 118 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Call to function is_string() with class-string will always evaluate to true.
continue;
}

$type = new ObjectType($targetEntity);
if ($this->isAssociationNullable($mapping)) {

Check failure on line 123 in src/Type/Doctrine/UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3, composer require --dev doctrine/orm:^3.0 doctrine/dbal:^4.0 carbonphp/carbon-doctri...

Parameter #1 $association of method PHPStan\Type\Doctrine\UnitOfWorkGetEntityChangeSetDynamicReturnTypeExtension::isAssociationNullable() expects array<string, mixed>, Doctrine\ORM\Mapping\ManyToManyInverseSideMapping|Doctrine\ORM\Mapping\ManyToManyOwningSideMapping|Doctrine\ORM\Mapping\ManyToOneAssociationMapping|Doctrine\ORM\Mapping\OneToManyAssociationMapping|Doctrine\ORM\Mapping\OneToOneInverseSideMapping|Doctrine\ORM\Mapping\OneToOneOwningSideMapping given.
$type = TypeCombinator::addNull($type);
}

$fieldBuilder = ConstantArrayTypeBuilder::createEmpty();
$fieldBuilder->setOffsetValueType(new ConstantIntegerType(0), $type);
$fieldBuilder->setOffsetValueType(new ConstantIntegerType(1), $type);

$builder->setOffsetValueType(
new ConstantStringType($fieldName),
$fieldBuilder->getArray(),
);
continue;
}

if (($mapping['type'] & ClassMetadata::TO_MANY) === 0) {
continue;
}

$fieldBuilder = ConstantArrayTypeBuilder::createEmpty();
$fieldBuilder->setOffsetValueType(new ConstantIntegerType(0), $collectionType);
$fieldBuilder->setOffsetValueType(new ConstantIntegerType(1), $collectionType);

$builder->setOffsetValueType(
new ConstantStringType($fieldName),
$fieldBuilder->getArray(),
);
}

return $builder->getArray();
}

/**
* @param array<string, mixed> $association
*/
private function isAssociationNullable(array $association): bool
{
$joinColumns = $association['joinColumns'] ?? null;
if (!is_array($joinColumns)) {
return true;
}

foreach ($joinColumns as $joinColumn) {
if (!is_array($joinColumn)) {
continue;
}
if (($joinColumn['nullable'] ?? true) === false) {
return false;
}
}

return true;
}

private function getDefaultReturnType(MethodReflection $methodReflection, Scope $scope, MethodCall $methodCall): Type
{
return ParametersAcceptorSelector::selectFromArgs(
$scope,
$methodCall->getArgs(),
$methodReflection->getVariants(),
)->getReturnType();
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,177 @@
<?php declare(strict_types = 1);

namespace PHPStan\Type\Doctrine;

use Doctrine\ORM\Mapping\ClassMetadata;
use Doctrine\ORM\PersistentCollection;
use Doctrine\ORM\UnitOfWork;
use PhpParser\Node\Expr\MethodCall;
use PHPStan\Analyser\Scope;
use PHPStan\Reflection\MethodReflection;
use PHPStan\Reflection\ParametersAcceptorSelector;
use PHPStan\Type\Constant\ConstantArrayTypeBuilder;
use PHPStan\Type\Constant\ConstantStringType;
use PHPStan\Type\DynamicMethodReturnTypeExtension;
use PHPStan\Type\MixedType;
use PHPStan\Type\ObjectType;
use PHPStan\Type\Type;
use PHPStan\Type\TypeCombinator;
use function count;
use function is_array;
use function is_string;

final class UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension implements DynamicMethodReturnTypeExtension
{

private ObjectMetadataResolver $metadataResolver;

private DescriptorRegistry $descriptorRegistry;

public function __construct(
ObjectMetadataResolver $metadataResolver,
DescriptorRegistry $descriptorRegistry
)
{
$this->metadataResolver = $metadataResolver;
$this->descriptorRegistry = $descriptorRegistry;
}

public function getClass(): string
{
return UnitOfWork::class;
}

public function isMethodSupported(MethodReflection $methodReflection): bool
{
return $methodReflection->getName() === 'getOriginalEntityData';
}

public function getTypeFromMethodCall(
MethodReflection $methodReflection,
MethodCall $methodCall,
Scope $scope
): Type
{
if (count($methodCall->getArgs()) === 0) {
return $this->getDefaultReturnType($methodReflection, $scope, $methodCall);
}

$entityType = $scope->getType($methodCall->getArgs()[0]->value);
$objectClassNames = $entityType->getObjectClassNames();

if (count($objectClassNames) === 0) {
return $this->getDefaultReturnType($methodReflection, $scope, $methodCall);
}

$dataTypes = [];

foreach ($objectClassNames as $className) {
$metadata = $this->metadataResolver->getClassMetadata($className);

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3, composer require --dev doctrine/orm:^3.0 doctrine/dbal:^4.0 carbonphp/carbon-doctri...

Unable to resolve the template type T in call to method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata()

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3, composer require --dev doctrine/orm:^3.0 doctrine/dbal:^4.0 carbonphp/carbon-doctri...

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.

Check failure on line 69 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Parameter #1 $className of method PHPStan\Type\Doctrine\ObjectMetadataResolver::getClassMetadata() expects class-string<object>, string given.
if ($metadata === null) {
return $this->getDefaultReturnType($methodReflection, $scope, $methodCall);
}

$dataTypes[] = $this->createOriginalEntityDataType($metadata);
}

return TypeCombinator::union(...$dataTypes);
}

private function createOriginalEntityDataType(ClassMetadata $metadata): Type

Check failure on line 80 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Method PHPStan\Type\Doctrine\UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension::createOriginalEntityDataType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 80 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Method PHPStan\Type\Doctrine\UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension::createOriginalEntityDataType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 80 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Method PHPStan\Type\Doctrine\UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension::createOriginalEntityDataType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 80 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Method PHPStan\Type\Doctrine\UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension::createOriginalEntityDataType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 80 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Method PHPStan\Type\Doctrine\UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension::createOriginalEntityDataType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 80 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Method PHPStan\Type\Doctrine\UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension::createOriginalEntityDataType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T

Check failure on line 80 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3, composer require --dev doctrine/orm:^3.0 doctrine/dbal:^4.0 carbonphp/carbon-doctri...

Method PHPStan\Type\Doctrine\UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension::createOriginalEntityDataType() has parameter $metadata with generic class Doctrine\ORM\Mapping\ClassMetadata but does not specify its types: T
{
$builder = ConstantArrayTypeBuilder::createEmpty();
$collectionType = new ObjectType(PersistentCollection::class);

foreach ($metadata->fieldMappings as $fieldName => $mapping) {
if ($metadata->isIdentifier($fieldName) && $metadata->isIdGeneratorIdentity()) {
continue;
}

if ($metadata->versionField === $fieldName) {
continue;
}

if (!isset($mapping['type'])) {

Check failure on line 94 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.2)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 94 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.0)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 94 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 94 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (7.4)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 94 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.4)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.

Check failure on line 94 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.1)

Offset 'type' on array{type: string, fieldName: string, columnName: string, length?: int, id?: bool, nullable?: bool, notInsertable?: bool, notUpdatable?: bool, ...} in isset() always exists and is not nullable.
continue;
}

try {
$type = $this->descriptorRegistry->get($mapping['type'])->getWritableToPropertyType();
} catch (DescriptorNotRegisteredException $exception) {
$type = new MixedType();
}

if (($mapping['nullable'] ?? false) === true) {
$type = TypeCombinator::addNull($type);
}

$builder->setOffsetValueType(
new ConstantStringType($fieldName),
$type,
);
}

foreach ($metadata->associationMappings as $fieldName => $mapping) {
if (($mapping['type'] & ClassMetadata::TO_ONE) !== 0) {
$targetEntity = $mapping['targetEntity'] ?? null;
if (!is_string($targetEntity)) {
continue;
}

$type = new ObjectType($targetEntity);
if ($this->isAssociationNullable($mapping)) {

Check failure on line 122 in src/Type/Doctrine/UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension.php

View workflow job for this annotation

GitHub Actions / PHPStan (8.3, composer require --dev doctrine/orm:^3.0 doctrine/dbal:^4.0 carbonphp/carbon-doctri...

Parameter #1 $association of method PHPStan\Type\Doctrine\UnitOfWorkGetOriginalEntityDataDynamicReturnTypeExtension::isAssociationNullable() expects array<string, mixed>, Doctrine\ORM\Mapping\ManyToManyInverseSideMapping|Doctrine\ORM\Mapping\ManyToManyOwningSideMapping|Doctrine\ORM\Mapping\ManyToOneAssociationMapping|Doctrine\ORM\Mapping\OneToManyAssociationMapping|Doctrine\ORM\Mapping\OneToOneInverseSideMapping|Doctrine\ORM\Mapping\OneToOneOwningSideMapping given.
$type = TypeCombinator::addNull($type);
}

$builder->setOffsetValueType(
new ConstantStringType($fieldName),
$type,
);
continue;
}

if (($mapping['type'] & ClassMetadata::TO_MANY) === 0) {
continue;
}

$builder->setOffsetValueType(
new ConstantStringType($fieldName),
$collectionType,
);
}

return $builder->getArray();
}

/**
* @param array<string, mixed> $association
*/
private function isAssociationNullable(array $association): bool
{
$joinColumns = $association['joinColumns'] ?? null;
if (!is_array($joinColumns)) {
return true;
}

foreach ($joinColumns as $joinColumn) {
if (!is_array($joinColumn)) {
continue;
}
if (($joinColumn['nullable'] ?? true) === false) {
return false;
}
}

return true;
}

private function getDefaultReturnType(MethodReflection $methodReflection, Scope $scope, MethodCall $methodCall): Type
{
return ParametersAcceptorSelector::selectFromArgs(
$scope,
$methodCall->getArgs(),
$methodReflection->getVariants(),
)->getReturnType();
}

}
Loading
Loading