VersionConstraintParser.php 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115
  1. <?php declare(strict_types = 1);
  2. /*
  3. * This file is part of PharIo\Version.
  4. *
  5. * (c) Arne Blankerts <arne@blankerts.de>, Sebastian Heuer <sebastian@phpeople.de>, Sebastian Bergmann <sebastian@phpunit.de>
  6. *
  7. * For the full copyright and license information, please view the LICENSE
  8. * file that was distributed with this source code.
  9. */
  10. namespace PharIo\Version;
  11. class VersionConstraintParser {
  12. /**
  13. * @throws UnsupportedVersionConstraintException
  14. */
  15. public function parse(string $value): VersionConstraint {
  16. if (\strpos($value, '|') !== false) {
  17. return $this->handleOrGroup($value);
  18. }
  19. if (!\preg_match('/^[\^~*]?v?[\d.*]+(?:-.*)?$/i', $value)) {
  20. throw new UnsupportedVersionConstraintException(
  21. \sprintf('Version constraint %s is not supported.', $value)
  22. );
  23. }
  24. switch ($value[0]) {
  25. case '~':
  26. return $this->handleTildeOperator($value);
  27. case '^':
  28. return $this->handleCaretOperator($value);
  29. }
  30. $constraint = new VersionConstraintValue($value);
  31. if ($constraint->getMajor()->isAny()) {
  32. return new AnyVersionConstraint();
  33. }
  34. if ($constraint->getMinor()->isAny()) {
  35. return new SpecificMajorVersionConstraint(
  36. $constraint->getVersionString(),
  37. $constraint->getMajor()->getValue() ?? 0
  38. );
  39. }
  40. if ($constraint->getPatch()->isAny()) {
  41. return new SpecificMajorAndMinorVersionConstraint(
  42. $constraint->getVersionString(),
  43. $constraint->getMajor()->getValue() ?? 0,
  44. $constraint->getMinor()->getValue() ?? 0
  45. );
  46. }
  47. return new ExactVersionConstraint($constraint->getVersionString());
  48. }
  49. private function handleOrGroup(string $value): OrVersionConstraintGroup {
  50. $constraints = [];
  51. foreach (\preg_split('{\s*\|\|?\s*}', \trim($value)) as $groupSegment) {
  52. $constraints[] = $this->parse(\trim($groupSegment));
  53. }
  54. return new OrVersionConstraintGroup($value, $constraints);
  55. }
  56. private function handleTildeOperator(string $value): AndVersionConstraintGroup {
  57. $constraintValue = new VersionConstraintValue(\substr($value, 1));
  58. if ($constraintValue->getPatch()->isAny()) {
  59. return $this->handleCaretOperator($value);
  60. }
  61. $constraints = [
  62. new GreaterThanOrEqualToVersionConstraint(
  63. $value,
  64. new Version(\substr($value, 1))
  65. ),
  66. new SpecificMajorAndMinorVersionConstraint(
  67. $value,
  68. $constraintValue->getMajor()->getValue() ?? 0,
  69. $constraintValue->getMinor()->getValue() ?? 0
  70. )
  71. ];
  72. return new AndVersionConstraintGroup($value, $constraints);
  73. }
  74. private function handleCaretOperator(string $value): AndVersionConstraintGroup {
  75. $constraintValue = new VersionConstraintValue(\substr($value, 1));
  76. $constraints = [
  77. new GreaterThanOrEqualToVersionConstraint($value, new Version(\substr($value, 1)))
  78. ];
  79. if ($constraintValue->getMajor()->getValue() === 0) {
  80. $constraints[] = new SpecificMajorAndMinorVersionConstraint(
  81. $value,
  82. $constraintValue->getMajor()->getValue() ?? 0,
  83. $constraintValue->getMinor()->getValue() ?? 0
  84. );
  85. } else {
  86. $constraints[] = new SpecificMajorVersionConstraint(
  87. $value,
  88. $constraintValue->getMajor()->getValue() ?? 0
  89. );
  90. }
  91. return new AndVersionConstraintGroup(
  92. $value,
  93. $constraints
  94. );
  95. }
  96. }