From 71f8b753da9d1cac90365fcd267d5d0a06fe8d64 Mon Sep 17 00:00:00 2001 From: James Titcumb Date: Mon, 19 Jan 2026 15:24:55 +0000 Subject: [PATCH 1/2] 446: Fix versions not parsing when PHP_VERSION is not semver-compat Reverts commit 2962d921bec1223c7b6df96404e9be28edfc34c1 Presumably this was changed for simplicity, but there was no test to ensure any PHP builds with non-semver-compatible version strings don't crash --- src/Platform/TargetPhp/PhpBinaryPath.php | 2 +- test/assets/fake-php-invalid-version.sh | 26 +++++++++++++++++++ .../Command/InstallCommandTest.php | 2 ++ .../Installing/UnixInstallTest.php | 3 +++ .../Platform/TargetPhp/PhpBinaryPathTest.php | 19 ++++++++++++++ 5 files changed, 51 insertions(+), 1 deletion(-) create mode 100755 test/assets/fake-php-invalid-version.sh diff --git a/src/Platform/TargetPhp/PhpBinaryPath.php b/src/Platform/TargetPhp/PhpBinaryPath.php index 8dabf97d..63682c7b 100644 --- a/src/Platform/TargetPhp/PhpBinaryPath.php +++ b/src/Platform/TargetPhp/PhpBinaryPath.php @@ -299,7 +299,7 @@ public function version(): string $phpVersion = self::cleanWarningAndDeprecationsFromOutput(Process::run([ $this->phpBinaryPath, '-r', - 'echo PHP_VERSION;', + 'echo PHP_MAJOR_VERSION . "." . PHP_MINOR_VERSION . "." . PHP_RELEASE_VERSION;', ])); Assert::stringNotEmpty($phpVersion, 'Could not determine PHP version'); diff --git a/test/assets/fake-php-invalid-version.sh b/test/assets/fake-php-invalid-version.sh new file mode 100755 index 00000000..416428d5 --- /dev/null +++ b/test/assets/fake-php-invalid-version.sh @@ -0,0 +1,26 @@ +#!/usr/bin/env bash + +ARGS="$*" + +case "$ARGS" in + "-r echo \"PHP\";") + echo "PHP"; + exit 0 + ;; + "-r echo PHP_VERSION;") + echo "5.6.40-90+ubuntu24.04.1+deb.sury.org+1"; + exit 0 + ;; + "-r echo PHP_MAJOR_VERSION . \".\" . PHP_MINOR_VERSION . \".\" . PHP_RELEASE_VERSION;") + echo "5.6.40"; + exit 0 + ;; + "-r echo PHP_MAJOR_VERSION . \".\" . PHP_MINOR_VERSION;") + echo "5.6"; + exit 0 + ;; + *) + echo "unknown fake php command: $ARGS" + exit 1 +esac + diff --git a/test/integration/Command/InstallCommandTest.php b/test/integration/Command/InstallCommandTest.php index 531c8cd8..dd39e533 100644 --- a/test/integration/Command/InstallCommandTest.php +++ b/test/integration/Command/InstallCommandTest.php @@ -50,6 +50,8 @@ public static function phpPathProvider(): array $possiblePhpConfigPaths = array_filter( [ '/usr/bin/php-config', + '/usr/bin/php-config8.5', + '/usr/bin/php-config8.4', '/usr/bin/php-config8.3', '/usr/bin/php-config8.2', '/usr/bin/php-config8.1', diff --git a/test/integration/Installing/UnixInstallTest.php b/test/integration/Installing/UnixInstallTest.php index cd58849f..cae63683 100644 --- a/test/integration/Installing/UnixInstallTest.php +++ b/test/integration/Installing/UnixInstallTest.php @@ -47,12 +47,15 @@ public static function phpPathProvider(): array $possiblePhpConfigPaths = array_filter( [ '/usr/bin/php-config', + '/usr/bin/php-config8.5', '/usr/bin/php-config8.4', '/usr/bin/php-config8.3', '/usr/bin/php-config8.2', '/usr/bin/php-config8.1', '/usr/bin/php-config8.0', '/usr/bin/php-config7.4', + '/usr/bin/php-config7.3', + '/usr/bin/php-config7.2', ], static fn (string $phpConfigPath) => file_exists($phpConfigPath) && is_executable($phpConfigPath), diff --git a/test/unit/Platform/TargetPhp/PhpBinaryPathTest.php b/test/unit/Platform/TargetPhp/PhpBinaryPathTest.php index 064139e4..b3efe714 100644 --- a/test/unit/Platform/TargetPhp/PhpBinaryPathTest.php +++ b/test/unit/Platform/TargetPhp/PhpBinaryPathTest.php @@ -57,6 +57,7 @@ final class PhpBinaryPathTest extends TestCase { private const FAKE_PHP_EXECUTABLE = __DIR__ . '/../../../assets/fake-php.sh'; + private const PHP_INVALID_VERSION = __DIR__ . '/../../../assets/fake-php-invalid-version.sh'; private const VALID_PHP_WITH_WARNINGS = __DIR__ . '/../../../assets/valid-php-with-warnings.sh'; public function testNonExistentPhpBinaryIsRejected(): void @@ -92,6 +93,13 @@ public function testInvalidPhpBinaryIsRejected(): void PhpBinaryPath::fromPhpBinaryPath(self::FAKE_PHP_EXECUTABLE); } + public function testInvalidVersion(): void + { + $phpBinary = PhpBinaryPath::fromPhpBinaryPath(self::PHP_INVALID_VERSION); + self::assertSame('5.6.40', $phpBinary->version()); + self::assertSame('5.6', $phpBinary->majorMinorVersion()); + } + public function testWarningsAndDeprecationsAreFiltered(): void { if (Platform::isWindows()) { @@ -129,11 +137,17 @@ public static function phpConfigPathProvider(): array $possiblePhpConfigPaths = array_filter( [ + ['/usr/bin/php-config8.5', '8.5'], + ['/usr/bin/php-config8.4', '8.4'], ['/usr/bin/php-config8.3', '8.3'], ['/usr/bin/php-config8.2', '8.2'], ['/usr/bin/php-config8.1', '8.1'], ['/usr/bin/php-config8.0', '8.0'], ['/usr/bin/php-config7.4', '7.4'], + ['/usr/bin/php-config7.3', '7.3'], + ['/usr/bin/php-config7.2', '7.2'], + ['/usr/bin/php-config7.1', '7.1'], + ['/usr/bin/php-config5.6', '5.6'], ], static fn (array $phpConfigPath) => file_exists($phpConfigPath[0]) && is_executable($phpConfigPath[0]), @@ -168,6 +182,11 @@ public function testFromPhpConfigExecutable(string $phpConfigPath, string $expec $phpBinary->majorMinorVersion(), ); + self::assertStringStartsWith( + $expectedMajorMinor . '.', + $phpBinary->version(), + ); + self::assertSame($phpConfigPath, $phpBinary->phpConfigPath()); } From 5940a6f6636ba0a04ee00c589d43cf45abb2dd79 Mon Sep 17 00:00:00 2001 From: James Titcumb Date: Mon, 19 Jan 2026 18:03:33 +0000 Subject: [PATCH 2/2] 446: ensure PHP binary tests are only run on Linux --- test/unit/Platform/TargetPhp/PhpBinaryPathTest.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/test/unit/Platform/TargetPhp/PhpBinaryPathTest.php b/test/unit/Platform/TargetPhp/PhpBinaryPathTest.php index b3efe714..80badbc2 100644 --- a/test/unit/Platform/TargetPhp/PhpBinaryPathTest.php +++ b/test/unit/Platform/TargetPhp/PhpBinaryPathTest.php @@ -86,6 +86,7 @@ public function testNonExecutablePhpBinaryIsRejected(): void PhpBinaryPath::fromPhpBinaryPath(__FILE__); } + #[RequiresOperatingSystemFamily('Linux')] public function testInvalidPhpBinaryIsRejected(): void { $this->expectException(InvalidPhpBinaryPath::class); @@ -93,6 +94,7 @@ public function testInvalidPhpBinaryIsRejected(): void PhpBinaryPath::fromPhpBinaryPath(self::FAKE_PHP_EXECUTABLE); } + #[RequiresOperatingSystemFamily('Linux')] public function testInvalidVersion(): void { $phpBinary = PhpBinaryPath::fromPhpBinaryPath(self::PHP_INVALID_VERSION);