Merge pull request #9519 from Seldaek/lock-update-with-new-req
Fix mirror updates when adding new reqs and dev-reqs are presentpull/9532/head
commit
01887a2488
|
@ -24,6 +24,7 @@ use Composer\DependencyResolver\Pool;
|
|||
use Composer\DependencyResolver\Request;
|
||||
use Composer\DependencyResolver\Solver;
|
||||
use Composer\DependencyResolver\SolverProblemsException;
|
||||
use Composer\DependencyResolver\PolicyInterface;
|
||||
use Composer\Downloader\DownloadManager;
|
||||
use Composer\EventDispatcher\EventDispatcher;
|
||||
use Composer\Installer\InstallationManager;
|
||||
|
@ -52,6 +53,7 @@ use Composer\Repository\RootPackageRepository;
|
|||
use Composer\Repository\PlatformRepository;
|
||||
use Composer\Repository\RepositoryInterface;
|
||||
use Composer\Repository\RepositoryManager;
|
||||
use Composer\Repository\LockArrayRepository;
|
||||
use Composer\Script\ScriptEvents;
|
||||
|
||||
/**
|
||||
|
@ -365,12 +367,10 @@ class Installer
|
|||
// doing a full update
|
||||
}
|
||||
|
||||
if ($this->updateAllowList) {
|
||||
if (!$lockedRepository) {
|
||||
$this->io->writeError('<error>Cannot update only a partial set of packages without a lock file present.</error>', true, IOInterface::QUIET);
|
||||
if (($this->updateAllowList || $this->updateMirrors) && !$lockedRepository) {
|
||||
$this->io->writeError('<error>Cannot update ' . ($this->updateMirrors ? 'lock file information' : 'only a partial set of packages') . ' without a lock file present. Run `composer update` to generate a lock file.</error>', true, IOInterface::QUIET);
|
||||
|
||||
return 1;
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
|
||||
$this->io->writeError('<info>Loading composer repositories with package information</info>');
|
||||
|
@ -387,22 +387,7 @@ class Installer
|
|||
}
|
||||
|
||||
$request = $this->createRequest($this->fixedRootPackage, $platformRepo, $lockedRepository);
|
||||
|
||||
// if we're updating mirrors we want to keep exactly the same versions installed which are in the lock file, but we want current remote metadata
|
||||
if ($this->updateMirrors && $lockedRepository) {
|
||||
foreach ($lockedRepository->getPackages() as $lockedPackage) {
|
||||
// exclude alias packages here as for root aliases, both alias and aliased are
|
||||
// present in the lock repo and we only want to require the aliased version
|
||||
if (!$lockedPackage instanceof AliasPackage) {
|
||||
$request->requireName($lockedPackage->getName(), new Constraint('==', $lockedPackage->getVersion()));
|
||||
}
|
||||
}
|
||||
} else {
|
||||
$links = array_merge($this->package->getRequires(), $this->package->getDevRequires());
|
||||
foreach ($links as $link) {
|
||||
$request->requireName($link->getTarget(), $link->getConstraint());
|
||||
}
|
||||
}
|
||||
$this->requirePackagesForUpdate($request, $lockedRepository, true);
|
||||
|
||||
// pass the allow list into the request, so the pool builder can apply it
|
||||
if ($this->updateAllowList) {
|
||||
|
@ -442,7 +427,7 @@ class Installer
|
|||
$this->io->writeError('Nothing to modify in lock file');
|
||||
}
|
||||
|
||||
$exitCode = $this->extractDevPackages($lockTransaction, $platformRepo, $aliases, $policy);
|
||||
$exitCode = $this->extractDevPackages($lockTransaction, $platformRepo, $aliases, $policy, $lockedRepository);
|
||||
if ($exitCode !== 0) {
|
||||
return $exitCode;
|
||||
}
|
||||
|
@ -555,7 +540,7 @@ class Installer
|
|||
* Run the solver a second time on top of the existing update result with only the current result set in the pool
|
||||
* and see what packages would get removed if we only had the non-dev packages in the solver request
|
||||
*/
|
||||
protected function extractDevPackages(LockTransaction $lockTransaction, $platformRepo, $aliases, $policy)
|
||||
protected function extractDevPackages(LockTransaction $lockTransaction, PlatformRepository $platformRepo, array $aliases, PolicyInterface $policy, LockArrayRepository $lockedRepository = null)
|
||||
{
|
||||
if (!$this->package->getDevRequires()) {
|
||||
return 0;
|
||||
|
@ -572,11 +557,7 @@ class Installer
|
|||
$repositorySet->addRepository($resultRepo);
|
||||
|
||||
$request = $this->createRequest($this->fixedRootPackage, $platformRepo);
|
||||
|
||||
$links = $this->package->getRequires();
|
||||
foreach ($links as $link) {
|
||||
$request->requireName($link->getTarget(), $link->getConstraint());
|
||||
}
|
||||
$this->requirePackagesForUpdate($request, $lockedRepository, false);
|
||||
|
||||
$pool = $repositorySet->createPoolWithAllPackages();
|
||||
|
||||
|
@ -815,12 +796,9 @@ class Installer
|
|||
}
|
||||
|
||||
/**
|
||||
* @param RootPackageInterface $rootPackage
|
||||
* @param PlatformRepository $platformRepo
|
||||
* @param RepositoryInterface|null $lockedRepository
|
||||
* @return Request
|
||||
*/
|
||||
private function createRequest(RootPackageInterface $rootPackage, PlatformRepository $platformRepo, $lockedRepository = null)
|
||||
private function createRequest(RootPackageInterface $rootPackage, PlatformRepository $platformRepo, LockArrayRepository $lockedRepository = null)
|
||||
{
|
||||
$request = new Request($lockedRepository);
|
||||
|
||||
|
@ -851,6 +829,33 @@ class Installer
|
|||
return $request;
|
||||
}
|
||||
|
||||
private function requirePackagesForUpdate(Request $request, LockArrayRepository $lockedRepository = null, $includeDevRequires = true)
|
||||
{
|
||||
// if we're updating mirrors we want to keep exactly the same versions installed which are in the lock file, but we want current remote metadata
|
||||
if ($this->updateMirrors) {
|
||||
$excludedPackages = array();
|
||||
if (!$includeDevRequires) {
|
||||
$excludedPackages = array_flip($this->locker->getDevPackageNames());
|
||||
}
|
||||
|
||||
foreach ($lockedRepository->getPackages() as $lockedPackage) {
|
||||
// exclude alias packages here as for root aliases, both alias and aliased are
|
||||
// present in the lock repo and we only want to require the aliased version
|
||||
if (!$lockedPackage instanceof AliasPackage && !isset($excludedPackages[$lockedPackage->getName()])) {
|
||||
$request->requireName($lockedPackage->getName(), new Constraint('==', $lockedPackage->getVersion()));
|
||||
}
|
||||
}
|
||||
} else {
|
||||
$links = $this->package->getRequires();
|
||||
if ($includeDevRequires) {
|
||||
$links = array_merge($links, $this->package->getDevRequires());
|
||||
}
|
||||
foreach ($links as $link) {
|
||||
$request->requireName($link->getTarget(), $link->getConstraint());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param bool $forUpdate
|
||||
* @return array
|
||||
|
@ -870,7 +875,7 @@ class Installer
|
|||
* @param array $links
|
||||
* @return array
|
||||
*/
|
||||
private function extractPlatformRequirements($links)
|
||||
private function extractPlatformRequirements(array $links)
|
||||
{
|
||||
$platformReqs = array();
|
||||
foreach ($links as $link) {
|
||||
|
|
|
@ -31,7 +31,7 @@ Partial update without lock file should error
|
|||
--RUN--
|
||||
update b/unstable
|
||||
--EXPECT-OUTPUT--
|
||||
Cannot update only a partial set of packages without a lock file present.
|
||||
Cannot update only a partial set of packages without a lock file present. Run `composer update` to generate a lock file.
|
||||
--EXPECT-EXIT-CODE--
|
||||
1
|
||||
--EXPECT--
|
||||
|
|
|
@ -0,0 +1,65 @@
|
|||
--TEST--
|
||||
Update mirrors with a new root require which is not yet in lock should simply ignore it
|
||||
--COMPOSER--
|
||||
{
|
||||
"repositories": [
|
||||
{
|
||||
"type": "package",
|
||||
"package": [
|
||||
{"name": "a/a", "version": "1.0.0"},
|
||||
{"name": "a/a", "version": "1.1.0"},
|
||||
{"name": "b/b", "version": "1.0.0"},
|
||||
{"name": "b/b", "version": "1.1.0"},
|
||||
{"name": "new/req", "version": "1.0.0"},
|
||||
{"name": "new/req", "version": "1.1.0"}
|
||||
]
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"a/a": "1.*",
|
||||
"new/req": "1.*"
|
||||
},
|
||||
"require-dev": {
|
||||
"b/b": "1.*"
|
||||
}
|
||||
}
|
||||
--INSTALLED--
|
||||
[
|
||||
{"name": "a/a", "version": "1.0.0"},
|
||||
{"name": "b/b", "version": "1.0.0"}
|
||||
]
|
||||
--LOCK--
|
||||
{
|
||||
"packages": [
|
||||
{"name": "a/a", "version": "1.0.0", "type": "library"}
|
||||
],
|
||||
"packages-dev": [
|
||||
{"name": "b/b", "version": "1.0.0", "type": "library"}
|
||||
],
|
||||
"aliases": [],
|
||||
"minimum-stability": "dev",
|
||||
"stability-flags": [],
|
||||
"prefer-stable": false,
|
||||
"prefer-lowest": false,
|
||||
"platform": [],
|
||||
"platform-dev": []
|
||||
}
|
||||
--RUN--
|
||||
update mirrors
|
||||
--EXPECT-LOCK--
|
||||
{
|
||||
"packages": [
|
||||
{"name": "a/a", "version": "1.0.0", "type": "library"}
|
||||
],
|
||||
"packages-dev": [
|
||||
{"name": "b/b", "version": "1.0.0", "type": "library"}
|
||||
],
|
||||
"aliases": [],
|
||||
"minimum-stability": "stable",
|
||||
"stability-flags": [],
|
||||
"prefer-stable": false,
|
||||
"prefer-lowest": false,
|
||||
"platform": [],
|
||||
"platform-dev": []
|
||||
}
|
||||
--EXPECT--
|
Loading…
Reference in New Issue