diff --git a/CHANGELOG-5.2.md b/CHANGELOG-5.2.md index 8af2ebff38ba..eaac88436e23 100644 --- a/CHANGELOG-5.2.md +++ b/CHANGELOG-5.2.md @@ -7,6 +7,17 @@ in 5.2 minor versions. To get the diff for a specific change, go to https://github.com/symfony/symfony/commit/XXX where XXX is the change hash To get the diff between two versions, go to https://github.com/symfony/symfony/compare/v5.2.0...v5.2.1 +* 5.2.10 (2021-06-01) + + * bug #41000 [Form] Use !isset for checks cause this doesn't falsely include 0 (Kai Dederichs) + * bug #41407 [DependencyInjection] keep container.service_subscriber tag on the decorated definition (xabbuh) + * bug #40866 [Filesystem] fix readlink() for Windows (a1812) + * bug #41394 [Form] fix support for years outside of the 32b range on x86 arch (nicolas-grekas) + * bug #41380 Make Mailgun Header compatible with other Bridges (jderusse) + * bug #39847 [Messenger] Fix merging PrototypedArrayNode associative values (svityashchuk) + * bug #41346 [WebProfilerBundle] Wrapping exception js in Sfjs check and also loading base_js Sfjs if needed (weaverryan) + * bug #41344 [VarDumper] Don't pass null to parse_url() (derrabus) + * 5.2.9 (2021-05-19) * security #cve-2021-21424 [Security\Core] Fix user enumeration via response body on invalid credentials (chalasr) diff --git a/CHANGELOG-5.3.md b/CHANGELOG-5.3.md index d15bc4b4b1ab..3f2c56d63ac9 100644 --- a/CHANGELOG-5.3.md +++ b/CHANGELOG-5.3.md @@ -7,6 +7,14 @@ in 5.3 minor versions. To get the diff for a specific change, go to https://github.com/symfony/symfony/commit/XXX where XXX is the change hash To get the diff between two versions, go to https://github.com/symfony/symfony/compare/v5.3.0...v5.3.1 +* 5.3.1 (2021-06-02) + + * bug #41463 [Serializer][Validator] Fix not null return from "getCollectionValueTypes" (jderusse) + * bug #41493 [Security] Readd deprecated methods to the interfaces (wouterj) + * bug #41495 [HttpFoundation] Add ReturnTypeWillChange to SessionHandlers (nikic) + * bug #41485 [HttpKernel] fix ArgumentMetadataFactory messes up controller arguments with attributes (sgehrig) + * bug #41461 Fix Symfony 5.3 end of maintenance date (jmsche) + * 5.3.0 (2021-05-31) * bug #41458 [FrameworkBundle] fix ConfigBuilderCacheWarmer (nicolas-grekas) diff --git a/CONTRIBUTORS.md b/CONTRIBUTORS.md index 082da17e5c9f..311957098418 100644 --- a/CONTRIBUTORS.md +++ b/CONTRIBUTORS.md @@ -14,8 +14,8 @@ The Symfony Connect username in parenthesis allows to get more information - Christophe Coevoet (stof) - Maxime Steinhausser (ogizanagi) - Kévin Dunglas (dunglas) - - Grégoire Pineau (lyrixx) - Jérémy DERUSSÉ (jderusse) + - Grégoire Pineau (lyrixx) - Wouter De Jong (wouterj) - Jordi Boggiano (seldaek) - Victor Berchet (victor) @@ -140,6 +140,7 @@ The Symfony Connect username in parenthesis allows to get more information - Adrien Brault (adrienbrault) - Julien Falque (julienfalque) - Jacob Dreesen (jdreesen) + - Malte Schlüter (maltemaltesich) - Joel Wurtz (brouznouf) - Florian Voutzinos (florianv) - Teoh Han Hui (teohhanhui) @@ -152,10 +153,10 @@ The Symfony Connect username in parenthesis allows to get more information - Tugdual Saunier (tucksaun) - excelwebzone - Gordon Franke (gimler) + - Saif Eddin Gmati (azjezz) - Jesse Rushlow (geeshoe) - Fabien Pennequin (fabienpennequin) - Théo FIDRY (theofidry) - - Saif Eddin Gmati (azjezz) - Eric GELOEN (gelo) - Matthieu Napoli (mnapoli) - HypeMC (hypemc) @@ -182,6 +183,7 @@ The Symfony Connect username in parenthesis allows to get more information - Albert Casademont (acasademont) - Arnaud Kleinpeter (nanocom) - Guilherme Blanco (guilhermeblanco) + - Smaine Milianni (ismail1432) - SpacePossum - Pablo Godel (pgodel) - Andreas Braun @@ -194,6 +196,7 @@ The Symfony Connect username in parenthesis allows to get more information - George Mponos (gmponos) - jwdeitch - Fabien Bourigault (fbourigault) + - Alexander Menshchikov (zmey_kk) - YaFou - Mikael Pajunen - Andreas Schempp (aschempp) @@ -207,12 +210,10 @@ The Symfony Connect username in parenthesis allows to get more information - Chi-teck - Jeroen Spee (jeroens) - Timo Bakx (timobakx) - - Smaine Milianni (ismail1432) - Marco Pivetta (ocramius) - Vincent Touzet (vincenttouzet) - Rouven Weßling (realityking) - Jérôme Parmentier (lctrs) - - Alexander Menshchikov (zmey_kk) - Ben Davies (bendavies) - Alessandro Lai (jean85) - Clemens Tolboom @@ -268,7 +269,6 @@ The Symfony Connect username in parenthesis allows to get more information - Ruben Gonzalez (rubenrua) - Benjamin Dulau (dbenjamin) - Baptiste Lafontaine (magnetik) - - Malte Schlüter (maltemaltesich) - Mathieu Lemoine (lemoinem) - Christian Schmidt - Andreas Hucks (meandmymonkey) @@ -301,6 +301,7 @@ The Symfony Connect username in parenthesis allows to get more information - Jeremy Livingston (jeremylivingston) - Michael Lee (zerustech) - Matthieu Auger (matthieuauger) + - Michael Babker (mbabker) - Leszek Prabucki (l3l0) - Nicolas Philippe (nikophil) - Colin O'Dell (colinodell) @@ -342,7 +343,6 @@ The Symfony Connect username in parenthesis allows to get more information - Sébastien Lavoie (lavoiesl) - Dariusz - Farhad Safarov (safarov) - - Michael Babker (mbabker) - Thomas Lallement (raziel057) - Francois Zaninotto - Claude Khedhiri (ck-developer) @@ -453,6 +453,7 @@ The Symfony Connect username in parenthesis allows to get more information - Bertrand Zuchuat (garfield-fr) - Gabor Toth (tgabi333) - realmfoo + - Roman Martinuk (a2a4) - Thomas Tourlourat (armetiz) - Andrey Esaulov (andremaha) - Grégoire Passault (gregwar) @@ -473,6 +474,7 @@ The Symfony Connect username in parenthesis allows to get more information - Francesc Rosàs (frosas) - Romain Pierre (romain-pierre) - Julien Galenski (ruian) + - Dieter - Bongiraud Dominique - Kyle - janschoenherr @@ -546,7 +548,6 @@ The Symfony Connect username in parenthesis allows to get more information - Philipp Cordes - Jeroen Thora (bolle) - Costin Bereveanu (schniper) - - Roman Martinuk (a2a4) - Loïc Chardonnet (gnusat) - Marek Kalnik (marekkalnik) - Vyacheslav Salakhutdinov (megazoll) @@ -596,7 +597,6 @@ The Symfony Connect username in parenthesis allows to get more information - Christophe L. (christophelau) - Sander Toonen (xatoo) - Anthon Pang (robocoder) - - Dieter - Marko Kaznovac (kaznovac) - Marc Laporte - Michał Jusięga @@ -623,6 +623,7 @@ The Symfony Connect username in parenthesis allows to get more information - Niklas Fiekas - Philippe Segatori - Markus Bachmann (baachi) + - fd6130 (fdtvui) - Kévin THERAGE (kevin_therage) - Michel Hunziker - Gunnstein Lye (glye) @@ -873,7 +874,6 @@ The Symfony Connect username in parenthesis allows to get more information - Safonov Nikita (ns3777k) - vitaliytv - Nicolas Martin (cocorambo) - - fd6130 (fdtvui) - Dalibor Karlović (dkarlovi) - Sebastian Blum - Alexis Lefebvre @@ -1179,6 +1179,7 @@ The Symfony Connect username in parenthesis allows to get more information - possum - Denis Zunke (donalberto) - Ahmadou Waly Ndiaye (waly) + - Antonin CLAUZIER (0x346e3730) - moldman - Evert Harmeling (evertharmeling) - Jonathan Johnson (jrjohnson) @@ -1234,6 +1235,7 @@ The Symfony Connect username in parenthesis allows to get more information - Eric Hertwig - Niels Robin-Aubertin - Adrien Wilmet (adrienfr) + - Aleksandar Jakovljevic (ajakov) - Laurent Bassin (lbassin) - Hamza Makraz (makraz) - andrey1s @@ -1610,6 +1612,7 @@ The Symfony Connect username in parenthesis allows to get more information - hjkl - Tony Cosentino (tony-co) - Dan Wilga + - Oleksii Svitiashchuk - Andrew Tch - Alexander Cheprasov - Tristan Bessoussa (sf_tristanb) @@ -1651,6 +1654,7 @@ The Symfony Connect username in parenthesis allows to get more information - Gustavo Adrian - Jorrit Schippers (jorrit) - Yannick + - Kai Dederichs - Vladimir Luchaninov (luchaninov) - spdionis - rchoquet @@ -2774,6 +2778,7 @@ The Symfony Connect username in parenthesis allows to get more information - Jordane VASPARD (elementaire) - Elliot Anderson (elliot) - Fabien D. (fabd) + - Faizan Akram Dar (faizanakram) - Carsten Eilers (fnc) - Sorin Gitlan (forapathy) - Yohan Giarelli (frequence-web) diff --git a/src/Symfony/Bridge/Doctrine/Security/User/UserLoaderInterface.php b/src/Symfony/Bridge/Doctrine/Security/User/UserLoaderInterface.php index b190eb249967..551017c31331 100644 --- a/src/Symfony/Bridge/Doctrine/Security/User/UserLoaderInterface.php +++ b/src/Symfony/Bridge/Doctrine/Security/User/UserLoaderInterface.php @@ -29,4 +29,10 @@ */ interface UserLoaderInterface { + /** + * @return UserInterface|null + * + * @deprecated since Symfony 5.3, use loadUserByIdentifier() instead + */ + public function loadUserByUsername(string $username); } diff --git a/src/Symfony/Component/HttpFoundation/Session/Storage/Handler/AbstractSessionHandler.php b/src/Symfony/Component/HttpFoundation/Session/Storage/Handler/AbstractSessionHandler.php index 0bb236156d6f..bc7b944fc54e 100644 --- a/src/Symfony/Component/HttpFoundation/Session/Storage/Handler/AbstractSessionHandler.php +++ b/src/Symfony/Component/HttpFoundation/Session/Storage/Handler/AbstractSessionHandler.php @@ -31,6 +31,7 @@ abstract class AbstractSessionHandler implements \SessionHandlerInterface, \Sess /** * @return bool */ + #[\ReturnTypeWillChange] public function open($savePath, $sessionName) { $this->sessionName = $sessionName; @@ -59,6 +60,7 @@ abstract protected function doDestroy(string $sessionId); /** * @return bool */ + #[\ReturnTypeWillChange] public function validateId($sessionId) { $this->prefetchData = $this->read($sessionId); @@ -79,6 +81,7 @@ public function validateId($sessionId) /** * @return string */ + #[\ReturnTypeWillChange] public function read($sessionId) { if (null !== $this->prefetchId) { @@ -102,6 +105,7 @@ public function read($sessionId) /** * @return bool */ + #[\ReturnTypeWillChange] public function write($sessionId, $data) { if (null === $this->igbinaryEmptyData) { @@ -119,6 +123,7 @@ public function write($sessionId, $data) /** * @return bool */ + #[\ReturnTypeWillChange] public function destroy($sessionId) { if (!headers_sent() && filter_var(ini_get('session.use_cookies'), \FILTER_VALIDATE_BOOLEAN)) { diff --git a/src/Symfony/Component/HttpFoundation/Session/Storage/Handler/StrictSessionHandler.php b/src/Symfony/Component/HttpFoundation/Session/Storage/Handler/StrictSessionHandler.php index 3cf4a6f479de..0461e997e21c 100644 --- a/src/Symfony/Component/HttpFoundation/Session/Storage/Handler/StrictSessionHandler.php +++ b/src/Symfony/Component/HttpFoundation/Session/Storage/Handler/StrictSessionHandler.php @@ -33,6 +33,7 @@ public function __construct(\SessionHandlerInterface $handler) /** * @return bool */ + #[\ReturnTypeWillChange] public function open($savePath, $sessionName) { parent::open($savePath, $sessionName); @@ -51,6 +52,7 @@ protected function doRead(string $sessionId) /** * @return bool */ + #[\ReturnTypeWillChange] public function updateTimestamp($sessionId, $data) { return $this->write($sessionId, $data); @@ -67,6 +69,7 @@ protected function doWrite(string $sessionId, string $data) /** * @return bool */ + #[\ReturnTypeWillChange] public function destroy($sessionId) { $this->doDestroy = true; @@ -88,14 +91,16 @@ protected function doDestroy(string $sessionId) /** * @return bool */ + #[\ReturnTypeWillChange] public function close() { return $this->handler->close(); } /** - * @return bool + * @return int|false */ + #[\ReturnTypeWillChange] public function gc($maxlifetime) { return $this->handler->gc($maxlifetime); diff --git a/src/Symfony/Component/HttpFoundation/Session/Storage/Proxy/SessionHandlerProxy.php b/src/Symfony/Component/HttpFoundation/Session/Storage/Proxy/SessionHandlerProxy.php index de4f550badbc..5535bc96441d 100644 --- a/src/Symfony/Component/HttpFoundation/Session/Storage/Proxy/SessionHandlerProxy.php +++ b/src/Symfony/Component/HttpFoundation/Session/Storage/Proxy/SessionHandlerProxy.php @@ -38,6 +38,7 @@ public function getHandler() /** * @return bool */ + #[\ReturnTypeWillChange] public function open($savePath, $sessionName) { return (bool) $this->handler->open($savePath, $sessionName); @@ -46,6 +47,7 @@ public function open($savePath, $sessionName) /** * @return bool */ + #[\ReturnTypeWillChange] public function close() { return (bool) $this->handler->close(); @@ -54,6 +56,7 @@ public function close() /** * @return string */ + #[\ReturnTypeWillChange] public function read($sessionId) { return (string) $this->handler->read($sessionId); @@ -62,6 +65,7 @@ public function read($sessionId) /** * @return bool */ + #[\ReturnTypeWillChange] public function write($sessionId, $data) { return (bool) $this->handler->write($sessionId, $data); @@ -70,22 +74,25 @@ public function write($sessionId, $data) /** * @return bool */ + #[\ReturnTypeWillChange] public function destroy($sessionId) { return (bool) $this->handler->destroy($sessionId); } /** - * @return bool + * @return int|false */ + #[\ReturnTypeWillChange] public function gc($maxlifetime) { - return (bool) $this->handler->gc($maxlifetime); + return $this->handler->gc($maxlifetime); } /** * @return bool */ + #[\ReturnTypeWillChange] public function validateId($sessionId) { return !$this->handler instanceof \SessionUpdateTimestampHandlerInterface || $this->handler->validateId($sessionId); @@ -94,6 +101,7 @@ public function validateId($sessionId) /** * @return bool */ + #[\ReturnTypeWillChange] public function updateTimestamp($sessionId, $data) { return $this->handler instanceof \SessionUpdateTimestampHandlerInterface ? $this->handler->updateTimestamp($sessionId, $data) : $this->write($sessionId, $data); diff --git a/src/Symfony/Component/HttpKernel/ControllerMetadata/ArgumentMetadataFactory.php b/src/Symfony/Component/HttpKernel/ControllerMetadata/ArgumentMetadataFactory.php index a2feb05c1034..0af1d907159a 100644 --- a/src/Symfony/Component/HttpKernel/ControllerMetadata/ArgumentMetadataFactory.php +++ b/src/Symfony/Component/HttpKernel/ControllerMetadata/ArgumentMetadataFactory.php @@ -34,6 +34,7 @@ public function createArgumentMetadata($controller): array } foreach ($reflection->getParameters() as $param) { + $attributes = []; if (\PHP_VERSION_ID >= 80000) { foreach ($param->getAttributes() as $reflectionAttribute) { if (class_exists($reflectionAttribute->getName())) { @@ -42,7 +43,7 @@ public function createArgumentMetadata($controller): array } } - $arguments[] = new ArgumentMetadata($param->getName(), $this->getType($param, $reflection), $param->isVariadic(), $param->isDefaultValueAvailable(), $param->isDefaultValueAvailable() ? $param->getDefaultValue() : null, $param->allowsNull(), $attributes ?? []); + $arguments[] = new ArgumentMetadata($param->getName(), $this->getType($param, $reflection), $param->isVariadic(), $param->isDefaultValueAvailable(), $param->isDefaultValueAvailable() ? $param->getDefaultValue() : null, $param->allowsNull(), $attributes); } return $arguments; diff --git a/src/Symfony/Component/HttpKernel/Kernel.php b/src/Symfony/Component/HttpKernel/Kernel.php index 44bdd8d3398f..a50521454f36 100644 --- a/src/Symfony/Component/HttpKernel/Kernel.php +++ b/src/Symfony/Component/HttpKernel/Kernel.php @@ -75,14 +75,14 @@ abstract class Kernel implements KernelInterface, RebootableInterface, Terminabl private static $freshCache = []; - public const VERSION = '5.3.0'; - public const VERSION_ID = 50300; + public const VERSION = '5.3.1'; + public const VERSION_ID = 50301; public const MAJOR_VERSION = 5; public const MINOR_VERSION = 3; - public const RELEASE_VERSION = 0; + public const RELEASE_VERSION = 1; public const EXTRA_VERSION = ''; - public const END_OF_MAINTENANCE = '05/2021'; + public const END_OF_MAINTENANCE = '01/2022'; public const END_OF_LIFE = '01/2022'; public function __construct(string $environment, bool $debug) diff --git a/src/Symfony/Component/HttpKernel/Tests/ControllerMetadata/ArgumentMetadataFactoryTest.php b/src/Symfony/Component/HttpKernel/Tests/ControllerMetadata/ArgumentMetadataFactoryTest.php index d952e424c557..a7e8f3575095 100644 --- a/src/Symfony/Component/HttpKernel/Tests/ControllerMetadata/ArgumentMetadataFactoryTest.php +++ b/src/Symfony/Component/HttpKernel/Tests/ControllerMetadata/ArgumentMetadataFactoryTest.php @@ -140,6 +140,18 @@ public function testMultipleAttributes() $this->assertCount(1, $this->factory->createArgumentMetadata([new AttributeController(), 'multiAttributeArg'])[0]->getAttributes()); } + /** + * @requires PHP 8 + */ + public function testIssue41478() + { + $arguments = $this->factory->createArgumentMetadata([new AttributeController(), 'issue41478']); + $this->assertEquals([ + new ArgumentMetadata('baz', 'string', false, false, null, false, [new Foo('bar')]), + new ArgumentMetadata('bat', 'string', false, false, null, false, []), + ], $arguments); + } + private function signature1(self $foo, array $bar, callable $baz) { } diff --git a/src/Symfony/Component/HttpKernel/Tests/Fixtures/Controller/AttributeController.php b/src/Symfony/Component/HttpKernel/Tests/Fixtures/Controller/AttributeController.php index d6e0cde58d88..915b5e41d4e8 100644 --- a/src/Symfony/Component/HttpKernel/Tests/Fixtures/Controller/AttributeController.php +++ b/src/Symfony/Component/HttpKernel/Tests/Fixtures/Controller/AttributeController.php @@ -20,4 +20,7 @@ public function action(#[Foo('bar')] string $baz) { public function multiAttributeArg(#[Foo('bar'), Undefined('bar')] string $baz) { } + + public function issue41478(#[Foo('bar')] string $baz, string $bat) { + } } diff --git a/src/Symfony/Component/Lock/Store/MongoDbStore.php b/src/Symfony/Component/Lock/Store/MongoDbStore.php index b228d2b7ace2..39c1a2d113e2 100644 --- a/src/Symfony/Component/Lock/Store/MongoDbStore.php +++ b/src/Symfony/Component/Lock/Store/MongoDbStore.php @@ -47,14 +47,14 @@ */ class MongoDbStore implements PersistingStoreInterface { + use ExpiringStoreTrait; + private $collection; private $client; private $uri; private $options; private $initialTtl; - use ExpiringStoreTrait; - /** * @param Collection|Client|string $mongo An instance of a Collection or Client or URI @see https://docs.mongodb.com/manual/reference/connection-string/ * @param array $options See below diff --git a/src/Symfony/Component/PropertyInfo/Type.php b/src/Symfony/Component/PropertyInfo/Type.php index 5798306735ca..31ffaf388422 100644 --- a/src/Symfony/Component/PropertyInfo/Type.php +++ b/src/Symfony/Component/PropertyInfo/Type.php @@ -179,16 +179,7 @@ public function getCollectionValueType(): ?self { trigger_deprecation('symfony/property-info', '5.3', 'The "%s()" method is deprecated, use "getCollectionValueTypes()" instead.', __METHOD__); - $type = $this->getCollectionValueTypes(); - if (0 === \count($type)) { - return null; - } - - if (\is_array($type)) { - [$type] = $type; - } - - return $type; + return $this->getCollectionValueTypes()[0] ?? null; } /** diff --git a/src/Symfony/Component/Security/Core/Authentication/RememberMe/PersistentTokenInterface.php b/src/Symfony/Component/Security/Core/Authentication/RememberMe/PersistentTokenInterface.php index 85c5bc385e58..18eea22587b9 100644 --- a/src/Symfony/Component/Security/Core/Authentication/RememberMe/PersistentTokenInterface.php +++ b/src/Symfony/Component/Security/Core/Authentication/RememberMe/PersistentTokenInterface.php @@ -48,4 +48,11 @@ public function getTokenValue(); * @return \DateTime */ public function getLastUsed(); + + /** + * @return string + * + * @deprecated since Symfony 5.3, use getUserIdentifier() instead + */ + public function getUsername(); } diff --git a/src/Symfony/Component/Security/Core/Authentication/Token/TokenInterface.php b/src/Symfony/Component/Security/Core/Authentication/Token/TokenInterface.php index 047f571ae4a2..82633f92051f 100644 --- a/src/Symfony/Component/Security/Core/Authentication/Token/TokenInterface.php +++ b/src/Symfony/Component/Security/Core/Authentication/Token/TokenInterface.php @@ -130,4 +130,11 @@ public function __serialize(): array; * Restores the object state from an array given by __serialize(). */ public function __unserialize(array $data): void; + + /** + * @return string + * + * @deprecated since Symfony 5.3, use getUserIdentifier() instead + */ + public function getUsername(); } diff --git a/src/Symfony/Component/Security/Core/Exception/UserNotFoundException.php b/src/Symfony/Component/Security/Core/Exception/UserNotFoundException.php index d730f7d7719f..f9c40c3249f8 100644 --- a/src/Symfony/Component/Security/Core/Exception/UserNotFoundException.php +++ b/src/Symfony/Component/Security/Core/Exception/UserNotFoundException.php @@ -62,7 +62,7 @@ public function setUserIdentifier(string $identifier): void */ public function setUsername(string $username) { - trigger_deprecation('symfony/security-core', '5.3', 'Method "%s()" is deprecated, use getUserIdentifier() instead.', __METHOD__); + trigger_deprecation('symfony/security-core', '5.3', 'Method "%s()" is deprecated, use setUserIdentifier() instead.', __METHOD__); $this->identifier = $username; } diff --git a/src/Symfony/Component/Security/Core/User/UserInterface.php b/src/Symfony/Component/Security/Core/User/UserInterface.php index 6448ab519248..f30d36e17d4d 100644 --- a/src/Symfony/Component/Security/Core/User/UserInterface.php +++ b/src/Symfony/Component/Security/Core/User/UserInterface.php @@ -78,4 +78,11 @@ public function getSalt(); * the plain-text password is stored on this object. */ public function eraseCredentials(); + + /** + * @return string + * + * @deprecated since Symfony 5.3, use getUserIdentifier() instead + */ + public function getUsername(); } diff --git a/src/Symfony/Component/Security/Core/User/UserProviderInterface.php b/src/Symfony/Component/Security/Core/User/UserProviderInterface.php index 5ab67836c730..2444bdfa242d 100644 --- a/src/Symfony/Component/Security/Core/User/UserProviderInterface.php +++ b/src/Symfony/Component/Security/Core/User/UserProviderInterface.php @@ -57,4 +57,13 @@ public function refreshUser(UserInterface $user); * @return bool */ public function supportsClass(string $class); + + /** + * @return UserInterface + * + * @throws UserNotFoundException + * + * @deprecated since Symfony 5.3, use loadUserByIdentifier() instead + */ + public function loadUserByUsername(string $username); } diff --git a/src/Symfony/Component/Security/Http/Tests/LoginLink/LoginLinkHandlerTest.php b/src/Symfony/Component/Security/Http/Tests/LoginLink/LoginLinkHandlerTest.php index 02f6f0182f50..877e1b62bdb5 100644 --- a/src/Symfony/Component/Security/Http/Tests/LoginLink/LoginLinkHandlerTest.php +++ b/src/Symfony/Component/Security/Http/Tests/LoginLink/LoginLinkHandlerTest.php @@ -211,6 +211,11 @@ public function createUser(TestLoginLinkHandlerUser $user): void $this->users[$user->getUserIdentifier()] = $user; } + public function loadUserByUsername($username): TestLoginLinkHandlerUser + { + return $this->loadUserByIdentifier($username); + } + public function loadUserByIdentifier(string $userIdentifier): TestLoginLinkHandlerUser { if (!isset($this->users[$userIdentifier])) { diff --git a/src/Symfony/Component/Semaphore/Store/StoreFactory.php b/src/Symfony/Component/Semaphore/Store/StoreFactory.php index d19315061e01..4c6304921ff9 100644 --- a/src/Symfony/Component/Semaphore/Store/StoreFactory.php +++ b/src/Symfony/Component/Semaphore/Store/StoreFactory.php @@ -11,7 +11,6 @@ namespace Symfony\Component\Semaphore\Store; -use Doctrine\DBAL\Connection; use Symfony\Component\Cache\Adapter\AbstractAdapter; use Symfony\Component\Cache\Traits\RedisClusterProxy; use Symfony\Component\Cache\Traits\RedisProxy; diff --git a/src/Symfony/Component/Serializer/Normalizer/AbstractObjectNormalizer.php b/src/Symfony/Component/Serializer/Normalizer/AbstractObjectNormalizer.php index 6a151c31b764..9ab8c684c9cc 100644 --- a/src/Symfony/Component/Serializer/Normalizer/AbstractObjectNormalizer.php +++ b/src/Symfony/Component/Serializer/Normalizer/AbstractObjectNormalizer.php @@ -473,13 +473,13 @@ private function validateAndDenormalize(string $currentClass, string $attribute, if (null !== $collectionKeyType = $type->getCollectionKeyTypes()) { [$context['key_type']] = $collectionKeyType; } - } elseif ($type->isCollection() && null !== ($collectionValueType = $type->getCollectionValueTypes()) && \count($collectionValueType) > 0 && Type::BUILTIN_TYPE_ARRAY === $collectionValueType[0]->getBuiltinType()) { + } elseif ($type->isCollection() && \count($collectionValueType = $type->getCollectionValueTypes()) > 0 && Type::BUILTIN_TYPE_ARRAY === $collectionValueType[0]->getBuiltinType()) { // get inner type for any nested array [$innerType] = $collectionValueType; // note that it will break for any other builtinType $dimensions = '[]'; - while (null !== $innerType->getCollectionValueTypes() && Type::BUILTIN_TYPE_ARRAY === $innerType->getBuiltinType()) { + while (\count($innerType->getCollectionValueTypes()) > 0 && Type::BUILTIN_TYPE_ARRAY === $innerType->getBuiltinType()) { $dimensions .= '[]'; [$innerType] = $innerType->getCollectionValueTypes(); } diff --git a/src/Symfony/Component/Serializer/composer.json b/src/Symfony/Component/Serializer/composer.json index 60a0567f920a..78d84fdc5028 100644 --- a/src/Symfony/Component/Serializer/composer.json +++ b/src/Symfony/Component/Serializer/composer.json @@ -47,7 +47,7 @@ "phpdocumentor/type-resolver": "<1.4.0", "symfony/dependency-injection": "<4.4", "symfony/property-access": "<4.4", - "symfony/property-info": "<4.4", + "symfony/property-info": "<5.3", "symfony/yaml": "<4.4" }, "suggest": { diff --git a/src/Symfony/Component/Validator/Mapping/Loader/PropertyInfoLoader.php b/src/Symfony/Component/Validator/Mapping/Loader/PropertyInfoLoader.php index 3f83da8d0517..118c15944528 100644 --- a/src/Symfony/Component/Validator/Mapping/Loader/PropertyInfoLoader.php +++ b/src/Symfony/Component/Validator/Mapping/Loader/PropertyInfoLoader.php @@ -119,7 +119,7 @@ public function loadClassMetadata(ClassMetadata $metadata): bool } if (!$hasTypeConstraint) { if (1 === \count($builtinTypes)) { - if ($types[0]->isCollection() && (null !== $collectionValueType = $types[0]->getCollectionValueTypes())) { + if ($types[0]->isCollection() && \count($collectionValueType = $types[0]->getCollectionValueTypes()) > 0) { [$collectionValueType] = $collectionValueType; $this->handleAllConstraint($property, $allConstraint, $collectionValueType, $metadata); } diff --git a/src/Symfony/Component/Validator/Tests/Fixtures/PropertyInfoLoaderEntity.php b/src/Symfony/Component/Validator/Tests/Fixtures/PropertyInfoLoaderEntity.php index 144a0016e84c..2cc46e77de29 100644 --- a/src/Symfony/Component/Validator/Tests/Fixtures/PropertyInfoLoaderEntity.php +++ b/src/Symfony/Component/Validator/Tests/Fixtures/PropertyInfoLoaderEntity.php @@ -23,6 +23,7 @@ class PropertyInfoLoaderEntity public $scalar; public $object; public $collection; + public $collectionOfUnknown; /** * @Assert\Type(type="int") diff --git a/src/Symfony/Component/Validator/Tests/Mapping/Loader/PropertyInfoLoaderTest.php b/src/Symfony/Component/Validator/Tests/Mapping/Loader/PropertyInfoLoaderTest.php index 767a5ab5c697..0965d8e135fa 100644 --- a/src/Symfony/Component/Validator/Tests/Mapping/Loader/PropertyInfoLoaderTest.php +++ b/src/Symfony/Component/Validator/Tests/Mapping/Loader/PropertyInfoLoaderTest.php @@ -44,6 +44,7 @@ public function testLoadClassMetadata() 'scalar', 'object', 'collection', + 'collectionOfUnknown', 'alreadyMappedType', 'alreadyMappedNotNull', 'alreadyMappedNotBlank', @@ -61,6 +62,7 @@ public function testLoadClassMetadata() [new Type(Type::BUILTIN_TYPE_STRING, true), new Type(Type::BUILTIN_TYPE_INT), new Type(Type::BUILTIN_TYPE_BOOL)], [new Type(Type::BUILTIN_TYPE_OBJECT, true, Entity::class)], [new Type(Type::BUILTIN_TYPE_ARRAY, true, null, true, null, new Type(Type::BUILTIN_TYPE_OBJECT, false, Entity::class))], + [new Type(Type::BUILTIN_TYPE_ARRAY, true, null, true)], [new Type(Type::BUILTIN_TYPE_FLOAT, true)], // The existing constraint is float [new Type(Type::BUILTIN_TYPE_STRING, true)], [new Type(Type::BUILTIN_TYPE_STRING, true)], @@ -81,6 +83,7 @@ public function testLoadClassMetadata() true, true, true, + true, false, true )) @@ -135,6 +138,13 @@ public function testLoadClassMetadata() $this->assertInstanceOf(TypeConstraint::class, $collectionConstraints[0]->constraints[1]); $this->assertSame(Entity::class, $collectionConstraints[0]->constraints[1]->type); + $collectionOfUnknownMetadata = $classMetadata->getPropertyMetadata('collectionOfUnknown'); + $this->assertCount(1, $collectionOfUnknownMetadata); + $collectionOfUnknownConstraints = $collectionOfUnknownMetadata[0]->getConstraints(); + $this->assertCount(1, $collectionOfUnknownConstraints); + $this->assertInstanceOf(TypeConstraint::class, $collectionOfUnknownConstraints[0]); + $this->assertSame('array', $collectionOfUnknownConstraints[0]->type); + $alreadyMappedTypeMetadata = $classMetadata->getPropertyMetadata('alreadyMappedType'); $this->assertCount(1, $alreadyMappedTypeMetadata); $alreadyMappedTypeConstraints = $alreadyMappedTypeMetadata[0]->getConstraints(); diff --git a/src/Symfony/Component/Validator/composer.json b/src/Symfony/Component/Validator/composer.json index 119e90b03f6a..f46be9bb3cea 100644 --- a/src/Symfony/Component/Validator/composer.json +++ b/src/Symfony/Component/Validator/composer.json @@ -51,6 +51,7 @@ "symfony/expression-language": "<5.1", "symfony/http-kernel": "<4.4", "symfony/intl": "<4.4", + "symfony/property-info": "<5.3", "symfony/translation": "<4.4", "symfony/yaml": "<4.4" },