diff --git a/typo3/sysext/extensionmanager/Classes/Utility/DependencyUtility.php b/typo3/sysext/extensionmanager/Classes/Utility/DependencyUtility.php index a805c950a1630f8a9bab31b8d9e8b40065625181..b85386a0001e3f014c6df614d504591cf9b44fc0 100644 --- a/typo3/sysext/extensionmanager/Classes/Utility/DependencyUtility.php +++ b/typo3/sysext/extensionmanager/Classes/Utility/DependencyUtility.php @@ -524,6 +524,32 @@ class DependencyUtility implements SingletonInterface return !empty($count); } + /** + * Get the latest compatible version of an extension that's + * compatible with the current core and PHP version. + * + * @param iterable $extensions + * @return Extension|null + */ + protected function getCompatibleExtension(iterable $extensions): ?Extension + { + foreach ($extensions as $extension) { + /** @var Extension $extension */ + $this->checkDependencies($extension); + $extensionKey = $extension->getExtensionKey(); + + if (isset($this->dependencyErrors[$extensionKey])) { + // reset dependencyErrors and continue with next version + unset($this->dependencyErrors[$extensionKey]); + continue; + } + + return $extension; + } + + return null; + } + /** * Get the latest compatible version of an extension that * fulfills the given dependency from TER @@ -539,7 +565,7 @@ class DependencyUtility implements SingletonInterface $versions['lowestIntegerVersion'], $versions['highestIntegerVersion'] ); - return $compatibleDataSets->getFirst(); + return $this->getCompatibleExtension($compatibleDataSets); } /** diff --git a/typo3/sysext/extensionmanager/Tests/Unit/Fixtures/LatestCompatibleExtensionObjectStorageFixture.php b/typo3/sysext/extensionmanager/Tests/Unit/Fixtures/LatestCompatibleExtensionObjectStorageFixture.php index a861396576b657837e61d00de8b754eb7dd7164b..b6967ac1774bbf6015bd8adf822704dd4e3b5492 100644 --- a/typo3/sysext/extensionmanager/Tests/Unit/Fixtures/LatestCompatibleExtensionObjectStorageFixture.php +++ b/typo3/sysext/extensionmanager/Tests/Unit/Fixtures/LatestCompatibleExtensionObjectStorageFixture.php @@ -18,18 +18,22 @@ namespace TYPO3\CMS\Extensionmanager\Tests\Unit\Fixtures; /** * Latest compatible extension object storage fixture */ -class LatestCompatibleExtensionObjectStorageFixture +class LatestCompatibleExtensionObjectStorageFixture implements \IteratorAggregate { /** - * @var array + * @var int */ - public $extensions = []; + private $position = 0; /** - * @return \TYPO3\CMS\Extensionmanager\Domain\Model\Extension + * @var array<int, \TYPO3\CMS\Extensionmanager\Domain\Model\Extension> */ - public function getFirst() + public $extensions = []; + + public function getIterator(): \Generator { - return $this->extensions[0]; + foreach ($this->extensions as $extension) { + yield $extension; + } } } diff --git a/typo3/sysext/extensionmanager/Tests/Unit/Utility/DependencyUtilityTest.php b/typo3/sysext/extensionmanager/Tests/Unit/Utility/DependencyUtilityTest.php index 7000af2e2f30a68f76e60bb911a7e7c951fd7430..1de583dedcbd994851f8523ced1ea19bacb6c324 100644 --- a/typo3/sysext/extensionmanager/Tests/Unit/Utility/DependencyUtilityTest.php +++ b/typo3/sysext/extensionmanager/Tests/Unit/Utility/DependencyUtilityTest.php @@ -479,12 +479,29 @@ class DependencyUtilityTest extends UnitTestCase */ public function getLatestCompatibleExtensionByIntegerVersionDependencyWillReturnExtensionModelOfLatestExtension(): void { + $suitableDependency = new Dependency(); + $suitableDependency->setIdentifier('typo3'); + $suitableDependency->setLowestVersion('3.6.1'); + + $suitableDependencies = new \SplObjectStorage(); + $suitableDependencies->attach($suitableDependency); + + $unsuitableDependency = new Dependency(); + $unsuitableDependency->setIdentifier('typo3'); + $unsuitableDependency->setHighestVersion('4.3.0'); + + $unsuitableDependencies = new \SplObjectStorage(); + $unsuitableDependencies->attach($unsuitableDependency); + $extension1 = new Extension(); $extension1->setExtensionKey('foo'); $extension1->setVersion('1.0.0'); + $extension1->setDependencies($unsuitableDependencies); + $extension2 = new Extension(); $extension2->setExtensionKey('bar'); $extension2->setVersion('1.0.42'); + $extension2->setDependencies($suitableDependencies); $myStorage = new LatestCompatibleExtensionObjectStorageFixture(); $myStorage->extensions[] = $extension1; @@ -505,7 +522,7 @@ class DependencyUtilityTest extends UnitTestCase $extension = $dependencyUtility->_call('getLatestCompatibleExtensionByIntegerVersionDependency', $dependency); self::assertInstanceOf(Extension::class, $extension); - self::assertSame('foo', $extension->getExtensionKey()); + self::assertSame('bar', $extension->getExtensionKey()); } /**