mirror of https://github.com/rectorphp/rector.git
Updated Rector to commit 91f9f3057c2d51018228ed89273a76da991d3f45
91f9f3057c
Use symfony/console ~6.3.9 to fix downgrade build (#5302)
This commit is contained in:
parent
f8dc5ef396
commit
35f86a2fad
|
@ -7,6 +7,8 @@ use PhpParser\Node;
|
|||
use PhpParser\Node\Expr;
|
||||
use PhpParser\Node\Expr\BinaryOp\BooleanAnd;
|
||||
use PhpParser\Node\Expr\Closure;
|
||||
use PhpParser\Node\Expr\ConstFetch;
|
||||
use PhpParser\Node\Scalar;
|
||||
use PhpParser\Node\Stmt;
|
||||
use PhpParser\Node\Stmt\Break_;
|
||||
use PhpParser\Node\Stmt\ClassMethod;
|
||||
|
@ -128,6 +130,9 @@ CODE_SAMPLE
|
|||
continue;
|
||||
}
|
||||
$nextStmt = $stmts[$key + 1] ?? null;
|
||||
if ($this->isComplexReturn($nextStmt)) {
|
||||
return null;
|
||||
}
|
||||
if ($this->shouldSkip($stmt, $nextStmt)) {
|
||||
$newStmts[] = $stmt;
|
||||
continue;
|
||||
|
@ -222,4 +227,17 @@ CODE_SAMPLE
|
|||
}
|
||||
return $nextStmt instanceof Return_;
|
||||
}
|
||||
private function isComplexReturn(?Stmt $stmt) : bool
|
||||
{
|
||||
if (!$stmt instanceof Return_) {
|
||||
return \false;
|
||||
}
|
||||
if (!$stmt->expr instanceof Expr) {
|
||||
return \false;
|
||||
}
|
||||
if ($stmt->expr instanceof ConstFetch) {
|
||||
return \false;
|
||||
}
|
||||
return !$stmt->expr instanceof Scalar;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -19,12 +19,12 @@ final class VersionResolver
|
|||
* @api
|
||||
* @var string
|
||||
*/
|
||||
public const PACKAGE_VERSION = '84bcfebdf7e9f522c8f9f9e97814c82d3d5d3315';
|
||||
public const PACKAGE_VERSION = '91f9f3057c2d51018228ed89273a76da991d3f45';
|
||||
/**
|
||||
* @api
|
||||
* @var string
|
||||
*/
|
||||
public const RELEASE_DATE = '2023-11-28 21:17:42';
|
||||
public const RELEASE_DATE = '2023-11-30 17:03:56';
|
||||
/**
|
||||
* @var int
|
||||
*/
|
||||
|
|
|
@ -22,4 +22,4 @@ if (PHP_VERSION_ID < 50600) {
|
|||
|
||||
require_once __DIR__ . '/composer/autoload_real.php';
|
||||
|
||||
return ComposerAutoloaderInita55c41c7fa52abd86138c6f32df1d185::getLoader();
|
||||
return ComposerAutoloaderInit6ee5b17c87a6bea7c9006b4ba8060b02::getLoader();
|
||||
|
|
|
@ -893,11 +893,16 @@ return array(
|
|||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\ProcessFailedException' => $vendorDir . '/symfony/process/Exception/ProcessFailedException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\ProcessSignaledException' => $vendorDir . '/symfony/process/Exception/ProcessSignaledException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\ProcessTimedOutException' => $vendorDir . '/symfony/process/Exception/ProcessTimedOutException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\RunProcessFailedException' => $vendorDir . '/symfony/process/Exception/RunProcessFailedException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\RuntimeException' => $vendorDir . '/symfony/process/Exception/RuntimeException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\ExecutableFinder' => $vendorDir . '/symfony/process/ExecutableFinder.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\InputStream' => $vendorDir . '/symfony/process/InputStream.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Messenger\\RunProcessContext' => $vendorDir . '/symfony/process/Messenger/RunProcessContext.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Messenger\\RunProcessMessage' => $vendorDir . '/symfony/process/Messenger/RunProcessMessage.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Messenger\\RunProcessMessageHandler' => $vendorDir . '/symfony/process/Messenger/RunProcessMessageHandler.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\PhpExecutableFinder' => $vendorDir . '/symfony/process/PhpExecutableFinder.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\PhpProcess' => $vendorDir . '/symfony/process/PhpProcess.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\PhpSubprocess' => $vendorDir . '/symfony/process/PhpSubprocess.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Pipes\\AbstractPipes' => $vendorDir . '/symfony/process/Pipes/AbstractPipes.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Pipes\\PipesInterface' => $vendorDir . '/symfony/process/Pipes/PipesInterface.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Pipes\\UnixPipes' => $vendorDir . '/symfony/process/Pipes/UnixPipes.php',
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
// autoload_real.php @generated by Composer
|
||||
|
||||
class ComposerAutoloaderInita55c41c7fa52abd86138c6f32df1d185
|
||||
class ComposerAutoloaderInit6ee5b17c87a6bea7c9006b4ba8060b02
|
||||
{
|
||||
private static $loader;
|
||||
|
||||
|
@ -22,17 +22,17 @@ class ComposerAutoloaderInita55c41c7fa52abd86138c6f32df1d185
|
|||
return self::$loader;
|
||||
}
|
||||
|
||||
spl_autoload_register(array('ComposerAutoloaderInita55c41c7fa52abd86138c6f32df1d185', 'loadClassLoader'), true, true);
|
||||
spl_autoload_register(array('ComposerAutoloaderInit6ee5b17c87a6bea7c9006b4ba8060b02', 'loadClassLoader'), true, true);
|
||||
self::$loader = $loader = new \Composer\Autoload\ClassLoader(\dirname(__DIR__));
|
||||
spl_autoload_unregister(array('ComposerAutoloaderInita55c41c7fa52abd86138c6f32df1d185', 'loadClassLoader'));
|
||||
spl_autoload_unregister(array('ComposerAutoloaderInit6ee5b17c87a6bea7c9006b4ba8060b02', 'loadClassLoader'));
|
||||
|
||||
require __DIR__ . '/autoload_static.php';
|
||||
call_user_func(\Composer\Autoload\ComposerStaticInita55c41c7fa52abd86138c6f32df1d185::getInitializer($loader));
|
||||
call_user_func(\Composer\Autoload\ComposerStaticInit6ee5b17c87a6bea7c9006b4ba8060b02::getInitializer($loader));
|
||||
|
||||
$loader->setClassMapAuthoritative(true);
|
||||
$loader->register(true);
|
||||
|
||||
$filesToLoad = \Composer\Autoload\ComposerStaticInita55c41c7fa52abd86138c6f32df1d185::$files;
|
||||
$filesToLoad = \Composer\Autoload\ComposerStaticInit6ee5b17c87a6bea7c9006b4ba8060b02::$files;
|
||||
$requireFile = \Closure::bind(static function ($fileIdentifier, $file) {
|
||||
if (empty($GLOBALS['__composer_autoload_files'][$fileIdentifier])) {
|
||||
$GLOBALS['__composer_autoload_files'][$fileIdentifier] = true;
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
|
||||
namespace Composer\Autoload;
|
||||
|
||||
class ComposerStaticInita55c41c7fa52abd86138c6f32df1d185
|
||||
class ComposerStaticInit6ee5b17c87a6bea7c9006b4ba8060b02
|
||||
{
|
||||
public static $files = array (
|
||||
'ad155f8f1cf0d418fe49e248db8c661b' => __DIR__ . '/..' . '/react/promise/src/functions_include.php',
|
||||
|
@ -1111,11 +1111,16 @@ class ComposerStaticInita55c41c7fa52abd86138c6f32df1d185
|
|||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\ProcessFailedException' => __DIR__ . '/..' . '/symfony/process/Exception/ProcessFailedException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\ProcessSignaledException' => __DIR__ . '/..' . '/symfony/process/Exception/ProcessSignaledException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\ProcessTimedOutException' => __DIR__ . '/..' . '/symfony/process/Exception/ProcessTimedOutException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\RunProcessFailedException' => __DIR__ . '/..' . '/symfony/process/Exception/RunProcessFailedException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Exception\\RuntimeException' => __DIR__ . '/..' . '/symfony/process/Exception/RuntimeException.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\ExecutableFinder' => __DIR__ . '/..' . '/symfony/process/ExecutableFinder.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\InputStream' => __DIR__ . '/..' . '/symfony/process/InputStream.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Messenger\\RunProcessContext' => __DIR__ . '/..' . '/symfony/process/Messenger/RunProcessContext.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Messenger\\RunProcessMessage' => __DIR__ . '/..' . '/symfony/process/Messenger/RunProcessMessage.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Messenger\\RunProcessMessageHandler' => __DIR__ . '/..' . '/symfony/process/Messenger/RunProcessMessageHandler.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\PhpExecutableFinder' => __DIR__ . '/..' . '/symfony/process/PhpExecutableFinder.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\PhpProcess' => __DIR__ . '/..' . '/symfony/process/PhpProcess.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\PhpSubprocess' => __DIR__ . '/..' . '/symfony/process/PhpSubprocess.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Pipes\\AbstractPipes' => __DIR__ . '/..' . '/symfony/process/Pipes/AbstractPipes.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Pipes\\PipesInterface' => __DIR__ . '/..' . '/symfony/process/Pipes/PipesInterface.php',
|
||||
'RectorPrefix202311\\Symfony\\Component\\Process\\Pipes\\UnixPipes' => __DIR__ . '/..' . '/symfony/process/Pipes/UnixPipes.php',
|
||||
|
@ -2601,9 +2606,9 @@ class ComposerStaticInita55c41c7fa52abd86138c6f32df1d185
|
|||
public static function getInitializer(ClassLoader $loader)
|
||||
{
|
||||
return \Closure::bind(function () use ($loader) {
|
||||
$loader->prefixLengthsPsr4 = ComposerStaticInita55c41c7fa52abd86138c6f32df1d185::$prefixLengthsPsr4;
|
||||
$loader->prefixDirsPsr4 = ComposerStaticInita55c41c7fa52abd86138c6f32df1d185::$prefixDirsPsr4;
|
||||
$loader->classMap = ComposerStaticInita55c41c7fa52abd86138c6f32df1d185::$classMap;
|
||||
$loader->prefixLengthsPsr4 = ComposerStaticInit6ee5b17c87a6bea7c9006b4ba8060b02::$prefixLengthsPsr4;
|
||||
$loader->prefixDirsPsr4 = ComposerStaticInit6ee5b17c87a6bea7c9006b4ba8060b02::$prefixDirsPsr4;
|
||||
$loader->classMap = ComposerStaticInit6ee5b17c87a6bea7c9006b4ba8060b02::$classMap;
|
||||
|
||||
}, null, ClassLoader::class);
|
||||
}
|
||||
|
|
|
@ -1228,17 +1228,17 @@
|
|||
},
|
||||
{
|
||||
"name": "react\/dns",
|
||||
"version": "v1.11.0",
|
||||
"version_normalized": "1.11.0.0",
|
||||
"version": "v1.12.0",
|
||||
"version_normalized": "1.12.0.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https:\/\/github.com\/reactphp\/dns.git",
|
||||
"reference": "3be0fc8f1eb37d6875cd6f0c6c7d0be81435de9f"
|
||||
"reference": "c134600642fa615b46b41237ef243daa65bb64ec"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https:\/\/api.github.com\/repos\/reactphp\/dns\/zipball\/3be0fc8f1eb37d6875cd6f0c6c7d0be81435de9f",
|
||||
"reference": "3be0fc8f1eb37d6875cd6f0c6c7d0be81435de9f",
|
||||
"url": "https:\/\/api.github.com\/repos\/reactphp\/dns\/zipball\/c134600642fa615b46b41237ef243daa65bb64ec",
|
||||
"reference": "c134600642fa615b46b41237ef243daa65bb64ec",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
|
@ -1248,11 +1248,11 @@
|
|||
"react\/promise": "^3.0 || ^2.7 || ^1.2.1"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit\/phpunit": "^9.5 || ^4.8.35",
|
||||
"phpunit\/phpunit": "^9.6 || ^5.7 || ^4.8.36",
|
||||
"react\/async": "^4 || ^3 || ^2",
|
||||
"react\/promise-timer": "^1.9"
|
||||
},
|
||||
"time": "2023-06-02T12:45:26+00:00",
|
||||
"time": "2023-11-29T12:41:06+00:00",
|
||||
"type": "library",
|
||||
"installation-source": "dist",
|
||||
"autoload": {
|
||||
|
@ -1295,7 +1295,7 @@
|
|||
],
|
||||
"support": {
|
||||
"issues": "https:\/\/github.com\/reactphp\/dns\/issues",
|
||||
"source": "https:\/\/github.com\/reactphp\/dns\/tree\/v1.11.0"
|
||||
"source": "https:\/\/github.com\/reactphp\/dns\/tree\/v1.12.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
|
@ -2015,17 +2015,17 @@
|
|||
},
|
||||
{
|
||||
"name": "symfony\/console",
|
||||
"version": "v6.3.8",
|
||||
"version_normalized": "6.3.8.0",
|
||||
"version": "v6.3.9",
|
||||
"version_normalized": "6.3.9.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https:\/\/github.com\/symfony\/console.git",
|
||||
"reference": "0d14a9f6d04d4ac38a8cea1171f4554e325dae92"
|
||||
"reference": "0566dbd051f8648d980592c7849f5d90d2c7c60c"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https:\/\/api.github.com\/repos\/symfony\/console\/zipball\/0d14a9f6d04d4ac38a8cea1171f4554e325dae92",
|
||||
"reference": "0d14a9f6d04d4ac38a8cea1171f4554e325dae92",
|
||||
"url": "https:\/\/api.github.com\/repos\/symfony\/console\/zipball\/0566dbd051f8648d980592c7849f5d90d2c7c60c",
|
||||
"reference": "0566dbd051f8648d980592c7849f5d90d2c7c60c",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
|
@ -2054,7 +2054,7 @@
|
|||
"symfony\/process": "^5.4|^6.0",
|
||||
"symfony\/var-dumper": "^5.4|^6.0"
|
||||
},
|
||||
"time": "2023-10-31T08:09:35+00:00",
|
||||
"time": "2023-11-20T16:36:29+00:00",
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"patches_applied": [
|
||||
|
@ -2093,7 +2093,7 @@
|
|||
"terminal"
|
||||
],
|
||||
"support": {
|
||||
"source": "https:\/\/github.com\/symfony\/console\/tree\/v6.3.8"
|
||||
"source": "https:\/\/github.com\/symfony\/console\/tree\/v6.3.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
|
@ -2113,17 +2113,17 @@
|
|||
},
|
||||
{
|
||||
"name": "symfony\/filesystem",
|
||||
"version": "v6.3.1",
|
||||
"version_normalized": "6.3.1.0",
|
||||
"version": "v6.4.0",
|
||||
"version_normalized": "6.4.0.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https:\/\/github.com\/symfony\/filesystem.git",
|
||||
"reference": "edd36776956f2a6fcf577edb5b05eb0e3bdc52ae"
|
||||
"reference": "952a8cb588c3bc6ce76f6023000fb932f16a6e59"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https:\/\/api.github.com\/repos\/symfony\/filesystem\/zipball\/edd36776956f2a6fcf577edb5b05eb0e3bdc52ae",
|
||||
"reference": "edd36776956f2a6fcf577edb5b05eb0e3bdc52ae",
|
||||
"url": "https:\/\/api.github.com\/repos\/symfony\/filesystem\/zipball\/952a8cb588c3bc6ce76f6023000fb932f16a6e59",
|
||||
"reference": "952a8cb588c3bc6ce76f6023000fb932f16a6e59",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
|
@ -2131,7 +2131,7 @@
|
|||
"symfony\/polyfill-ctype": "~1.8",
|
||||
"symfony\/polyfill-mbstring": "~1.8"
|
||||
},
|
||||
"time": "2023-06-01T08:30:39+00:00",
|
||||
"time": "2023-07-26T17:27:13+00:00",
|
||||
"type": "library",
|
||||
"installation-source": "dist",
|
||||
"autoload": {
|
||||
|
@ -2159,7 +2159,7 @@
|
|||
"description": "Provides basic utilities for the filesystem",
|
||||
"homepage": "https:\/\/symfony.com",
|
||||
"support": {
|
||||
"source": "https:\/\/github.com\/symfony\/filesystem\/tree\/v6.3.1"
|
||||
"source": "https:\/\/github.com\/symfony\/filesystem\/tree\/v6.4.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
|
@ -2179,26 +2179,26 @@
|
|||
},
|
||||
{
|
||||
"name": "symfony\/finder",
|
||||
"version": "v6.3.5",
|
||||
"version_normalized": "6.3.5.0",
|
||||
"version": "v6.4.0",
|
||||
"version_normalized": "6.4.0.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https:\/\/github.com\/symfony\/finder.git",
|
||||
"reference": "a1b31d88c0e998168ca7792f222cbecee47428c4"
|
||||
"reference": "11d736e97f116ac375a81f96e662911a34cd50ce"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https:\/\/api.github.com\/repos\/symfony\/finder\/zipball\/a1b31d88c0e998168ca7792f222cbecee47428c4",
|
||||
"reference": "a1b31d88c0e998168ca7792f222cbecee47428c4",
|
||||
"url": "https:\/\/api.github.com\/repos\/symfony\/finder\/zipball\/11d736e97f116ac375a81f96e662911a34cd50ce",
|
||||
"reference": "11d736e97f116ac375a81f96e662911a34cd50ce",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=8.1"
|
||||
},
|
||||
"require-dev": {
|
||||
"symfony\/filesystem": "^6.0"
|
||||
"symfony\/filesystem": "^6.0|^7.0"
|
||||
},
|
||||
"time": "2023-09-26T12:56:25+00:00",
|
||||
"time": "2023-10-31T17:30:12+00:00",
|
||||
"type": "library",
|
||||
"installation-source": "dist",
|
||||
"autoload": {
|
||||
|
@ -2226,7 +2226,7 @@
|
|||
"description": "Finds files and directories via an intuitive fluent interface",
|
||||
"homepage": "https:\/\/symfony.com",
|
||||
"support": {
|
||||
"source": "https:\/\/github.com\/symfony\/finder\/tree\/v6.3.5"
|
||||
"source": "https:\/\/github.com\/symfony\/finder\/tree\/v6.4.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
|
@ -2332,23 +2332,23 @@
|
|||
},
|
||||
{
|
||||
"name": "symfony\/process",
|
||||
"version": "v6.3.4",
|
||||
"version_normalized": "6.3.4.0",
|
||||
"version": "v6.4.0",
|
||||
"version_normalized": "6.4.0.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https:\/\/github.com\/symfony\/process.git",
|
||||
"reference": "0b5c29118f2e980d455d2e34a5659f4579847c54"
|
||||
"reference": "191703b1566d97a5425dc969e4350d32b8ef17aa"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https:\/\/api.github.com\/repos\/symfony\/process\/zipball\/0b5c29118f2e980d455d2e34a5659f4579847c54",
|
||||
"reference": "0b5c29118f2e980d455d2e34a5659f4579847c54",
|
||||
"url": "https:\/\/api.github.com\/repos\/symfony\/process\/zipball\/191703b1566d97a5425dc969e4350d32b8ef17aa",
|
||||
"reference": "191703b1566d97a5425dc969e4350d32b8ef17aa",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=8.1"
|
||||
},
|
||||
"time": "2023-08-07T10:39:22+00:00",
|
||||
"time": "2023-11-17T21:06:49+00:00",
|
||||
"type": "library",
|
||||
"installation-source": "dist",
|
||||
"autoload": {
|
||||
|
@ -2376,7 +2376,7 @@
|
|||
"description": "Executes commands in sub-processes",
|
||||
"homepage": "https:\/\/symfony.com",
|
||||
"support": {
|
||||
"source": "https:\/\/github.com\/symfony\/process\/tree\/v6.3.4"
|
||||
"source": "https:\/\/github.com\/symfony\/process\/tree\/v6.4.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
|
|
File diff suppressed because one or more lines are too long
|
@ -1,5 +1,13 @@
|
|||
# Changelog
|
||||
|
||||
## 1.12.0 (2023-11-29)
|
||||
|
||||
* Feature: Full PHP 8.3 compatibility.
|
||||
(#217 by @sergiy-petrov)
|
||||
|
||||
* Update test environment and avoid unhandled promise rejections.
|
||||
(#215, #216 and #218 by @clue)
|
||||
|
||||
## 1.11.0 (2023-06-02)
|
||||
|
||||
* Feature: Include timeout logic to avoid dependency on reactphp/promise-timer.
|
||||
|
|
|
@ -410,7 +410,7 @@ This project follows [SemVer](https://semver.org/).
|
|||
This will install the latest supported version:
|
||||
|
||||
```bash
|
||||
composer require react/dns:^1.11
|
||||
composer require react/dns:^1.12
|
||||
```
|
||||
|
||||
See also the [CHANGELOG](CHANGELOG.md) for details about version upgrades.
|
||||
|
|
|
@ -37,7 +37,7 @@
|
|||
"react\/promise": "^3.0 || ^2.7 || ^1.2.1"
|
||||
},
|
||||
"require-dev": {
|
||||
"phpunit\/phpunit": "^9.5 || ^4.8.35",
|
||||
"phpunit\/phpunit": "^9.6 || ^5.7 || ^4.8.36",
|
||||
"react\/async": "^4 || ^3 || ^2",
|
||||
"react\/promise-timer": "^1.9"
|
||||
},
|
||||
|
|
|
@ -20,6 +20,9 @@ use RectorPrefix202311\Symfony\Component\Filesystem\Exception\IOException;
|
|||
*/
|
||||
class Filesystem
|
||||
{
|
||||
/**
|
||||
* @var string|null
|
||||
*/
|
||||
private static $lastError;
|
||||
/**
|
||||
* Copies a file.
|
||||
|
@ -650,7 +653,7 @@ class Filesystem
|
|||
{
|
||||
self::assertFunctionExists($func);
|
||||
self::$lastError = null;
|
||||
\set_error_handler(__CLASS__ . '::handleError');
|
||||
\set_error_handler(\Closure::fromCallable([self::class, 'handleError']));
|
||||
try {
|
||||
return $func(...$args);
|
||||
} finally {
|
||||
|
|
|
@ -1,6 +1,11 @@
|
|||
CHANGELOG
|
||||
=========
|
||||
|
||||
6.4
|
||||
---
|
||||
|
||||
* Add early directory pruning to `Finder::filter()`
|
||||
|
||||
6.2
|
||||
---
|
||||
|
||||
|
|
|
@ -62,6 +62,10 @@ class Finder implements \IteratorAggregate, \Countable
|
|||
* @var mixed[]
|
||||
*/
|
||||
private $filters = [];
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $pruneFilters = [];
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
|
@ -582,13 +586,20 @@ class Finder implements \IteratorAggregate, \Countable
|
|||
* The anonymous function receives a \SplFileInfo and must return false
|
||||
* to remove files.
|
||||
*
|
||||
* @param \Closure(SplFileInfo): bool $closure
|
||||
* @param bool $prune Whether to skip traversing directories further
|
||||
*
|
||||
* @return $this
|
||||
*
|
||||
* @see CustomFilterIterator
|
||||
*/
|
||||
public function filter(\Closure $closure)
|
||||
{
|
||||
$prune = 1 < \func_num_args() ? \func_get_arg(1) : \false;
|
||||
$this->filters[] = $closure;
|
||||
if ($prune) {
|
||||
$this->pruneFilters[] = $closure;
|
||||
}
|
||||
return $this;
|
||||
}
|
||||
/**
|
||||
|
@ -721,6 +732,9 @@ class Finder implements \IteratorAggregate, \Countable
|
|||
{
|
||||
$exclude = $this->exclude;
|
||||
$notPaths = $this->notPaths;
|
||||
if ($this->pruneFilters) {
|
||||
$exclude = \array_merge($exclude, $this->pruneFilters);
|
||||
}
|
||||
if (static::IGNORE_VCS_FILES === (static::IGNORE_VCS_FILES & $this->ignore)) {
|
||||
$exclude = \array_merge($exclude, self::$vcsPatterns);
|
||||
}
|
||||
|
|
|
@ -28,17 +28,17 @@ class ExcludeDirectoryFilterIterator extends \FilterIterator implements \Recursi
|
|||
* @var bool
|
||||
*/
|
||||
private $isRecursive;
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
/** @var array<string, true> */
|
||||
private $excludedDirs = [];
|
||||
/**
|
||||
* @var string|null
|
||||
*/
|
||||
private $excludedPattern;
|
||||
/** @var list<callable(SplFileInfo):bool> */
|
||||
private $pruneFilters = [];
|
||||
/**
|
||||
* @param \Iterator<string, SplFileInfo> $iterator The Iterator to filter
|
||||
* @param string[] $directories An array of directories to exclude
|
||||
* @param \Iterator<string, SplFileInfo> $iterator The Iterator to filter
|
||||
* @param list<string|callable(SplFileInfo):bool> $directories An array of directories to exclude
|
||||
*/
|
||||
public function __construct(\Iterator $iterator, array $directories)
|
||||
{
|
||||
|
@ -46,6 +46,13 @@ class ExcludeDirectoryFilterIterator extends \FilterIterator implements \Recursi
|
|||
$this->isRecursive = $iterator instanceof \RecursiveIterator;
|
||||
$patterns = [];
|
||||
foreach ($directories as $directory) {
|
||||
if (!\is_string($directory)) {
|
||||
if (!\is_callable($directory)) {
|
||||
throw new \InvalidArgumentException('Invalid PHP callback.');
|
||||
}
|
||||
$this->pruneFilters[] = $directory;
|
||||
continue;
|
||||
}
|
||||
$directory = \rtrim($directory, '/');
|
||||
if (!$this->isRecursive || \strpos($directory, '/') !== \false) {
|
||||
$patterns[] = \preg_quote($directory, '#');
|
||||
|
@ -71,6 +78,13 @@ class ExcludeDirectoryFilterIterator extends \FilterIterator implements \Recursi
|
|||
$path = \str_replace('\\', '/', $path);
|
||||
return !\preg_match($this->excludedPattern, $path);
|
||||
}
|
||||
if ($this->pruneFilters && $this->hasChildren()) {
|
||||
foreach ($this->pruneFilters as $pruneFilter) {
|
||||
if (!$pruneFilter($this->current())) {
|
||||
return \false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return \true;
|
||||
}
|
||||
public function hasChildren() : bool
|
||||
|
|
|
@ -19,7 +19,7 @@
|
|||
"php": ">=8.1"
|
||||
},
|
||||
"require-dev": {
|
||||
"symfony\/filesystem": "^6.0"
|
||||
"symfony\/filesystem": "^6.0|^7.0"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
|
|
|
@ -1,6 +1,14 @@
|
|||
CHANGELOG
|
||||
=========
|
||||
|
||||
6.4
|
||||
---
|
||||
|
||||
* Add `PhpSubprocess` to handle PHP subprocesses that take over the
|
||||
configuration from their parent
|
||||
* Add `RunProcessMessage` and `RunProcessMessageHandler`
|
||||
* Support using `Process::findExecutable()` independently of `open_basedir`
|
||||
|
||||
5.2.0
|
||||
-----
|
||||
|
||||
|
|
|
@ -18,6 +18,9 @@ use RectorPrefix202311\Symfony\Component\Process\Process;
|
|||
*/
|
||||
class ProcessFailedException extends RuntimeException
|
||||
{
|
||||
/**
|
||||
* @var \Symfony\Component\Process\Process
|
||||
*/
|
||||
private $process;
|
||||
public function __construct(Process $process)
|
||||
{
|
||||
|
|
|
@ -18,6 +18,9 @@ use RectorPrefix202311\Symfony\Component\Process\Process;
|
|||
*/
|
||||
final class ProcessSignaledException extends RuntimeException
|
||||
{
|
||||
/**
|
||||
* @var \Symfony\Component\Process\Process
|
||||
*/
|
||||
private $process;
|
||||
public function __construct(Process $process)
|
||||
{
|
||||
|
|
|
@ -20,7 +20,13 @@ class ProcessTimedOutException extends RuntimeException
|
|||
{
|
||||
public const TYPE_GENERAL = 1;
|
||||
public const TYPE_IDLE = 2;
|
||||
/**
|
||||
* @var \Symfony\Component\Process\Process
|
||||
*/
|
||||
private $process;
|
||||
/**
|
||||
* @var int
|
||||
*/
|
||||
private $timeoutType;
|
||||
public function __construct(Process $process, int $timeoutType)
|
||||
{
|
||||
|
|
|
@ -0,0 +1,29 @@
|
|||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of the Symfony package.
|
||||
*
|
||||
* (c) Fabien Potencier <fabien@symfony.com>
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
namespace RectorPrefix202311\Symfony\Component\Process\Exception;
|
||||
|
||||
use RectorPrefix202311\Symfony\Component\Process\Messenger\RunProcessContext;
|
||||
/**
|
||||
* @author Kevin Bond <kevinbond@gmail.com>
|
||||
*/
|
||||
final class RunProcessFailedException extends RuntimeException
|
||||
{
|
||||
/**
|
||||
* @readonly
|
||||
* @var \Symfony\Component\Process\Messenger\RunProcessContext
|
||||
*/
|
||||
public $context;
|
||||
public function __construct(ProcessFailedException $exception, RunProcessContext $context)
|
||||
{
|
||||
$this->context = $context;
|
||||
parent::__construct($exception->getMessage(), $exception->getCode());
|
||||
}
|
||||
}
|
|
@ -18,6 +18,9 @@ namespace RectorPrefix202311\Symfony\Component\Process;
|
|||
*/
|
||||
class ExecutableFinder
|
||||
{
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $suffixes = ['.exe', '.bat', '.cmd', '.com'];
|
||||
/**
|
||||
* Replaces default suffixes of executable.
|
||||
|
@ -46,22 +49,7 @@ class ExecutableFinder
|
|||
*/
|
||||
public function find(string $name, string $default = null, array $extraDirs = []) : ?string
|
||||
{
|
||||
if (\ini_get('open_basedir')) {
|
||||
$searchPath = \array_merge(\explode(\PATH_SEPARATOR, \ini_get('open_basedir')), $extraDirs);
|
||||
$dirs = [];
|
||||
foreach ($searchPath as $path) {
|
||||
// Silencing against https://bugs.php.net/69240
|
||||
if (@\is_dir($path)) {
|
||||
$dirs[] = $path;
|
||||
} else {
|
||||
if (\basename($path) == $name && @\is_executable($path)) {
|
||||
return $path;
|
||||
}
|
||||
}
|
||||
}
|
||||
} else {
|
||||
$dirs = \array_merge(\explode(\PATH_SEPARATOR, \getenv('PATH') ?: \getenv('Path')), $extraDirs);
|
||||
}
|
||||
$dirs = \array_merge(\explode(\PATH_SEPARATOR, \getenv('PATH') ?: \getenv('Path')), $extraDirs);
|
||||
$suffixes = [''];
|
||||
if ('\\' === \DIRECTORY_SEPARATOR) {
|
||||
$pathExt = \getenv('PATHEXT');
|
||||
|
@ -72,8 +60,15 @@ class ExecutableFinder
|
|||
if (@\is_file($file = $dir . \DIRECTORY_SEPARATOR . $name . $suffix) && ('\\' === \DIRECTORY_SEPARATOR || @\is_executable($file))) {
|
||||
return $file;
|
||||
}
|
||||
if (!@\is_dir($dir) && \basename($dir) === $name . $suffix && @\is_executable($dir)) {
|
||||
return $dir;
|
||||
}
|
||||
}
|
||||
}
|
||||
$command = '\\' === \DIRECTORY_SEPARATOR ? 'where' : 'command -v';
|
||||
if (\function_exists('exec') && ($executablePath = \strtok(@\exec($command . ' ' . \escapeshellarg($name)), \PHP_EOL)) && \is_executable($executablePath)) {
|
||||
return $executablePath;
|
||||
}
|
||||
return $default;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -20,9 +20,17 @@ use RectorPrefix202311\Symfony\Component\Process\Exception\RuntimeException;
|
|||
*/
|
||||
class InputStream implements \IteratorAggregate
|
||||
{
|
||||
/** @var callable|null */
|
||||
/**
|
||||
* @var \Closure|null
|
||||
*/
|
||||
private $onEmpty;
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $input = [];
|
||||
/**
|
||||
* @var bool
|
||||
*/
|
||||
private $open = \true;
|
||||
/**
|
||||
* Sets a callback that is called when the write buffer becomes empty.
|
||||
|
@ -31,7 +39,7 @@ class InputStream implements \IteratorAggregate
|
|||
*/
|
||||
public function onEmpty(callable $onEmpty = null)
|
||||
{
|
||||
$this->onEmpty = $onEmpty;
|
||||
$this->onEmpty = null !== $onEmpty ? \Closure::fromCallable($onEmpty) : null;
|
||||
}
|
||||
/**
|
||||
* Appends an input to the write buffer.
|
||||
|
|
|
@ -0,0 +1,46 @@
|
|||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of the Symfony package.
|
||||
*
|
||||
* (c) Fabien Potencier <fabien@symfony.com>
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
namespace RectorPrefix202311\Symfony\Component\Process\Messenger;
|
||||
|
||||
use RectorPrefix202311\Symfony\Component\Process\Process;
|
||||
/**
|
||||
* @author Kevin Bond <kevinbond@gmail.com>
|
||||
*/
|
||||
final class RunProcessContext
|
||||
{
|
||||
/**
|
||||
* @readonly
|
||||
* @var \Symfony\Component\Process\Messenger\RunProcessMessage
|
||||
*/
|
||||
public $message;
|
||||
/**
|
||||
* @readonly
|
||||
* @var int|null
|
||||
*/
|
||||
public $exitCode;
|
||||
/**
|
||||
* @readonly
|
||||
* @var string|null
|
||||
*/
|
||||
public $output;
|
||||
/**
|
||||
* @readonly
|
||||
* @var string|null
|
||||
*/
|
||||
public $errorOutput;
|
||||
public function __construct(RunProcessMessage $message, Process $process)
|
||||
{
|
||||
$this->message = $message;
|
||||
$this->exitCode = $process->getExitCode();
|
||||
$this->output = $process->isOutputDisabled() ? null : $process->getOutput();
|
||||
$this->errorOutput = $process->isOutputDisabled() ? null : $process->getErrorOutput();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,58 @@
|
|||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of the Symfony package.
|
||||
*
|
||||
* (c) Fabien Potencier <fabien@symfony.com>
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
namespace RectorPrefix202311\Symfony\Component\Process\Messenger;
|
||||
|
||||
/**
|
||||
* @author Kevin Bond <kevinbond@gmail.com>
|
||||
*/
|
||||
class RunProcessMessage
|
||||
{
|
||||
/**
|
||||
* @readonly
|
||||
* @var mixed[]
|
||||
*/
|
||||
public $command;
|
||||
/**
|
||||
* @readonly
|
||||
* @var string|null
|
||||
*/
|
||||
public $cwd;
|
||||
/**
|
||||
* @readonly
|
||||
* @var mixed[]|null
|
||||
*/
|
||||
public $env;
|
||||
/**
|
||||
* @readonly
|
||||
* @var mixed
|
||||
*/
|
||||
public $input = null;
|
||||
/**
|
||||
* @readonly
|
||||
* @var float|null
|
||||
*/
|
||||
public $timeout = 60.0;
|
||||
/**
|
||||
* @param mixed $input
|
||||
*/
|
||||
public function __construct(array $command, ?string $cwd = null, ?array $env = null, $input = null, ?float $timeout = 60.0)
|
||||
{
|
||||
$this->command = $command;
|
||||
$this->cwd = $cwd;
|
||||
$this->env = $env;
|
||||
$this->input = $input;
|
||||
$this->timeout = $timeout;
|
||||
}
|
||||
public function __toString() : string
|
||||
{
|
||||
return \implode(' ', $this->command);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,30 @@
|
|||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of the Symfony package.
|
||||
*
|
||||
* (c) Fabien Potencier <fabien@symfony.com>
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
namespace RectorPrefix202311\Symfony\Component\Process\Messenger;
|
||||
|
||||
use RectorPrefix202311\Symfony\Component\Process\Exception\ProcessFailedException;
|
||||
use RectorPrefix202311\Symfony\Component\Process\Exception\RunProcessFailedException;
|
||||
use RectorPrefix202311\Symfony\Component\Process\Process;
|
||||
/**
|
||||
* @author Kevin Bond <kevinbond@gmail.com>
|
||||
*/
|
||||
final class RunProcessMessageHandler
|
||||
{
|
||||
public function __invoke(RunProcessMessage $message) : RunProcessContext
|
||||
{
|
||||
$process = new Process($message->command, $message->cwd, $message->env, $message->input, $message->timeout);
|
||||
try {
|
||||
return new RunProcessContext($message, $process->mustRun());
|
||||
} catch (ProcessFailedException $e) {
|
||||
throw new RunProcessFailedException($e, new RunProcessContext($message, $e->getProcess()));
|
||||
}
|
||||
}
|
||||
}
|
|
@ -18,6 +18,9 @@ namespace RectorPrefix202311\Symfony\Component\Process;
|
|||
*/
|
||||
class PhpExecutableFinder
|
||||
{
|
||||
/**
|
||||
* @var \Symfony\Component\Process\ExecutableFinder
|
||||
*/
|
||||
private $executableFinder;
|
||||
public function __construct()
|
||||
{
|
||||
|
@ -32,7 +35,7 @@ class PhpExecutableFinder
|
|||
if ($php = \getenv('PHP_BINARY')) {
|
||||
if (!\is_executable($php)) {
|
||||
$command = '\\' === \DIRECTORY_SEPARATOR ? 'where' : 'command -v';
|
||||
if ($php = \strtok(\exec($command . ' ' . \escapeshellarg($php)), \PHP_EOL)) {
|
||||
if (\function_exists('exec') && ($php = \strtok(\exec($command . ' ' . \escapeshellarg($php)), \PHP_EOL))) {
|
||||
if (!\is_executable($php)) {
|
||||
return \false;
|
||||
}
|
||||
|
|
|
@ -0,0 +1,140 @@
|
|||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of the Symfony package.
|
||||
*
|
||||
* (c) Fabien Potencier <fabien@symfony.com>
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
namespace RectorPrefix202311\Symfony\Component\Process;
|
||||
|
||||
use RectorPrefix202311\Symfony\Component\Process\Exception\LogicException;
|
||||
use RectorPrefix202311\Symfony\Component\Process\Exception\RuntimeException;
|
||||
/**
|
||||
* PhpSubprocess runs a PHP command as a subprocess while keeping the original php.ini settings.
|
||||
*
|
||||
* For this, it generates a temporary php.ini file taking over all the current settings and disables
|
||||
* loading additional .ini files. Basically, your command gets prefixed using "php -n -c /tmp/temp.ini".
|
||||
*
|
||||
* Given your php.ini contains "memory_limit=-1" and you have a "MemoryTest.php" with the following content:
|
||||
*
|
||||
* <?php var_dump(ini_get('memory_limit'));
|
||||
*
|
||||
* These are the differences between the regular Process and PhpSubprocess classes:
|
||||
*
|
||||
* $p = new Process(['php', '-d', 'memory_limit=256M', 'MemoryTest.php']);
|
||||
* $p->run();
|
||||
* print $p->getOutput()."\n";
|
||||
*
|
||||
* This will output "string(2) "-1", because the process is started with the default php.ini settings.
|
||||
*
|
||||
* $p = new PhpSubprocess(['MemoryTest.php'], null, null, 60, ['php', '-d', 'memory_limit=256M']);
|
||||
* $p->run();
|
||||
* print $p->getOutput()."\n";
|
||||
*
|
||||
* This will output "string(4) "256M"", because the process is started with the temporarily created php.ini settings.
|
||||
*
|
||||
* @author Yanick Witschi <yanick.witschi@terminal42.ch>
|
||||
* @author Partially copied and heavily inspired from composer/xdebug-handler by John Stevenson <john-stevenson@blueyonder.co.uk>
|
||||
*/
|
||||
class PhpSubprocess extends Process
|
||||
{
|
||||
/**
|
||||
* @param array $command The command to run and its arguments listed as separate entries. They will automatically
|
||||
* get prefixed with the PHP binary
|
||||
* @param string|null $cwd The working directory or null to use the working dir of the current PHP process
|
||||
* @param array|null $env The environment variables or null to use the same environment as the current PHP process
|
||||
* @param int $timeout The timeout in seconds
|
||||
* @param array|null $php Path to the PHP binary to use with any additional arguments
|
||||
*/
|
||||
public function __construct(array $command, string $cwd = null, array $env = null, int $timeout = 60, array $php = null)
|
||||
{
|
||||
if (null === $php) {
|
||||
$executableFinder = new PhpExecutableFinder();
|
||||
$php = $executableFinder->find(\false);
|
||||
$php = \false === $php ? null : \array_merge([$php], $executableFinder->findArguments());
|
||||
}
|
||||
if (null === $php) {
|
||||
throw new RuntimeException('Unable to find PHP binary.');
|
||||
}
|
||||
$tmpIni = $this->writeTmpIni($this->getAllIniFiles(), \sys_get_temp_dir());
|
||||
$php = \array_merge($php, ['-n', '-c', $tmpIni]);
|
||||
\register_shutdown_function('unlink', $tmpIni);
|
||||
$command = \array_merge($php, $command);
|
||||
parent::__construct($command, $cwd, $env, null, $timeout);
|
||||
}
|
||||
/**
|
||||
* @param mixed $input
|
||||
* @return static
|
||||
*/
|
||||
public static function fromShellCommandline(string $command, string $cwd = null, array $env = null, $input = null, ?float $timeout = 60)
|
||||
{
|
||||
throw new LogicException(\sprintf('The "%s()" method cannot be called when using "%s".', __METHOD__, self::class));
|
||||
}
|
||||
public function start(callable $callback = null, array $env = []) : void
|
||||
{
|
||||
if (null === $this->getCommandLine()) {
|
||||
throw new RuntimeException('Unable to find the PHP executable.');
|
||||
}
|
||||
parent::start($callback, $env);
|
||||
}
|
||||
private function writeTmpIni(array $iniFiles, string $tmpDir) : string
|
||||
{
|
||||
if (\false === ($tmpfile = @\tempnam($tmpDir, ''))) {
|
||||
throw new RuntimeException('Unable to create temporary ini file.');
|
||||
}
|
||||
// $iniFiles has at least one item and it may be empty
|
||||
if ('' === $iniFiles[0]) {
|
||||
\array_shift($iniFiles);
|
||||
}
|
||||
$content = '';
|
||||
foreach ($iniFiles as $file) {
|
||||
// Check for inaccessible ini files
|
||||
if (($data = @\file_get_contents($file)) === \false) {
|
||||
throw new RuntimeException('Unable to read ini: ' . $file);
|
||||
}
|
||||
// Check and remove directives after HOST and PATH sections
|
||||
if (\preg_match('/^\\s*\\[(?:PATH|HOST)\\s*=/mi', $data, $matches)) {
|
||||
$data = \substr($data, 0, $matches[0][1]);
|
||||
}
|
||||
$content .= $data . "\n";
|
||||
}
|
||||
// Merge loaded settings into our ini content, if it is valid
|
||||
$config = \parse_ini_string($content);
|
||||
$loaded = \ini_get_all(null, \false);
|
||||
if (\false === $config || \false === $loaded) {
|
||||
throw new RuntimeException('Unable to parse ini data.');
|
||||
}
|
||||
$content .= $this->mergeLoadedConfig($loaded, $config);
|
||||
// Work-around for https://bugs.php.net/bug.php?id=75932
|
||||
$content .= "opcache.enable_cli=0\n";
|
||||
if (\false === @\file_put_contents($tmpfile, $content)) {
|
||||
throw new RuntimeException('Unable to write temporary ini file.');
|
||||
}
|
||||
return $tmpfile;
|
||||
}
|
||||
private function mergeLoadedConfig(array $loadedConfig, array $iniConfig) : string
|
||||
{
|
||||
$content = '';
|
||||
foreach ($loadedConfig as $name => $value) {
|
||||
if (!\is_string($value)) {
|
||||
continue;
|
||||
}
|
||||
if (!isset($iniConfig[$name]) || $iniConfig[$name] !== $value) {
|
||||
// Double-quote escape each value
|
||||
$content .= $name . '="' . \addcslashes($value, '\\"') . "\"\n";
|
||||
}
|
||||
}
|
||||
return $content;
|
||||
}
|
||||
private function getAllIniFiles() : array
|
||||
{
|
||||
$paths = [(string) \php_ini_loaded_file()];
|
||||
if (\false !== ($scanned = \php_ini_scanned_files())) {
|
||||
$paths = \array_merge($paths, \array_map('trim', \explode(',', $scanned)));
|
||||
}
|
||||
return $paths;
|
||||
}
|
||||
}
|
|
@ -22,19 +22,27 @@ abstract class AbstractPipes implements PipesInterface
|
|||
* @var mixed[]
|
||||
*/
|
||||
public $pipes = [];
|
||||
/**
|
||||
* @var string
|
||||
*/
|
||||
private $inputBuffer = '';
|
||||
/** @var resource|string|\Iterator */
|
||||
private $input;
|
||||
/**
|
||||
* @var bool
|
||||
*/
|
||||
private $blocked = \true;
|
||||
/**
|
||||
* @var string|null
|
||||
*/
|
||||
private $lastError;
|
||||
/**
|
||||
* @param mixed $input
|
||||
* @param resource|string|\Iterator $input
|
||||
*/
|
||||
public function __construct($input)
|
||||
{
|
||||
if (\is_resource($input) || $input instanceof \Iterator) {
|
||||
$this->input = $input;
|
||||
} elseif (\is_string($input)) {
|
||||
$this->inputBuffer = $input;
|
||||
} else {
|
||||
$this->inputBuffer = (string) $input;
|
||||
}
|
||||
|
|
|
@ -20,8 +20,17 @@ use RectorPrefix202311\Symfony\Component\Process\Process;
|
|||
*/
|
||||
class UnixPipes extends AbstractPipes
|
||||
{
|
||||
/**
|
||||
* @var bool|null
|
||||
*/
|
||||
private $ttyMode;
|
||||
/**
|
||||
* @var bool
|
||||
*/
|
||||
private $ptyMode;
|
||||
/**
|
||||
* @var bool
|
||||
*/
|
||||
private $haveReadSupport;
|
||||
/**
|
||||
* @param mixed $input
|
||||
|
@ -37,7 +46,7 @@ class UnixPipes extends AbstractPipes
|
|||
{
|
||||
throw new \BadMethodCallException('Cannot serialize ' . __CLASS__);
|
||||
}
|
||||
public function __wakeup()
|
||||
public function __wakeup() : void
|
||||
{
|
||||
throw new \BadMethodCallException('Cannot unserialize ' . __CLASS__);
|
||||
}
|
||||
|
|
|
@ -24,10 +24,25 @@ use RectorPrefix202311\Symfony\Component\Process\Process;
|
|||
*/
|
||||
class WindowsPipes extends AbstractPipes
|
||||
{
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $files = [];
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $fileHandles = [];
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $lockHandles = [];
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $readBytes = [Process::STDOUT => 0, Process::STDERR => 0];
|
||||
/**
|
||||
* @var bool
|
||||
*/
|
||||
private $haveReadSupport;
|
||||
/**
|
||||
* @param mixed $input
|
||||
|
@ -83,7 +98,7 @@ class WindowsPipes extends AbstractPipes
|
|||
{
|
||||
throw new \BadMethodCallException('Cannot serialize ' . __CLASS__);
|
||||
}
|
||||
public function __wakeup()
|
||||
public function __wakeup() : void
|
||||
{
|
||||
throw new \BadMethodCallException('Cannot unserialize ' . __CLASS__);
|
||||
}
|
||||
|
|
|
@ -16,7 +16,6 @@ use RectorPrefix202311\Symfony\Component\Process\Exception\ProcessFailedExceptio
|
|||
use RectorPrefix202311\Symfony\Component\Process\Exception\ProcessSignaledException;
|
||||
use RectorPrefix202311\Symfony\Component\Process\Exception\ProcessTimedOutException;
|
||||
use RectorPrefix202311\Symfony\Component\Process\Exception\RuntimeException;
|
||||
use RectorPrefix202311\Symfony\Component\Process\Pipes\PipesInterface;
|
||||
use RectorPrefix202311\Symfony\Component\Process\Pipes\UnixPipes;
|
||||
use RectorPrefix202311\Symfony\Component\Process\Pipes\WindowsPipes;
|
||||
/**
|
||||
|
@ -48,33 +47,97 @@ class Process implements \IteratorAggregate
|
|||
// Use this flag to skip STDOUT while iterating
|
||||
public const ITER_SKIP_ERR = 8;
|
||||
// Use this flag to skip STDERR while iterating
|
||||
/**
|
||||
* @var \Closure|null
|
||||
*/
|
||||
private $callback;
|
||||
private $hasCallback = \false;
|
||||
/**
|
||||
* @var mixed[]|string
|
||||
*/
|
||||
private $commandline;
|
||||
/**
|
||||
* @var string|null
|
||||
*/
|
||||
private $cwd;
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $env = [];
|
||||
/** @var resource|string|\Iterator|null */
|
||||
private $input;
|
||||
/**
|
||||
* @var float|null
|
||||
*/
|
||||
private $starttime;
|
||||
/**
|
||||
* @var float|null
|
||||
*/
|
||||
private $lastOutputTime;
|
||||
/**
|
||||
* @var float|null
|
||||
*/
|
||||
private $timeout;
|
||||
/**
|
||||
* @var float|null
|
||||
*/
|
||||
private $idleTimeout;
|
||||
/**
|
||||
* @var int|null
|
||||
*/
|
||||
private $exitcode;
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $fallbackStatus = [];
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $processInformation;
|
||||
/**
|
||||
* @var bool
|
||||
*/
|
||||
private $outputDisabled = \false;
|
||||
/** @var resource */
|
||||
private $stdout;
|
||||
/** @var resource */
|
||||
private $stderr;
|
||||
/** @var resource|null */
|
||||
private $process;
|
||||
/**
|
||||
* @var string
|
||||
*/
|
||||
private $status = self::STATUS_READY;
|
||||
/**
|
||||
* @var int
|
||||
*/
|
||||
private $incrementalOutputOffset = 0;
|
||||
/**
|
||||
* @var int
|
||||
*/
|
||||
private $incrementalErrorOutputOffset = 0;
|
||||
/**
|
||||
* @var bool
|
||||
*/
|
||||
private $tty = \false;
|
||||
/**
|
||||
* @var bool
|
||||
*/
|
||||
private $pty;
|
||||
/**
|
||||
* @var mixed[]
|
||||
*/
|
||||
private $options = ['suppress_errors' => \true, 'bypass_shell' => \true];
|
||||
private $useFileHandles = \false;
|
||||
/** @var PipesInterface */
|
||||
/**
|
||||
* @var \Symfony\Component\Process\Pipes\WindowsPipes|\Symfony\Component\Process\Pipes\UnixPipes
|
||||
*/
|
||||
private $processPipes;
|
||||
/**
|
||||
* @var int|null
|
||||
*/
|
||||
private $latestSignal;
|
||||
/**
|
||||
* @var bool|null
|
||||
*/
|
||||
private static $sigchild;
|
||||
/**
|
||||
* Exit codes translation table.
|
||||
|
@ -149,7 +212,6 @@ class Process implements \IteratorAggregate
|
|||
}
|
||||
$this->setInput($input);
|
||||
$this->setTimeout($timeout);
|
||||
$this->useFileHandles = '\\' === \DIRECTORY_SEPARATOR;
|
||||
$this->pty = \false;
|
||||
}
|
||||
/**
|
||||
|
@ -184,6 +246,9 @@ class Process implements \IteratorAggregate
|
|||
{
|
||||
throw new \BadMethodCallException('Cannot serialize ' . __CLASS__);
|
||||
}
|
||||
/**
|
||||
* @return void
|
||||
*/
|
||||
public function __wakeup()
|
||||
{
|
||||
throw new \BadMethodCallException('Cannot unserialize ' . __CLASS__);
|
||||
|
@ -276,8 +341,7 @@ class Process implements \IteratorAggregate
|
|||
$this->resetProcessData();
|
||||
$this->starttime = $this->lastOutputTime = \microtime(\true);
|
||||
$this->callback = $this->buildCallback($callback);
|
||||
$this->hasCallback = null !== $callback;
|
||||
$descriptors = $this->getDescriptors();
|
||||
$descriptors = $this->getDescriptors(null !== $callback);
|
||||
if ($this->env) {
|
||||
$env += '\\' === \DIRECTORY_SEPARATOR ? \array_diff_ukey($this->env, $env, 'strcasecmp') : $this->env;
|
||||
}
|
||||
|
@ -293,15 +357,12 @@ class Process implements \IteratorAggregate
|
|||
}
|
||||
if ('\\' === \DIRECTORY_SEPARATOR) {
|
||||
$commandline = $this->prepareWindowsCommandLine($commandline, $env);
|
||||
} elseif (!$this->useFileHandles && $this->isSigchildEnabled()) {
|
||||
} elseif ($this->isSigchildEnabled()) {
|
||||
// last exit code is output on the fourth pipe and caught to work around --enable-sigchild
|
||||
$descriptors[3] = ['pipe', 'w'];
|
||||
// See https://unix.stackexchange.com/questions/71205/background-process-pipe-input
|
||||
$commandline = '{ (' . $commandline . ') <&3 3<&- 3>/dev/null & } 3<&0;';
|
||||
$commandline .= 'pid=$!; echo $pid >&3; wait $pid 2>/dev/null; code=$?; echo $code >&3; exit $code';
|
||||
// Workaround for the bug, when PTS functionality is enabled.
|
||||
// @see : https://bugs.php.net/69442
|
||||
$ptsWorkaround = \fopen(__FILE__, 'r');
|
||||
}
|
||||
$envPairs = [];
|
||||
foreach ($env as $k => $v) {
|
||||
|
@ -312,10 +373,11 @@ class Process implements \IteratorAggregate
|
|||
if (!\is_dir($this->cwd)) {
|
||||
throw new RuntimeException(\sprintf('The provided cwd "%s" does not exist.', $this->cwd));
|
||||
}
|
||||
$this->process = @\proc_open($commandline, $descriptors, $this->processPipes->pipes, $this->cwd, $envPairs, $this->options);
|
||||
if (!\is_resource($this->process)) {
|
||||
$process = @\proc_open($commandline, $descriptors, $this->processPipes->pipes, $this->cwd, $envPairs, $this->options);
|
||||
if (!\is_resource($process)) {
|
||||
throw new RuntimeException('Unable to launch a new process.');
|
||||
}
|
||||
$this->process = $process;
|
||||
$this->status = self::STATUS_STARTED;
|
||||
if (isset($descriptors[3])) {
|
||||
$this->fallbackStatus['pid'] = (int) \fgets($this->processPipes->pipes[3]);
|
||||
|
@ -1070,15 +1132,15 @@ class Process implements \IteratorAggregate
|
|||
/**
|
||||
* Creates the descriptors needed by the proc_open.
|
||||
*/
|
||||
private function getDescriptors() : array
|
||||
private function getDescriptors(bool $hasCallback) : array
|
||||
{
|
||||
if ($this->input instanceof \Iterator) {
|
||||
$this->input->rewind();
|
||||
}
|
||||
if ('\\' === \DIRECTORY_SEPARATOR) {
|
||||
$this->processPipes = new WindowsPipes($this->input, !$this->outputDisabled || $this->hasCallback);
|
||||
$this->processPipes = new WindowsPipes($this->input, !$this->outputDisabled || $hasCallback);
|
||||
} else {
|
||||
$this->processPipes = new UnixPipes($this->isTty(), $this->isPty(), $this->input, !$this->outputDisabled || $this->hasCallback);
|
||||
$this->processPipes = new UnixPipes($this->isTty(), $this->isPty(), $this->input, !$this->outputDisabled || $hasCallback);
|
||||
}
|
||||
return $this->processPipes->getDescriptors();
|
||||
}
|
||||
|
@ -1230,7 +1292,7 @@ class Process implements \IteratorAggregate
|
|||
$this->callback = null;
|
||||
$this->exitcode = null;
|
||||
$this->fallbackStatus = [];
|
||||
$this->processInformation = null;
|
||||
$this->processInformation = [];
|
||||
$this->stdout = \fopen('php://temp/maxmemory:' . 1024 * 1024, 'w+');
|
||||
$this->stderr = \fopen('php://temp/maxmemory:' . 1024 * 1024, 'w+');
|
||||
$this->process = null;
|
||||
|
|
|
@ -41,9 +41,6 @@ class ProcessUtils
|
|||
if (\is_resource($input)) {
|
||||
return $input;
|
||||
}
|
||||
if (\is_string($input)) {
|
||||
return $input;
|
||||
}
|
||||
if (\is_scalar($input)) {
|
||||
return (string) $input;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue