1
0
Fork 0

Reaching phpstan level 6 in Composer/DependencyResolver (refs #10159) (#10178)

pull/10185/head
immeëmosol 2021-10-18 22:33:37 +02:00 committed by GitHub
parent 04ab74bbef
commit 50d738eeee
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
26 changed files with 292 additions and 113 deletions

View File

@ -16,7 +16,7 @@ namespace Composer\DependencyResolver;
* Stores decisions on installing, removing or keeping packages * Stores decisions on installing, removing or keeping packages
* *
* @author Nils Adermann <naderman@naderman.de> * @author Nils Adermann <naderman@naderman.de>
* @implements \Iterator<array{0: int, 1: mixed}> * @implements \Iterator<array{0: int, 1: Rule}>
*/ */
class Decisions implements \Iterator, \Countable class Decisions implements \Iterator, \Countable
{ {
@ -27,7 +27,9 @@ class Decisions implements \Iterator, \Countable
protected $pool; protected $pool;
/** @var array<int, int> */ /** @var array<int, int> */
protected $decisionMap; protected $decisionMap;
/** @var array<array{0: int, 1: mixed}> */ /**
* @var array<array{0: int, 1: Rule}>
*/
protected $decisionQueue = array(); protected $decisionQueue = array();
public function __construct(Pool $pool) public function __construct(Pool $pool)
@ -36,7 +38,12 @@ class Decisions implements \Iterator, \Countable
$this->decisionMap = array(); $this->decisionMap = array();
} }
public function decide($literal, $level, $why) /**
* @param int $literal
* @param int $level
* @return void
*/
public function decide($literal, $level, Rule $why)
{ {
$this->addDecision($literal, $level); $this->addDecision($literal, $level);
$this->decisionQueue[] = array( $this->decisionQueue[] = array(
@ -46,6 +53,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @param int $literal
* @return bool * @return bool
*/ */
public function satisfy($literal) public function satisfy($literal)
@ -59,6 +67,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @param int $literal
* @return bool * @return bool
*/ */
public function conflict($literal) public function conflict($literal)
@ -72,6 +81,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @param int $literalOrPackageId
* @return bool * @return bool
*/ */
public function decided($literalOrPackageId) public function decided($literalOrPackageId)
@ -80,6 +90,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @param int $literalOrPackageId
* @return bool * @return bool
*/ */
public function undecided($literalOrPackageId) public function undecided($literalOrPackageId)
@ -88,6 +99,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @param int $literalOrPackageId
* @return bool * @return bool
*/ */
public function decidedInstall($literalOrPackageId) public function decidedInstall($literalOrPackageId)
@ -98,6 +110,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @param int $literalOrPackageId
* @return int * @return int
*/ */
public function decisionLevel($literalOrPackageId) public function decisionLevel($literalOrPackageId)
@ -111,13 +124,14 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @return mixed|null * @param int $literalOrPackageId
* @return Rule|null
*/ */
public function decisionRule($literalOrPackageId) public function decisionRule($literalOrPackageId)
{ {
$packageId = abs($literalOrPackageId); $packageId = abs($literalOrPackageId);
foreach ($this->decisionQueue as $i => $decision) { foreach ($this->decisionQueue as $decision) {
if ($packageId === abs($decision[self::DECISION_LITERAL])) { if ($packageId === abs($decision[self::DECISION_LITERAL])) {
return $decision[self::DECISION_REASON]; return $decision[self::DECISION_REASON];
} }
@ -127,7 +141,8 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @return array{0: int, 1: mixed} a literal and decision reason * @param int $queueOffset
* @return array{0: int, 1: Rule} a literal and decision reason
*/ */
public function atOffset($queueOffset) public function atOffset($queueOffset)
{ {
@ -135,6 +150,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @param int $queueOffset
* @return bool * @return bool
*/ */
public function validOffset($queueOffset) public function validOffset($queueOffset)
@ -143,7 +159,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @return mixed * @return Rule
*/ */
public function lastReason() public function lastReason()
{ {
@ -169,6 +185,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @param int $offset
* @return void * @return void
*/ */
public function resetToOffset($offset) public function resetToOffset($offset)
@ -207,7 +224,7 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @return array{0: int, 1: mixed}|false * @return array{0: int, 1: Rule}|false
*/ */
#[\ReturnTypeWillChange] #[\ReturnTypeWillChange]
public function current() public function current()
@ -251,6 +268,8 @@ class Decisions implements \Iterator, \Countable
} }
/** /**
* @param int $literal
* @param int $level
* @return void * @return void
*/ */
protected function addDecision($literal, $level) protected function addDecision($literal, $level)
@ -289,9 +308,6 @@ class Decisions implements \Iterator, \Countable
return $str; return $str;
} }
/**
* @return string
*/
public function __toString() public function __toString()
{ {
return $this->toString(); return $this->toString();

View File

@ -28,6 +28,10 @@ class DefaultPolicy implements PolicyInterface
/** @var bool */ /** @var bool */
private $preferLowest; private $preferLowest;
/**
* @param bool $preferStable
* @param bool $preferLowest
*/
public function __construct($preferStable = false, $preferLowest = false) public function __construct($preferStable = false, $preferLowest = false)
{ {
$this->preferStable = $preferStable; $this->preferStable = $preferStable;
@ -35,7 +39,10 @@ class DefaultPolicy implements PolicyInterface
} }
/** /**
* @param string $operator One of Constraint::STR_OP_*
* @return bool * @return bool
*
* @phpstan-param Constraint::STR_OP_* $operator
*/ */
public function versionCompare(PackageInterface $a, PackageInterface $b, $operator) public function versionCompare(PackageInterface $a, PackageInterface $b, $operator)
{ {
@ -101,6 +108,8 @@ class DefaultPolicy implements PolicyInterface
/** /**
* @protected * @protected
* @param ?string $requiredPackage
* @param bool $ignoreReplace
* @return int * @return int
*/ */
public function compareByPriority(Pool $pool, BasePackage $a, BasePackage $b, $requiredPackage = null, $ignoreReplace = false) public function compareByPriority(Pool $pool, BasePackage $a, BasePackage $b, $requiredPackage = null, $ignoreReplace = false)
@ -154,8 +163,6 @@ class DefaultPolicy implements PolicyInterface
* Replace constraints are ignored. This method should only be used for * Replace constraints are ignored. This method should only be used for
* prioritisation, not for actual constraint verification. * prioritisation, not for actual constraint verification.
* *
* @param BasePackage $source
* @param BasePackage $target
* @return bool * @return bool
*/ */
protected function replaces(BasePackage $source, BasePackage $target) protected function replaces(BasePackage $source, BasePackage $target)

View File

@ -12,10 +12,6 @@
namespace Composer\DependencyResolver; namespace Composer\DependencyResolver;
use Composer\Package\BasePackage;
use Composer\Package\Link;
use Composer\Semver\Constraint\ConstraintInterface;
/** /**
* @author Nils Adermann <naderman@naderman.de> * @author Nils Adermann <naderman@naderman.de>
*/ */
@ -25,7 +21,7 @@ class GenericRule extends Rule
protected $literals; protected $literals;
/** /**
* @param int[] $literals * @param int[] $literals
*/ */
public function __construct(array $literals, $reason, $reasonData) public function __construct(array $literals, $reason, $reasonData)
{ {
@ -45,6 +41,9 @@ class GenericRule extends Rule
return $this->literals; return $this->literals;
} }
/**
* @inheritDoc
*/
public function getHash() public function getHash()
{ {
$data = unpack('ihash', md5(implode(',', $this->literals), true)); $data = unpack('ihash', md5(implode(',', $this->literals), true));

View File

@ -12,6 +12,7 @@
namespace Composer\DependencyResolver; namespace Composer\DependencyResolver;
use Composer\Repository\InstalledRepositoryInterface;
use Composer\Repository\RepositoryInterface; use Composer\Repository\RepositoryInterface;
/** /**
@ -20,7 +21,7 @@ use Composer\Repository\RepositoryInterface;
*/ */
class LocalRepoTransaction extends Transaction class LocalRepoTransaction extends Transaction
{ {
public function __construct(RepositoryInterface $lockedRepository, $localRepository) public function __construct(RepositoryInterface $lockedRepository, InstalledRepositoryInterface $localRepository)
{ {
parent::__construct( parent::__construct(
$localRepository->getPackages(), $localRepository->getPackages(),

View File

@ -58,7 +58,11 @@ class LockTransaction extends Transaction
parent::__construct($this->presentMap, $this->resultPackages['all']); parent::__construct($this->presentMap, $this->resultPackages['all']);
} }
// TODO make this a bit prettier instead of the two text indexes? // TODO make this a bit prettier instead of the two text indexes?
/**
* @return void
*/
public function setResultPackages(Pool $pool, Decisions $decisions) public function setResultPackages(Pool $pool, Decisions $decisions)
{ {
$this->resultPackages = array('all' => array(), 'non-dev' => array(), 'dev' => array()); $this->resultPackages = array('all' => array(), 'non-dev' => array(), 'dev' => array());
@ -76,6 +80,9 @@ class LockTransaction extends Transaction
} }
} }
/**
* @return void
*/
public function setNonDevPackages(LockTransaction $extractionResult) public function setNonDevPackages(LockTransaction $extractionResult)
{ {
$packages = $extractionResult->getNewLockPackages(false); $packages = $extractionResult->getNewLockPackages(false);
@ -96,6 +103,8 @@ class LockTransaction extends Transaction
// TODO additionalFixedRepository needs to be looked at here as well? // TODO additionalFixedRepository needs to be looked at here as well?
/** /**
* @param bool $devMode
* @param bool $updateMirrors
* @return BasePackage[] * @return BasePackage[]
*/ */
public function getNewLockPackages($devMode, $updateMirrors = false) public function getNewLockPackages($devMode, $updateMirrors = false)
@ -126,6 +135,8 @@ class LockTransaction extends Transaction
/** /**
* Checks which of the given aliases from composer.json are actually in use for the lock file * Checks which of the given aliases from composer.json are actually in use for the lock file
* @param array<array{package: string, version: string, alias: string, alias_normalized: string}> $aliases
* @return array<array{package: string, version: string, alias: string, alias_normalized: string}>
*/ */
public function getAliases($aliases) public function getAliases($aliases)
{ {

View File

@ -12,9 +12,6 @@
namespace Composer\DependencyResolver; namespace Composer\DependencyResolver;
use Composer\Package\BasePackage;
use Composer\Package\Link;
/** /**
* @author Nils Adermann <naderman@naderman.de> * @author Nils Adermann <naderman@naderman.de>
* *
@ -26,7 +23,7 @@ class MultiConflictRule extends Rule
protected $literals; protected $literals;
/** /**
* @param int[] $literals * @param int[] $literals
*/ */
public function __construct(array $literals, $reason, $reasonData) public function __construct(array $literals, $reason, $reasonData)
{ {
@ -50,6 +47,9 @@ class MultiConflictRule extends Rule
return $this->literals; return $this->literals;
} }
/**
* @inheritDoc
*/
public function getHash() public function getHash()
{ {
$data = unpack('ihash', md5('c:'.implode(',', $this->literals), true)); $data = unpack('ihash', md5('c:'.implode(',', $this->literals), true));
@ -82,6 +82,10 @@ class MultiConflictRule extends Rule
return false; return false;
} }
/**
* @return never
* @throws \RuntimeException
*/
public function disable() public function disable()
{ {
throw new \RuntimeException("Disabling multi conflict rules is not possible. Please contact composer at https://github.com/composer/composer to let us debug what lead to this situation."); throw new \RuntimeException("Disabling multi conflict rules is not possible. Please contact composer at https://github.com/composer/composer to let us debug what lead to this situation.");

View File

@ -52,6 +52,7 @@ class InstallOperation extends SolverOperation implements OperationInterface
} }
/** /**
* @param bool $lock
* @return string * @return string
*/ */
public static function format(PackageInterface $package, $lock = false) public static function format(PackageInterface $package, $lock = false)

View File

@ -52,6 +52,7 @@ class UninstallOperation extends SolverOperation implements OperationInterface
} }
/** /**
* @param bool $lock
* @return string * @return string
*/ */
public static function format(PackageInterface $package, $lock = false) public static function format(PackageInterface $package, $lock = false)

View File

@ -73,6 +73,7 @@ class UpdateOperation extends SolverOperation implements OperationInterface
} }
/** /**
* @param bool $lock
* @return string * @return string
*/ */
public static function format(PackageInterface $initialPackage, PackageInterface $targetPackage, $lock = false) public static function format(PackageInterface $initialPackage, PackageInterface $targetPackage, $lock = false)

View File

@ -12,11 +12,11 @@
namespace Composer\DependencyResolver; namespace Composer\DependencyResolver;
use Composer\Package\BasePackage;
use Composer\Package\Version\VersionParser; use Composer\Package\Version\VersionParser;
use Composer\Semver\CompilingMatcher; use Composer\Semver\CompilingMatcher;
use Composer\Semver\Constraint\ConstraintInterface; use Composer\Semver\Constraint\ConstraintInterface;
use Composer\Semver\Constraint\Constraint; use Composer\Semver\Constraint\Constraint;
use Composer\Package\BasePackage;
/** /**
* A package pool contains all packages for dependency resolution * A package pool contains all packages for dependency resolution
@ -37,6 +37,10 @@ class Pool implements \Countable
/** @var BasePackage[] */ /** @var BasePackage[] */
protected $unacceptableFixedOrLockedPackages; protected $unacceptableFixedOrLockedPackages;
/**
* @param BasePackage[] $packages
* @param BasePackage[] $unacceptableFixedOrLockedPackages
*/
public function __construct(array $packages = array(), array $unacceptableFixedOrLockedPackages = array()) public function __construct(array $packages = array(), array $unacceptableFixedOrLockedPackages = array())
{ {
$this->versionParser = new VersionParser; $this->versionParser = new VersionParser;
@ -44,6 +48,10 @@ class Pool implements \Countable
$this->unacceptableFixedOrLockedPackages = $unacceptableFixedOrLockedPackages; $this->unacceptableFixedOrLockedPackages = $unacceptableFixedOrLockedPackages;
} }
/**
* @param BasePackage[] $packages
* @return void
*/
private function setPackages(array $packages) private function setPackages(array $packages)
{ {
$id = 1; $id = 1;
@ -91,10 +99,10 @@ class Pool implements \Countable
/** /**
* Searches all packages providing the given package name and match the constraint * Searches all packages providing the given package name and match the constraint
* *
* @param string $name The package name to be searched for * @param string $name The package name to be searched for
* @param ConstraintInterface $constraint A constraint that all returned * @param ?ConstraintInterface $constraint A constraint that all returned
* packages must match or null to return all * packages must match or null to return all
* @return BasePackage[] A set of packages * @return BasePackage[] A set of packages
*/ */
public function whatProvides($name, ConstraintInterface $constraint = null) public function whatProvides($name, ConstraintInterface $constraint = null)
{ {
@ -130,6 +138,7 @@ class Pool implements \Countable
} }
/** /**
* @param int $literal
* @return BasePackage * @return BasePackage
*/ */
public function literalToPackage($literal) public function literalToPackage($literal)
@ -140,6 +149,8 @@ class Pool implements \Countable
} }
/** /**
* @param int $literal
* @param array<int, BasePackage> $installedMap
* @return string * @return string
*/ */
public function literalToPrettyString($literal, $installedMap) public function literalToPrettyString($literal, $installedMap)
@ -159,9 +170,7 @@ class Pool implements \Countable
* Checks if the package matches the given constraint directly or through * Checks if the package matches the given constraint directly or through
* provided or replaced packages * provided or replaced packages
* *
* @param BasePackage $candidate
* @param string $name Name of the package to be matched * @param string $name Name of the package to be matched
* @param ConstraintInterface $constraint The constraint to verify
* @return bool * @return bool
*/ */
public function match(BasePackage $candidate, $name, ConstraintInterface $constraint = null) public function match(BasePackage $candidate, $name, ConstraintInterface $constraint = null)

View File

@ -18,12 +18,13 @@ use Composer\Package\AliasPackage;
use Composer\Package\BasePackage; use Composer\Package\BasePackage;
use Composer\Package\CompleteAliasPackage; use Composer\Package\CompleteAliasPackage;
use Composer\Package\CompletePackage; use Composer\Package\CompletePackage;
use Composer\Package\CompletePackageInterface;
use Composer\Package\PackageInterface; use Composer\Package\PackageInterface;
use Composer\Package\Version\StabilityFilter; use Composer\Package\Version\StabilityFilter;
use Composer\Plugin\PluginEvents; use Composer\Plugin\PluginEvents;
use Composer\Plugin\PrePoolCreateEvent; use Composer\Plugin\PrePoolCreateEvent;
use Composer\Repository\LockArrayRepository;
use Composer\Repository\PlatformRepository; use Composer\Repository\PlatformRepository;
use Composer\Repository\RepositoryInterface;
use Composer\Repository\RootPackageRepository; use Composer\Repository\RootPackageRepository;
use Composer\Semver\CompilingMatcher; use Composer\Semver\CompilingMatcher;
use Composer\Semver\Constraint\Constraint; use Composer\Semver\Constraint\Constraint;
@ -86,12 +87,11 @@ class PoolBuilder
*/ */
private $loadedPerRepo = array(); private $loadedPerRepo = array();
/** /**
* @var PackageInterface[] * @var BasePackage[]
*/ */
private $packages = array(); private $packages = array();
/** /**
* @var PackageInterface[] * @var BasePackage[]
* @phpstan-var list<PackageInterface>
*/ */
private $unacceptableFixedOrLockedPackages = array(); private $unacceptableFixedOrLockedPackages = array();
/** @var string[] */ /** @var string[] */
@ -140,6 +140,7 @@ class PoolBuilder
} }
/** /**
* @param RepositoryInterface[] $repositories
* @return Pool * @return Pool
*/ */
public function buildPool(array $repositories, Request $request) public function buildPool(array $repositories, Request $request)
@ -265,6 +266,7 @@ class PoolBuilder
} }
/** /**
* @param string $name
* @return void * @return void
*/ */
private function markPackageNameForLoading(Request $request, $name, ConstraintInterface $constraint) private function markPackageNameForLoading(Request $request, $name, ConstraintInterface $constraint)
@ -323,6 +325,7 @@ class PoolBuilder
} }
/** /**
* @param RepositoryInterface[] $repositories
* @return void * @return void
*/ */
private function loadPackagesMarkedForLoading(Request $request, $repositories) private function loadPackagesMarkedForLoading(Request $request, $repositories)
@ -358,6 +361,7 @@ class PoolBuilder
} }
/** /**
* @param bool $propagateUpdate
* @return void * @return void
*/ */
private function loadPackage(Request $request, BasePackage $package, $propagateUpdate = true) private function loadPackage(Request $request, BasePackage $package, $propagateUpdate = true)
@ -446,6 +450,7 @@ class PoolBuilder
/** /**
* Checks if a particular name is required directly in the request * Checks if a particular name is required directly in the request
* *
* @param string $name packageName
* @return bool * @return bool
*/ */
private function isRootRequire(Request $request, $name) private function isRootRequire(Request $request, $name)
@ -460,7 +465,7 @@ class PoolBuilder
* *
* @return bool * @return bool
*/ */
private function isUpdateAllowed(PackageInterface $package) private function isUpdateAllowed(BasePackage $package)
{ {
// Path repo packages are never loaded from lock, to force them to always remain in sync // Path repo packages are never loaded from lock, to force them to always remain in sync
// unless symlinking is disabled in which case we probably should rather treat them like // unless symlinking is disabled in which case we probably should rather treat them like
@ -513,6 +518,7 @@ class PoolBuilder
* Reverts the decision to use a locked package if a partial update with transitive dependencies * Reverts the decision to use a locked package if a partial update with transitive dependencies
* found that this package actually needs to be updated * found that this package actually needs to be updated
* *
* @param string $name
* @return void * @return void
*/ */
private function unlockPackage(Request $request, $name) private function unlockPackage(Request $request, $name)
@ -553,9 +559,10 @@ class PoolBuilder
} }
/** /**
* @param int $index
* @return void * @return void
*/ */
private function removeLoadedPackage(Request $request, PackageInterface $package, $index) private function removeLoadedPackage(Request $request, BasePackage $package, $index)
{ {
unset($this->packages[$index]); unset($this->packages[$index]);
if (isset($this->aliasMap[spl_object_hash($package)])) { if (isset($this->aliasMap[spl_object_hash($package)])) {

View File

@ -14,6 +14,8 @@ namespace Composer\DependencyResolver;
use Composer\Package\CompletePackageInterface; use Composer\Package\CompletePackageInterface;
use Composer\Package\AliasPackage; use Composer\Package\AliasPackage;
use Composer\Package\BasePackage;
use Composer\Package\PackageInterface;
use Composer\Package\RootPackageInterface; use Composer\Package\RootPackageInterface;
use Composer\Repository\RepositorySet; use Composer\Repository\RepositorySet;
use Composer\Repository\LockArrayRepository; use Composer\Repository\LockArrayRepository;
@ -47,6 +49,7 @@ class Problem
* Add a rule as a reason * Add a rule as a reason
* *
* @param Rule $rule A rule which is a reason for this problem * @param Rule $rule A rule which is a reason for this problem
* @return void
*/ */
public function addRule(Rule $rule) public function addRule(Rule $rule)
{ {
@ -56,7 +59,7 @@ class Problem
/** /**
* Retrieve all reasons for this problem * Retrieve all reasons for this problem
* *
* @return array The problem's reasons * @return array<int, array<int, Rule>> The problem's reasons
*/ */
public function getReasons() public function getReasons()
{ {
@ -66,7 +69,9 @@ class Problem
/** /**
* A human readable textual representation of the problem's reasons * A human readable textual representation of the problem's reasons
* *
* @param array $installedMap A map of all present packages * @param bool $isVerbose
* @param array<int|string, BasePackage> $installedMap A map of all present packages
* @param array<Rule[]> $learnedPool
* @return string * @return string
*/ */
public function getPrettyString(RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, array $installedMap = array(), array $learnedPool = array()) public function getPrettyString(RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, array $installedMap = array(), array $learnedPool = array())
@ -101,8 +106,13 @@ class Problem
} }
/** /**
* @internal * @param Rule[] $rules
* @param string $indent
* @param bool $isVerbose
* @param array<int|string, BasePackage> $installedMap A map of all present packages
* @param array<Rule[]> $learnedPool
* @return string * @return string
* @internal
*/ */
public static function formatDeduplicatedRules($rules, $indent, RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, array $installedMap = array(), array $learnedPool = array()) public static function formatDeduplicatedRules($rules, $indent, RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, array $installedMap = array(), array $learnedPool = array())
{ {
@ -166,7 +176,6 @@ class Problem
* *
* @param string $id A canonical identifier for the reason * @param string $id A canonical identifier for the reason
* @param Rule $reason The reason descriptor * @param Rule $reason The reason descriptor
*
* @return void * @return void
*/ */
protected function addReason($id, Rule $reason) protected function addReason($id, Rule $reason)
@ -190,9 +199,11 @@ class Problem
/** /**
* @internal * @internal
* @param bool $isVerbose
* @param string $packageName
* @return array{0: string, 1: string} * @return array{0: string, 1: string}
*/ */
public static function getMissingPackageReason(RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, $packageName, $constraint = null) public static function getMissingPackageReason(RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, $packageName, ConstraintInterface $constraint = null)
{ {
// handle php/hhvm // handle php/hhvm
if ($packageName === 'php' || $packageName === 'php-64bit' || $packageName === 'hhvm') { if ($packageName === 'php' || $packageName === 'php-64bit' || $packageName === 'hhvm') {
@ -343,6 +354,8 @@ class Problem
/** /**
* @internal * @internal
* @param PackageInterface[] $packages
* @param bool $isVerbose
* @return string * @return string
*/ */
public static function getPackageList(array $packages, $isVerbose) public static function getPackageList(array $packages, $isVerbose)
@ -395,7 +408,9 @@ class Problem
} }
/** /**
* @param string[] $versions an array of pretty versions, with normalized versions as keys * @param string[] $versions an array of pretty versions, with normalized versions as keys
* @param int $max
* @param int $maxDev
* @return list<string> a list of pretty versions and '...' where versions were removed * @return list<string> a list of pretty versions and '...' where versions were removed
*/ */
private static function condenseVersionList(array $versions, $max, $maxDev = 16) private static function condenseVersionList(array $versions, $max, $maxDev = 16)
@ -429,6 +444,7 @@ class Problem
} }
/** /**
* @param PackageInterface[] $packages
* @return bool * @return bool
*/ */
private static function hasMultipleNames(array $packages) private static function hasMultipleNames(array $packages)
@ -446,6 +462,12 @@ class Problem
} }
/** /**
* @param bool $isVerbose
* @param string $packageName
* @param ?ConstraintInterface $constraint
* @param PackageInterface[] $higherRepoPackages
* @param PackageInterface[] $allReposPackages
* @param string $reason
* @return array{0: string, 1: string} * @return array{0: string, 1: string}
*/ */
private static function computeCheckForLowerPrioRepo($isVerbose, $packageName, $constraint, array $higherRepoPackages, array $allReposPackages, $reason) private static function computeCheckForLowerPrioRepo($isVerbose, $packageName, $constraint, array $higherRepoPackages, array $allReposPackages, $reason)

View File

@ -12,8 +12,8 @@
namespace Composer\DependencyResolver; namespace Composer\DependencyResolver;
use Composer\Package\Package;
use Composer\Package\BasePackage; use Composer\Package\BasePackage;
use Composer\Package\PackageInterface;
use Composer\Repository\LockArrayRepository; use Composer\Repository\LockArrayRepository;
use Composer\Semver\Constraint\ConstraintInterface; use Composer\Semver\Constraint\ConstraintInterface;
use Composer\Semver\Constraint\MatchAllConstraint; use Composer\Semver\Constraint\MatchAllConstraint;
@ -60,6 +60,10 @@ class Request
$this->lockedRepository = $lockedRepository; $this->lockedRepository = $lockedRepository;
} }
/**
* @param string $packageName
* @return void
*/
public function requireName($packageName, ConstraintInterface $constraint = null) public function requireName($packageName, ConstraintInterface $constraint = null)
{ {
$packageName = strtolower($packageName); $packageName = strtolower($packageName);
@ -78,6 +82,8 @@ class Request
* *
* This is used for platform packages which cannot be modified by Composer. A rule enforcing their installation is * This is used for platform packages which cannot be modified by Composer. A rule enforcing their installation is
* generated for dependency resolution. Partial updates with dependencies cannot in any way modify these packages. * generated for dependency resolution. Partial updates with dependencies cannot in any way modify these packages.
*
* @return void
*/ */
public function fixPackage(BasePackage $package) public function fixPackage(BasePackage $package)
{ {
@ -93,6 +99,8 @@ class Request
* However unlike fixed packages there will not be a special rule enforcing their installation for the solver, so * However unlike fixed packages there will not be a special rule enforcing their installation for the solver, so
* if nothing requires these packages they will be removed. Additionally in a partial update these packages can be * if nothing requires these packages they will be removed. Additionally in a partial update these packages can be
* unlocked, meaning other versions can be installed if explicitly requested as part of the update. * unlocked, meaning other versions can be installed if explicitly requested as part of the update.
*
* @return void
*/ */
public function lockPackage(BasePackage $package) public function lockPackage(BasePackage $package)
{ {
@ -105,6 +113,8 @@ class Request
* This is necessary for the composer install step which verifies the lock file integrity and should not allow * This is necessary for the composer install step which verifies the lock file integrity and should not allow
* removal of any packages. At the same time lock packages there cannot simply be marked fixed, as error reporting * removal of any packages. At the same time lock packages there cannot simply be marked fixed, as error reporting
* would then report them as platform packages, so this still marks them as locked packages at the same time. * would then report them as platform packages, so this still marks them as locked packages at the same time.
*
* @return void
*/ */
public function fixLockedPackage(BasePackage $package) public function fixLockedPackage(BasePackage $package)
{ {
@ -112,11 +122,19 @@ class Request
$this->fixedLockedPackages[spl_object_hash($package)] = $package; $this->fixedLockedPackages[spl_object_hash($package)] = $package;
} }
/**
* @return void
*/
public function unlockPackage(BasePackage $package) public function unlockPackage(BasePackage $package)
{ {
unset($this->lockedPackages[spl_object_hash($package)]); unset($this->lockedPackages[spl_object_hash($package)]);
} }
/**
* @param string[] $updateAllowList
* @param false|self::UPDATE_* $updateAllowTransitiveDependencies
* @return void
*/
public function setUpdateAllowList($updateAllowList, $updateAllowTransitiveDependencies) public function setUpdateAllowList($updateAllowList, $updateAllowTransitiveDependencies)
{ {
$this->updateAllowList = $updateAllowList; $this->updateAllowList = $updateAllowList;
@ -182,7 +200,7 @@ class Request
/** /**
* @return bool * @return bool
*/ */
public function isLockedPackage(BasePackage $package) public function isLockedPackage(PackageInterface $package)
{ {
return isset($this->lockedPackages[spl_object_hash($package)]) || isset($this->fixedLockedPackages[spl_object_hash($package)]); return isset($this->lockedPackages[spl_object_hash($package)]) || isset($this->fixedLockedPackages[spl_object_hash($package)]);
} }
@ -195,10 +213,14 @@ class Request
return array_merge($this->fixedPackages, $this->lockedPackages); return array_merge($this->fixedPackages, $this->lockedPackages);
} }
// TODO look into removing the packageIds option, the only place true is used is for the installed map in the solver problems
// some locked packages may not be in the pool so they have a package->id of -1
/** /**
* @param bool $packageIds
* @return array<int|string, BasePackage> * @return array<int|string, BasePackage>
*
* @TODO look into removing the packageIds option, the only place true is used
* is for the installed map in the solver problems.
* Some locked packages may not be in the pool,
* so they have a package->id of -1
*/ */
public function getPresentMap($packageIds = false) public function getPresentMap($packageIds = false)
{ {

View File

@ -12,11 +12,11 @@
namespace Composer\DependencyResolver; namespace Composer\DependencyResolver;
use Composer\Package\Link;
use Composer\Package\BasePackage;
use Composer\Package\AliasPackage; use Composer\Package\AliasPackage;
use Composer\Repository\RepositorySet; use Composer\Package\BasePackage;
use Composer\Package\Link;
use Composer\Repository\PlatformRepository; use Composer\Repository\PlatformRepository;
use Composer\Repository\RepositorySet;
use Composer\Package\Version\VersionParser; use Composer\Package\Version\VersionParser;
use Composer\Semver\Constraint\Constraint; use Composer\Semver\Constraint\Constraint;
use Composer\Semver\Constraint\ConstraintInterface; use Composer\Semver\Constraint\ConstraintInterface;
@ -54,8 +54,8 @@ abstract class Rule
protected $reasonData; protected $reasonData;
/** /**
* @param self::RULE_* $reason A RULE_* constant describing the reason for generating this rule * @param self::RULE_* $reason A RULE_* constant describing the reason for generating this rule
* @param Link|BasePackage|ConstraintInterface|string $reasonData * @param mixed $reasonData
* *
* @phpstan-param ReasonData $reasonData * @phpstan-param ReasonData $reasonData
*/ */
@ -68,26 +68,42 @@ abstract class Rule
(255 << self::BITFIELD_TYPE); (255 << self::BITFIELD_TYPE);
} }
/**
* @return int[]
*/
abstract public function getLiterals(); abstract public function getLiterals();
/**
* @return int|string
*/
abstract public function getHash(); abstract public function getHash();
abstract public function __toString(); abstract public function __toString();
/**
* @param Rule $rule
* @return bool
*/
abstract public function equals(Rule $rule); abstract public function equals(Rule $rule);
/**
* @return int
*/
public function getReason() public function getReason()
{ {
return ($this->bitfield & (255 << self::BITFIELD_REASON)) >> self::BITFIELD_REASON; return ($this->bitfield & (255 << self::BITFIELD_REASON)) >> self::BITFIELD_REASON;
} }
/**
* @phpstan-return ReasonData
*/
public function getReasonData() public function getReasonData()
{ {
return $this->reasonData; return $this->reasonData;
} }
/** /**
* @return ?string * @return string|null
*/ */
public function getRequiredPackage() public function getRequiredPackage()
{ {
@ -108,38 +124,63 @@ abstract class Rule
return null; return null;
} }
/**
* @param 255|RuleSet::TYPE_* $type
* @return void
*/
public function setType($type) public function setType($type)
{ {
$this->bitfield = ($this->bitfield & ~(255 << self::BITFIELD_TYPE)) | ((255 & $type) << self::BITFIELD_TYPE); $this->bitfield = ($this->bitfield & ~(255 << self::BITFIELD_TYPE)) | ((255 & $type) << self::BITFIELD_TYPE);
} }
/**
* @return int
*/
public function getType() public function getType()
{ {
return ($this->bitfield & (255 << self::BITFIELD_TYPE)) >> self::BITFIELD_TYPE; return ($this->bitfield & (255 << self::BITFIELD_TYPE)) >> self::BITFIELD_TYPE;
} }
/**
* @return void
*/
public function disable() public function disable()
{ {
$this->bitfield = ($this->bitfield & ~(255 << self::BITFIELD_DISABLED)) | (1 << self::BITFIELD_DISABLED); $this->bitfield = ($this->bitfield & ~(255 << self::BITFIELD_DISABLED)) | (1 << self::BITFIELD_DISABLED);
} }
/**
* @return void
*/
public function enable() public function enable()
{ {
$this->bitfield &= ~(255 << self::BITFIELD_DISABLED); $this->bitfield &= ~(255 << self::BITFIELD_DISABLED);
} }
/**
* @return bool
*/
public function isDisabled() public function isDisabled()
{ {
return (bool) (($this->bitfield & (255 << self::BITFIELD_DISABLED)) >> self::BITFIELD_DISABLED); return (bool) (($this->bitfield & (255 << self::BITFIELD_DISABLED)) >> self::BITFIELD_DISABLED);
} }
/**
* @return bool
*/
public function isEnabled() public function isEnabled()
{ {
return !(($this->bitfield & (255 << self::BITFIELD_DISABLED)) >> self::BITFIELD_DISABLED); return !(($this->bitfield & (255 << self::BITFIELD_DISABLED)) >> self::BITFIELD_DISABLED);
} }
/**
* @return bool
*/
abstract public function isAssertion(); abstract public function isAssertion();
/**
* @return bool
*/
public function isCausedByLock(RepositorySet $repositorySet, Request $request, Pool $pool) public function isCausedByLock(RepositorySet $repositorySet, Request $request, Pool $pool)
{ {
if ($this->getReason() === self::RULE_PACKAGE_REQUIRES) { if ($this->getReason() === self::RULE_PACKAGE_REQUIRES) {
@ -187,6 +228,12 @@ abstract class Rule
return false; return false;
} }
/**
* @param bool $isVerbose
* @param BasePackage[] $installedMap
* @param array<Rule[]> $learnedPool
* @return string
*/
public function getPrettyString(RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, array $installedMap = array(), array $learnedPool = array()) public function getPrettyString(RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, array $installedMap = array(), array $learnedPool = array())
{ {
$literals = $this->getLiterals(); $literals = $this->getLiterals();
@ -396,12 +443,11 @@ abstract class Rule
} }
/** /**
* @param Pool $pool * @param array<int|BasePackage> $packages An array containing packages or literals
* @param array $packages * @param bool $isVerbose
*
* @return string * @return string
*/ */
protected function formatPackagesUnique($pool, array $packages, $isVerbose) protected function formatPackagesUnique(Pool $pool, array $packages, $isVerbose)
{ {
foreach ($packages as $index => $package) { foreach ($packages as $index => $package) {
if (!\is_object($package)) { if (!\is_object($package)) {
@ -412,6 +458,9 @@ abstract class Rule
return Problem::getPackageList($packages, $isVerbose); return Problem::getPackageList($packages, $isVerbose);
} }
/**
* @return BasePackage
*/
private function deduplicateDefaultBranchAlias(BasePackage $package) private function deduplicateDefaultBranchAlias(BasePackage $package)
{ {
if ($package instanceof AliasPackage && $package->getPrettyVersion() === VersionParser::DEFAULT_BRANCH_ALIAS) { if ($package instanceof AliasPackage && $package->getPrettyVersion() === VersionParser::DEFAULT_BRANCH_ALIAS) {

View File

@ -12,11 +12,9 @@
namespace Composer\DependencyResolver; namespace Composer\DependencyResolver;
use Composer\Package\BasePackage;
use Composer\Package\Link;
/** /**
* @author Nils Adermann <naderman@naderman.de> * @author Nils Adermann <naderman@naderman.de>
* @phpstan-import-type ReasonData from Rule
*/ */
class Rule2Literals extends Rule class Rule2Literals extends Rule
{ {
@ -26,8 +24,12 @@ class Rule2Literals extends Rule
protected $literal2; protected $literal2;
/** /**
* @param int $literal1 * @param int $literal1
* @param int $literal2 * @param int $literal2
* @param Rule::RULE_* $reason A RULE_* constant
* @param mixed $reasonData
*
* @phpstan-param ReasonData $reasonData
*/ */
public function __construct($literal1, $literal2, $reason, $reasonData) public function __construct($literal1, $literal2, $reason, $reasonData)
{ {
@ -48,7 +50,9 @@ class Rule2Literals extends Rule
return array($this->literal1, $this->literal2); return array($this->literal1, $this->literal2);
} }
/** @return string */ /**
* @inheritDoc
*/
public function getHash() public function getHash()
{ {
return $this->literal1.','.$this->literal2; return $this->literal1.','.$this->literal2;

View File

@ -56,6 +56,10 @@ class RuleSet implements \IteratorAggregate, \Countable
} }
} }
/**
* @param 255|self::TYPE_* $type
* @return void
*/
public function add(Rule $rule, $type) public function add(Rule $rule, $type)
{ {
if (!isset(self::$types[$type])) { if (!isset(self::$types[$type])) {
@ -110,6 +114,7 @@ class RuleSet implements \IteratorAggregate, \Countable
} }
/** /**
* @param int $id
* @return Rule * @return Rule
*/ */
public function ruleById($id) public function ruleById($id)
@ -155,6 +160,7 @@ class RuleSet implements \IteratorAggregate, \Countable
} }
/** /**
* @param array<self::TYPE_*>|self::TYPE_* $types
* @return RuleSetIterator * @return RuleSetIterator
*/ */
public function getIteratorWithout($types) public function getIteratorWithout($types)
@ -182,6 +188,7 @@ class RuleSet implements \IteratorAggregate, \Countable
} }
/** /**
* @param bool $isVerbose
* @return string * @return string
*/ */
public function getPrettyString(RepositorySet $repositorySet = null, Request $request = null, Pool $pool = null, $isVerbose = false) public function getPrettyString(RepositorySet $repositorySet = null, Request $request = null, Pool $pool = null, $isVerbose = false)

View File

@ -14,7 +14,6 @@ namespace Composer\DependencyResolver;
use Composer\Package\BasePackage; use Composer\Package\BasePackage;
use Composer\Package\AliasPackage; use Composer\Package\AliasPackage;
use Composer\Package\PackageInterface;
use Composer\Repository\PlatformRepository; use Composer\Repository\PlatformRepository;
/** /**
@ -29,9 +28,9 @@ class RuleSetGenerator
protected $pool; protected $pool;
/** @var RuleSet */ /** @var RuleSet */
protected $rules; protected $rules;
/** @var array<int, PackageInterface> */ /** @var array<int, BasePackage> */
protected $addedMap = array(); protected $addedMap = array();
/** @var array<string, PackageInterface[]> */ /** @var array<string, BasePackage[]> */
protected $addedPackagesByNames = array(); protected $addedPackagesByNames = array();
public function __construct(PolicyInterface $policy, Pool $pool) public function __construct(PolicyInterface $policy, Pool $pool)
@ -47,13 +46,11 @@ class RuleSetGenerator
* This rule is of the form (-A|B|C), where B and C are the providers of * This rule is of the form (-A|B|C), where B and C are the providers of
* one requirement of the package A. * one requirement of the package A.
* *
* @param BasePackage $package The package with a requirement * @param BasePackage $package The package with a requirement
* @param array $providers The providers of the requirement * @param BasePackage[] $providers The providers of the requirement
* @param Rule::RULE_* $reason A RULE_* constant describing the * @param Rule::RULE_* $reason A RULE_* constant describing the reason for generating this rule
* reason for generating this rule * @param mixed $reasonData Any data, e.g. the requirement name, that goes with the reason
* @param mixed $reasonData Any data, e.g. the requirement name, * @return Rule|null The generated rule or null if tautological
* that goes with the reason
* @return Rule|null The generated rule or null if tautological
* *
* @phpstan-param ReasonData $reasonData * @phpstan-param ReasonData $reasonData
*/ */
@ -102,13 +99,11 @@ class RuleSetGenerator
* The rule for conflicting packages A and B is (-A|-B). A is called the issuer * The rule for conflicting packages A and B is (-A|-B). A is called the issuer
* and B the provider. * and B the provider.
* *
* @param BasePackage $issuer The package declaring the conflict * @param BasePackage $issuer The package declaring the conflict
* @param BasePackage $provider The package causing the conflict * @param BasePackage $provider The package causing the conflict
* @param Rule::RULE_* $reason A RULE_* constant describing the * @param Rule::RULE_* $reason A RULE_* constant describing the reason for generating this rule
* reason for generating this rule * @param mixed $reasonData Any data, e.g. the package name, that goes with the reason
* @param mixed $reasonData Any data, e.g. the package name, that * @return ?Rule The generated rule
* goes with the reason
* @return Rule|null The generated rule
* *
* @phpstan-param ReasonData $reasonData * @phpstan-param ReasonData $reasonData
*/ */
@ -123,9 +118,14 @@ class RuleSetGenerator
} }
/** /**
* @param BasePackage[] $packages
* @param Rule::RULE_* $reason A RULE_* constant
* @param mixed $reasonData
* @return Rule * @return Rule
*
* @phpstan-param ReasonData $reasonData
*/ */
protected function createMultiConflictRule(array $packages, $reason, $reasonData = null) protected function createMultiConflictRule(array $packages, $reason, $reasonData)
{ {
$literals = array(); $literals = array();
foreach ($packages as $package) { foreach ($packages as $package) {
@ -145,7 +145,7 @@ class RuleSetGenerator
* To be able to directly pass in the result of one of the rule creation * To be able to directly pass in the result of one of the rule creation
* methods null is allowed which will not insert a rule. * methods null is allowed which will not insert a rule.
* *
* @param int $type A TYPE_* constant defining the rule type * @param 255|RuleSet::TYPE_* $type A TYPE_* constant defining the rule type
* @param Rule $newRule The rule about to be added * @param Rule $newRule The rule about to be added
* *
* @return void * @return void
@ -160,6 +160,7 @@ class RuleSetGenerator
} }
/** /**
* @param bool|string[] $ignorePlatformReqs
* @return void * @return void
*/ */
protected function addRulesForPackage(BasePackage $package, $ignorePlatformReqs) protected function addRulesForPackage(BasePackage $package, $ignorePlatformReqs)
@ -211,6 +212,7 @@ class RuleSetGenerator
} }
/** /**
* @param bool|string[] $ignorePlatformReqs
* @return void * @return void
*/ */
protected function addConflictRules($ignorePlatformReqs = false) protected function addConflictRules($ignorePlatformReqs = false)
@ -249,6 +251,7 @@ class RuleSetGenerator
} }
/** /**
* @param bool|string[] $ignorePlatformReqs
* @return void * @return void
*/ */
protected function addRulesForRequest(Request $request, $ignorePlatformReqs) protected function addRulesForRequest(Request $request, $ignorePlatformReqs)
@ -293,6 +296,7 @@ class RuleSetGenerator
} }
/** /**
* @param bool|string[] $ignorePlatformReqs
* @return void * @return void
*/ */
protected function addRulesForRootAliases($ignorePlatformReqs) protected function addRulesForRootAliases($ignorePlatformReqs)
@ -311,7 +315,7 @@ class RuleSetGenerator
} }
/** /**
* @param bool|array $ignorePlatformReqs * @param bool|string[] $ignorePlatformReqs
* @return RuleSet * @return RuleSet
*/ */
public function getRulesFor(Request $request, $ignorePlatformReqs = false) public function getRulesFor(Request $request, $ignorePlatformReqs = false)

View File

@ -27,6 +27,7 @@ class RuleWatchChain extends \SplDoublyLinkedList
* Moves the internal iterator to the specified offset * Moves the internal iterator to the specified offset
* *
* @param int $offset The offset to seek to. * @param int $offset The offset to seek to.
* @return void
*/ */
public function seek($offset) public function seek($offset)
{ {
@ -41,6 +42,8 @@ class RuleWatchChain extends \SplDoublyLinkedList
* incorrectly sets the internal iterator if you delete the current value * incorrectly sets the internal iterator if you delete the current value
* this method sets the internal iterator back to the following element * this method sets the internal iterator back to the following element
* using the seek method. * using the seek method.
*
* @return void
*/ */
public function remove() public function remove()
{ {

View File

@ -38,6 +38,7 @@ class RuleWatchGraph
* watch changes in any literals. * watch changes in any literals.
* *
* @param RuleWatchNode $node The rule node to be inserted into the graph * @param RuleWatchNode $node The rule node to be inserted into the graph
* @return void
*/ */
public function insert(RuleWatchNode $node) public function insert(RuleWatchNode $node)
{ {
@ -87,7 +88,7 @@ class RuleWatchGraph
* register decisions resulting from propagation * register decisions resulting from propagation
* @return Rule|null If a conflict is found the conflicting rule is returned * @return Rule|null If a conflict is found the conflicting rule is returned
*/ */
public function propagateLiteral($decidedLiteral, $level, $decisions) public function propagateLiteral($decidedLiteral, $level, Decisions $decisions)
{ {
// we invert the decided literal here, example: // we invert the decided literal here, example:
// A was decided => (-A|B) now requires B to be true, so we look for // A was decided => (-A|B) now requires B to be true, so we look for
@ -153,6 +154,7 @@ class RuleWatchGraph
* @param int $fromLiteral A literal the node used to watch * @param int $fromLiteral A literal the node used to watch
* @param int $toLiteral A literal the node should watch now * @param int $toLiteral A literal the node should watch now
* @param RuleWatchNode $node The rule node to be moved * @param RuleWatchNode $node The rule node to be moved
* @return void
*/ */
protected function moveWatch($fromLiteral, $toLiteral, RuleWatchNode $node) protected function moveWatch($fromLiteral, $toLiteral, RuleWatchNode $node)
{ {

View File

@ -52,6 +52,7 @@ class RuleWatchNode
* likely to quickly lead to further decisions. * likely to quickly lead to further decisions.
* *
* @param Decisions $decisions The decisions made so far by the solver * @param Decisions $decisions The decisions made so far by the solver
* @return void
*/ */
public function watch2OnHighest(Decisions $decisions) public function watch2OnHighest(Decisions $decisions)
{ {
@ -104,6 +105,7 @@ class RuleWatchNode
* *
* @param int $from The previously watched literal * @param int $from The previously watched literal
* @param int $to The literal to be watched now * @param int $to The literal to be watched now
* @return void
*/ */
public function moveWatch($from, $to) public function moveWatch($from, $to)
{ {

View File

@ -56,11 +56,6 @@ class Solver
/** @var IOInterface */ /** @var IOInterface */
protected $io; protected $io;
/**
* @param PolicyInterface $policy
* @param Pool $pool
* @param IOInterface $io
*/
public function __construct(PolicyInterface $policy, Pool $pool, IOInterface $io) public function __construct(PolicyInterface $policy, Pool $pool, IOInterface $io)
{ {
$this->io = $io; $this->io = $io;
@ -171,9 +166,7 @@ class Solver
} }
/** /**
* @param Request $request * @param bool|string[] $ignorePlatformReqs
* @param bool|array $ignorePlatformReqs
*
* @return void * @return void
*/ */
protected function checkForRootRequireProblems(Request $request, $ignorePlatformReqs) protected function checkForRootRequireProblems(Request $request, $ignorePlatformReqs)
@ -192,8 +185,7 @@ class Solver
} }
/** /**
* @param Request $request * @param bool|string[] $ignorePlatformReqs
* @param bool|array $ignorePlatformReqs
* @return LockTransaction * @return LockTransaction
*/ */
public function solve(Request $request, $ignorePlatformReqs = false) public function solve(Request $request, $ignorePlatformReqs = false)
@ -304,7 +296,6 @@ class Solver
* *
* @param int $level * @param int $level
* @param string|int $literal * @param string|int $literal
* @param Rule $rule
* @return int * @return int
*/ */
private function setPropagateLearn($level, $literal, Rule $rule) private function setPropagateLearn($level, $literal, Rule $rule)
@ -332,11 +323,6 @@ class Solver
"Trying to revert to invalid level ".(int) $newLevel." from level ".(int) $level."." "Trying to revert to invalid level ".(int) $newLevel." from level ".(int) $level."."
); );
} }
if (!$newRule) {
throw new SolverBugException(
"No rule was learned from analyzing $rule at level $level."
);
}
$level = $newLevel; $level = $newLevel;
@ -358,8 +344,7 @@ class Solver
/** /**
* @param int $level * @param int $level
* @param array $decisionQueue * @param int[] $decisionQueue
* @param Rule $rule
* @return int * @return int
*/ */
private function selectAndInstall($level, array $decisionQueue, Rule $rule) private function selectAndInstall($level, array $decisionQueue, Rule $rule)
@ -379,8 +364,7 @@ class Solver
/** /**
* @param int $level * @param int $level
* @param Rule $rule * @return array{int, int, GenericRule, int}
* @return array
*/ */
protected function analyze($level, Rule $rule) protected function analyze($level, Rule $rule)
{ {
@ -527,6 +511,7 @@ class Solver
} }
/** /**
* @param array<string, true> $ruleSeen
* @return void * @return void
*/ */
private function analyzeUnsolvableRule(Problem $problem, Rule $conflictRule, array &$ruleSeen) private function analyzeUnsolvableRule(Problem $problem, Rule $conflictRule, array &$ruleSeen)
@ -557,7 +542,6 @@ class Solver
} }
/** /**
* @param Rule $conflictRule
* @return int * @return int
*/ */
private function analyzeUnsolvable(Rule $conflictRule) private function analyzeUnsolvable(Rule $conflictRule)

View File

@ -17,6 +17,9 @@ namespace Composer\DependencyResolver;
*/ */
class SolverBugException extends \RuntimeException class SolverBugException extends \RuntimeException
{ {
/**
* @param string $message
*/
public function __construct($message) public function __construct($message)
{ {
parent::__construct( parent::__construct(

View File

@ -14,7 +14,6 @@ namespace Composer\DependencyResolver;
use Composer\Util\IniHelper; use Composer\Util\IniHelper;
use Composer\Repository\RepositorySet; use Composer\Repository\RepositorySet;
use Composer\Package\PackageInterface;
/** /**
* @author Nils Adermann <naderman@naderman.de> * @author Nils Adermann <naderman@naderman.de>
@ -29,7 +28,7 @@ class SolverProblemsException extends \RuntimeException
protected $learnedPool; protected $learnedPool;
/** /**
* @param Problem[] $problems * @param Problem[] $problems
* @param array<Rule[]> $learnedPool * @param array<Rule[]> $learnedPool
*/ */
public function __construct(array $problems, array $learnedPool) public function __construct(array $problems, array $learnedPool)
@ -41,6 +40,8 @@ class SolverProblemsException extends \RuntimeException
} }
/** /**
* @param bool $isVerbose
* @param bool $isDevExtraction
* @return string * @return string
*/ */
public function getPrettyString(RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, $isDevExtraction = false) public function getPrettyString(RepositorySet $repositorySet, Request $request, Pool $pool, $isVerbose, $isDevExtraction = false)
@ -123,6 +124,7 @@ class SolverProblemsException extends \RuntimeException
} }
/** /**
* @param Rule[][] $reasonSets
* @return bool * @return bool
*/ */
private function hasExtensionProblems(array $reasonSets) private function hasExtensionProblems(array $reasonSets)

View File

@ -46,6 +46,10 @@ class Transaction
*/ */
protected $resultPackagesByName = array(); protected $resultPackagesByName = array();
/**
* @param PackageInterface[] $presentPackages
* @param PackageInterface[] $resultPackages
*/
public function __construct($presentPackages, $resultPackages) public function __construct($presentPackages, $resultPackages)
{ {
$this->presentPackages = $presentPackages; $this->presentPackages = $presentPackages;
@ -53,12 +57,18 @@ class Transaction
$this->operations = $this->calculateOperations(); $this->operations = $this->calculateOperations();
} }
/** @return OperationInterface[] */ /**
* @return OperationInterface[]
*/
public function getOperations() public function getOperations()
{ {
return $this->operations; return $this->operations;
} }
/**
* @param PackageInterface[] $resultPackages
* @return void
*/
private function setResultPackageMaps($resultPackages) private function setResultPackageMaps($resultPackages)
{ {
$packageSort = function (PackageInterface $a, PackageInterface $b) { $packageSort = function (PackageInterface $a, PackageInterface $b) {
@ -88,6 +98,9 @@ class Transaction
} }
} }
/**
* @return OperationInterface[]
*/
protected function calculateOperations() protected function calculateOperations()
{ {
$operations = array(); $operations = array();
@ -228,6 +241,9 @@ class Transaction
return $roots; return $roots;
} }
/**
* @return PackageInterface[]
*/
protected function getProvidersInResult(Link $link) protected function getProvidersInResult(Link $link)
{ {
if (!isset($this->resultPackagesByName[$link->getTarget()])) { if (!isset($this->resultPackagesByName[$link->getTarget()])) {

View File

@ -15,7 +15,6 @@ namespace Composer\Plugin;
use Composer\EventDispatcher\Event; use Composer\EventDispatcher\Event;
use Composer\Repository\RepositoryInterface; use Composer\Repository\RepositoryInterface;
use Composer\DependencyResolver\Request; use Composer\DependencyResolver\Request;
use Composer\Package\PackageInterface;
use Composer\Package\BasePackage; use Composer\Package\BasePackage;
/** /**
@ -54,11 +53,11 @@ class PrePoolCreateEvent extends Event
*/ */
private $rootReferences; private $rootReferences;
/** /**
* @var PackageInterface[] * @var BasePackage[]
*/ */
private $packages; private $packages;
/** /**
* @var PackageInterface[] * @var BasePackage[]
*/ */
private $unacceptableFixedPackages; private $unacceptableFixedPackages;
@ -69,6 +68,8 @@ class PrePoolCreateEvent extends Event
* @param int[] $stabilityFlags array of package name => BasePackage::STABILITY_* value * @param int[] $stabilityFlags array of package name => BasePackage::STABILITY_* value
* @param array[] $rootAliases array of package => version => [alias, alias_normalized] * @param array[] $rootAliases array of package => version => [alias, alias_normalized]
* @param string[] $rootReferences * @param string[] $rootReferences
* @param BasePackage[] $packages
* @param BasePackage[] $unacceptableFixedPackages
* *
* @phpstan-param array<string, BasePackage::STABILITY_*> $acceptableStabilities * @phpstan-param array<string, BasePackage::STABILITY_*> $acceptableStabilities
* @phpstan-param array<string, BasePackage::STABILITY_*> $stabilityFlags * @phpstan-param array<string, BasePackage::STABILITY_*> $stabilityFlags
@ -142,7 +143,7 @@ class PrePoolCreateEvent extends Event
} }
/** /**
* @return PackageInterface[] * @return BasePackage[]
*/ */
public function getPackages() public function getPackages()
{ {
@ -150,7 +151,7 @@ class PrePoolCreateEvent extends Event
} }
/** /**
* @return PackageInterface[] * @return BasePackage[]
*/ */
public function getUnacceptableFixedPackages() public function getUnacceptableFixedPackages()
{ {
@ -158,7 +159,7 @@ class PrePoolCreateEvent extends Event
} }
/** /**
* @param PackageInterface[] $packages * @param BasePackage[] $packages
*/ */
public function setPackages(array $packages) public function setPackages(array $packages)
{ {
@ -166,7 +167,7 @@ class PrePoolCreateEvent extends Event
} }
/** /**
* @param PackageInterface[] $packages * @param BasePackage[] $packages
*/ */
public function setUnacceptableFixedPackages(array $packages) public function setUnacceptableFixedPackages(array $packages)
{ {

View File

@ -68,6 +68,7 @@ class RuleSetTest extends TestCase
$ruleSet = new RuleSet; $ruleSet = new RuleSet;
$this->setExpectedException('OutOfBoundsException'); $this->setExpectedException('OutOfBoundsException');
// @phpstan-ignore-next-line
$ruleSet->add(new GenericRule(array(), Rule::RULE_ROOT_REQUIRE, array('packageName' => '', 'constraint' => new MatchAllConstraint)), 7); $ruleSet->add(new GenericRule(array(), Rule::RULE_ROOT_REQUIRE, array('packageName' => '', 'constraint' => new MatchAllConstraint)), 7);
} }