Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(doctrine 3): fix phpstan issues with doctrine 3.x #1556

Merged
merged 1 commit into from
Aug 20, 2024
Merged
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
1 change: 0 additions & 1 deletion src/Metadata/Driver/AbstractDoctrineTypeDriver.php
Original file line number Diff line number Diff line change
Expand Up @@ -89,7 +89,6 @@ public function loadMetadataForClass(\ReflectionClass $class): ?BaseClassMetadat
}

\assert($classMetadata instanceof ClassMetadata);

// Abort if the given class is not a mapped entity
if (!$doctrineMetadata = $this->tryLoadingDoctrineMetadata($class->name)) {
return $classMetadata;
Expand Down
10 changes: 4 additions & 6 deletions src/Metadata/Driver/DoctrineTypeDriver.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@

namespace JMS\Serializer\Metadata\Driver;

use Doctrine\ORM\Mapping\ClassMetadataInfo;
use Doctrine\ODM\PHPCR\Mapping\ClassMetadata as ORMClassMetadata;
use Doctrine\ORM\Mapping\ClassMetadata as ODMClassMetadata;
use Doctrine\Persistence\Mapping\ClassMetadata as DoctrineClassMetadata;
use JMS\Serializer\Metadata\ClassMetadata;
use JMS\Serializer\Metadata\PropertyMetadata;
Expand All @@ -15,12 +16,9 @@
*/
class DoctrineTypeDriver extends AbstractDoctrineTypeDriver
{
/**
* @param ClassMetadataInfo $doctrineMetadata
* @param ClassMetadata $classMetadata
*/
protected function setDiscriminator(DoctrineClassMetadata $doctrineMetadata, ClassMetadata $classMetadata): void
{
assert($doctrineMetadata instanceof ORMClassMetadata || $doctrineMetadata instanceof ODMClassMetadata);
if (
empty($classMetadata->discriminatorMap) && !$classMetadata->discriminatorDisabled
&& !empty($doctrineMetadata->discriminatorMap) && $doctrineMetadata->isRootEntity()
Expand Down Expand Up @@ -51,7 +49,7 @@ protected function setPropertyType(DoctrineClassMetadata $doctrineMetadata, Prop
// For inheritance schemes, we cannot add any type as we would only add the super-type of the hierarchy.
// On serialization, this would lead to only the supertype being serialized, and properties of subtypes
// being ignored.
if ($targetMetadata instanceof ClassMetadataInfo && !$targetMetadata->isInheritanceTypeNone()) {
if ($targetMetadata instanceof ODMClassMetadata && !$targetMetadata->isInheritanceTypeNone()) {
return;
}

Expand Down
9 changes: 9 additions & 0 deletions tests/Fixtures/Doctrine/Entity/BlogPost.php
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,9 @@
use Doctrine\Common\Collections\ArrayCollection;
use Doctrine\DBAL\Types\Types;
use Doctrine\ORM\Mapping as ORM;
use Doctrine\ORM\Mapping\DiscriminatorColumn;
use Doctrine\ORM\Mapping\DiscriminatorMap;
use Doctrine\ORM\Mapping\InheritanceType;
use JMS\Serializer\Annotation as Serializer;
use JMS\Serializer\Annotation\Groups;
use JMS\Serializer\Annotation\SerializedName;
Expand All @@ -18,10 +21,16 @@
/**
* @ORM\Entity
*
* @InheritanceType("SINGLE_TABLE")
* @DiscriminatorColumn(name="discr", type="string")
* @DiscriminatorMap({"simple" = "BlogPost", "extended" = "ExtendedPost"})
* @XmlRoot("blog-post")
*/
#[ORM\Entity]
#[InheritanceType('SINGLE_TABLE')]
#[XmlRoot(name: 'blog-post')]
#[DiscriminatorColumn(name: 'discr', type: 'string')]
#[DiscriminatorMap(['simple' => BlogPost::class, 'extended' => ExtendedPost::class])]
class BlogPost
{
/**
Expand Down
15 changes: 15 additions & 0 deletions tests/Fixtures/Doctrine/Entity/ExtendedPost.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
<?php

declare(strict_types=1);

namespace JMS\Serializer\Tests\Fixtures\Doctrine\Entity;

use Doctrine\ORM\Mapping\Entity;

/**
* @Entity
*/
#[Entity]
class ExtendedPost extends BlogPost
{
}
18 changes: 12 additions & 6 deletions tests/Metadata/Driver/DoctrineDriverTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -16,15 +16,20 @@
use JMS\Serializer\Metadata\Driver\DoctrineTypeDriver;
use JMS\Serializer\Metadata\Driver\NullDriver;
use JMS\Serializer\Naming\IdenticalPropertyNamingStrategy;
use JMS\Serializer\Tests\Fixtures\BlogPost;
use JMS\Serializer\Tests\Fixtures\Doctrine\Embeddable\BlogPostWithEmbedded;
use JMS\Serializer\Tests\Fixtures\Doctrine\Entity\Author;
use JMS\Serializer\Tests\Fixtures\Doctrine\Entity\BlogPost as DoctrineBlogPost;
use JMS\Serializer\Tests\Fixtures\Doctrine\Entity\Comment;
use JMS\Serializer\Tests\Fixtures\ExcludePublicAccessor;
use Metadata\Driver\DriverChain;
use PHPUnit\Framework\TestCase;

class DoctrineDriverTest extends TestCase
{
public function getMetadata()
{
$refClass = new \ReflectionClass('JMS\Serializer\Tests\Fixtures\Doctrine\Entity\BlogPost');
$refClass = new \ReflectionClass(DoctrineBlogPost::class);

return $this->getDoctrineDriver()->loadMetadataForClass($refClass);
}
Expand All @@ -50,7 +55,7 @@ public function testSingleValuedAssociationIsProperlyHinted()
{
$metadata = $this->getMetadata();
self::assertEquals(
['name' => 'JMS\Serializer\Tests\Fixtures\Doctrine\Entity\Author', 'params' => []],
['name' => Author::class, 'params' => []],
$metadata->propertyMetadata['author']->type,
);
}
Expand All @@ -63,7 +68,7 @@ public function testMultiValuedAssociationIsProperlyHinted()
[
'name' => 'ArrayCollection',
'params' => [
['name' => 'JMS\Serializer\Tests\Fixtures\Doctrine\Entity\Comment', 'params' => []],
['name' => Comment::class, 'params' => []],
],
],
$metadata->propertyMetadata['comments']->type,
Expand Down Expand Up @@ -91,7 +96,7 @@ public function testNonDoctrineEntityClassIsNotModified()
{
// Note: Using regular BlogPost fixture here instead of Doctrine fixture
// because it has no Doctrine metadata.
$refClass = new \ReflectionClass('JMS\Serializer\Tests\Fixtures\BlogPost');
$refClass = new \ReflectionClass(BlogPost::class);

$plainMetadata = $this->getMetadataDriver()->loadMetadataForClass($refClass);
$doctrineMetadata = $this->getDoctrineDriver()->loadMetadataForClass($refClass);
Expand All @@ -107,7 +112,7 @@ public function testNonDoctrineEntityClassIsNotModified()
public function testExcludePropertyNoPublicAccessorException()
{
$first = $this->getMetadataDriver()
->loadMetadataForClass(new \ReflectionClass('JMS\Serializer\Tests\Fixtures\ExcludePublicAccessor'));
->loadMetadataForClass(new \ReflectionClass(ExcludePublicAccessor::class));

self::assertArrayHasKey('id', $first->propertyMetadata);
self::assertArrayNotHasKey('iShallNotBeAccessed', $first->propertyMetadata);
Expand All @@ -129,7 +134,7 @@ public function testGuidPropertyIsGivenStringType()
);
}

protected function getEntityManager()
protected function getEntityManager(): EntityManager
{
$config = new Configuration();
$config->setProxyDir(sys_get_temp_dir() . '/JMSDoctrineTestProxies');
Expand All @@ -140,6 +145,7 @@ protected function getEntityManager()
new DoctrineAttributeDriver([__DIR__ . '/../../Fixtures/Doctrine'], true),
);
} else {
assert(class_exists(DoctrineAnnotationDriver::class));
$config->setMetadataDriverImpl(
new DoctrineAnnotationDriver(new AnnotationReader(), __DIR__ . '/../../Fixtures/Doctrine'),
);
Expand Down
1 change: 1 addition & 0 deletions tests/Metadata/Driver/DoctrinePHPCRDriverTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,7 @@ protected function getDocumentManager()
$config = new Configuration();
$config->setProxyDir(sys_get_temp_dir() . '/JMSDoctrineTestProxies');
$config->setProxyNamespace('JMS\Tests\Proxies');
assert(class_exists(DoctrinePHPCRDriver::class));
$config->setMetadataDriverImpl(
new DoctrinePHPCRDriver(new AnnotationReader(), __DIR__ . '/../../Fixtures/DoctrinePHPCR'),
);
Expand Down
34 changes: 6 additions & 28 deletions tests/Serializer/Doctrine/IntegrationTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@
use Doctrine\ORM\EntityManager;
use Doctrine\ORM\Mapping\Driver\AnnotationDriver;
use Doctrine\ORM\Mapping\Driver\AttributeDriver;
use Doctrine\ORM\ORMException;
use Doctrine\ORM\Tools\SchemaTool;
use Doctrine\Persistence\AbstractManagerRegistry;
use Doctrine\Persistence\Proxy;
Expand Down Expand Up @@ -143,6 +142,7 @@ private function createEntityManager(Connection $con)
]));
AnnotationReader::addGlobalIgnoredNamespace('Doctrine\ORM\Mapping');
} else {
assert(class_exists(AnnotationDriver::class));
$cfg->setMetadataDriverImpl(new AnnotationDriver(new AnnotationReader(), [
__DIR__ . '/../../Fixtures/Doctrine/SingleTableInheritance',
]));
Expand All @@ -158,10 +158,10 @@ private function createEntityManager(Connection $con)

class SimpleManagerRegistry extends AbstractManagerRegistry
{
private $services = [];
private $serviceCreator;
private array $services = [];
private \Closure $serviceCreator;

public function __construct($serviceCreator, $name = 'anonymous', array $connections = ['default' => 'default_connection'], array $managers = ['default' => 'default_manager'], $defaultConnection = null, $defaultManager = null, $proxyInterface = Proxy::class)
public function __construct(\Closure $serviceCreator, $name = 'anonymous', array $connections = ['default' => 'default_connection'], array $managers = ['default' => 'default_manager'], $defaultConnection = null, $defaultManager = null, $proxyInterface = Proxy::class)
{
if (null === $defaultConnection) {
$defaultConnection = key($connections);
Expand All @@ -173,20 +173,12 @@ public function __construct($serviceCreator, $name = 'anonymous', array $connect

parent::__construct($name, $connections, $managers, $defaultConnection, $defaultManager, $proxyInterface);

if (!is_callable($serviceCreator)) {
throw new \InvalidArgumentException('$serviceCreator must be a valid callable.');
}

$this->serviceCreator = $serviceCreator;
}

public function getService($name)
{
if (isset($this->services[$name])) {
return $this->services[$name];
}

return $this->services[$name] = call_user_func($this->serviceCreator, $name);
return $this->services[$name] ??= call_user_func($this->serviceCreator, $name);
}

public function resetService($name)
Expand All @@ -196,20 +188,6 @@ public function resetService($name)

public function getAliasNamespace($alias)
{
foreach (array_keys($this->getManagers()) as $name) {
$manager = $this->getManager($name);

if ($manager instanceof EntityManager) {
try {
return $manager->getConfiguration()->getEntityNamespace($alias);
} catch (ORMException $ex) {
// Probably mapped by another entity manager, or invalid, just ignore this here.
}
} else {
throw new \LogicException(sprintf('Unsupported manager type "%s".', get_class($manager)));
}
}

throw new \RuntimeException(sprintf('The namespace alias "%s" is not known to any manager.', $alias));
return $alias;
}
}
35 changes: 6 additions & 29 deletions tests/Serializer/Doctrine/ObjectConstructorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@
use Doctrine\ORM\Mapping\Driver\AnnotationDriver;
use Doctrine\ORM\Mapping\Driver\AttributeDriver;
use Doctrine\ORM\Mapping\Driver\XmlDriver;
use Doctrine\ORM\ORMException;
use Doctrine\ORM\PersistentCollection;
use Doctrine\ORM\Tools\SchemaTool;
use Doctrine\ORM\UnitOfWork;
Expand Down Expand Up @@ -51,7 +50,6 @@
use JMS\Serializer\Tests\Fixtures\Doctrine\PersistendCollection\SmartPhone;
use JMS\Serializer\Tests\Fixtures\DoctrinePHPCR\Author as DoctrinePHPCRAuthor;
use JMS\Serializer\Visitor\DeserializationVisitorInterface;
use LogicException;
use Metadata\Driver\AdvancedDriverInterface;
use Metadata\MetadataFactoryInterface;
use PHPUnit\Framework\Attributes\DataProvider;
Expand Down Expand Up @@ -536,6 +534,7 @@ private function createEntityManager(Connection $con, ?Configuration $cfg = null
__DIR__ . '/../../Fixtures/Doctrine/PersistendCollection',
]));
} else {
assert(class_exists(AnnotationDriver::class));
$cfg->setMetadataDriverImpl(new AnnotationDriver(new AnnotationReader(), [
__DIR__ . '/../../Fixtures/Doctrine/Entity',
__DIR__ . '/../../Fixtures/Doctrine/IdentityFields',
Expand Down Expand Up @@ -597,10 +596,10 @@ private function createSerializerWithDoctrineObjectConstructor()

class SimpleBaseManagerRegistry extends AbstractManagerRegistry
{
private $services = [];
private $serviceCreator;
private array $services = [];
private \Closure $serviceCreator;

public function __construct($serviceCreator, $name = 'anonymous', array $connections = ['default' => 'default_connection'], array $managers = ['default' => 'default_manager'], $defaultConnection = null, $defaultManager = null, $proxyInterface = Proxy::class)
public function __construct(\Closure $serviceCreator, $name = 'anonymous', array $connections = ['default' => 'default_connection'], array $managers = ['default' => 'default_manager'], $defaultConnection = null, $defaultManager = null, $proxyInterface = Proxy::class)
{
if (null === $defaultConnection) {
$defaultConnection = key($connections);
Expand All @@ -612,20 +611,12 @@ public function __construct($serviceCreator, $name = 'anonymous', array $connect

parent::__construct($name, $connections, $managers, $defaultConnection, $defaultManager, $proxyInterface);

if (!is_callable($serviceCreator)) {
throw new \InvalidArgumentException('$serviceCreator must be a valid callable.');
}

$this->serviceCreator = $serviceCreator;
}

public function getService($name)
{
if (isset($this->services[$name])) {
return $this->services[$name];
}

return $this->services[$name] = call_user_func($this->serviceCreator, $name);
return $this->services[$name] ??= call_user_func($this->serviceCreator, $name);
}

public function resetService($name)
Expand All @@ -635,20 +626,6 @@ public function resetService($name)

public function getAliasNamespace($alias)
{
foreach (array_keys($this->getManagers()) as $name) {
$manager = $this->getManager($name);

if ($manager instanceof EntityManager) {
try {
return $manager->getConfiguration()->getEntityNamespace($alias);
} catch (ORMException $ex) {
// Probably mapped by another entity manager, or invalid, just ignore this here.
}
} else {
throw new LogicException(sprintf('Unsupported manager type "%s".', get_class($manager)));
}
}

throw new RuntimeException(sprintf('The namespace alias "%s" is not known to any manager.', $alias));
return $alias;
}
}
Loading