diff --git a/src/Composer/Factory.php b/src/Composer/Factory.php index 22bae3667..e27976a4b 100644 --- a/src/Composer/Factory.php +++ b/src/Composer/Factory.php @@ -15,6 +15,7 @@ namespace Composer; use Composer\Json\JsonFile; use Composer\IO\IOInterface; use Composer\Repository\RepositoryManager; +use Composer\Util\ProcessExecutor; /** * Creates an configured instance of composer. @@ -67,6 +68,11 @@ class Factory } $binDir = getenv('COMPOSER_BIN_DIR') ?: $packageConfig['config']['bin-dir']; + // setup process timeout + if (false !== getenv('COMPOSER_PROCESS_TIMEOUT')) { + ProcessExecutor::setTimeout((int) getenv('COMPOSER_PROCESS_TIMEOUT')); + } + // initialize repository manager $rm = $this->createRepositoryManager($io); diff --git a/src/Composer/Util/ProcessExecutor.php b/src/Composer/Util/ProcessExecutor.php index e4c7ba811..fef4de96a 100644 --- a/src/Composer/Util/ProcessExecutor.php +++ b/src/Composer/Util/ProcessExecutor.php @@ -19,6 +19,8 @@ use Symfony\Component\Process\Process; */ class ProcessExecutor { + static protected $timeout = 60; + /** * runs a process on the commandline * @@ -29,7 +31,7 @@ class ProcessExecutor public function execute($command, &$output = null) { $captureOutput = count(func_get_args()) > 1; - $process = new Process($command); + $process = new Process($command, null, null, null, static::getTimeout()); $process->run(function($type, $buffer) use ($captureOutput) { if ($captureOutput) { return; @@ -49,4 +51,14 @@ class ProcessExecutor { return ((string) $output === '') ? array() : preg_split('{\r?\n}', $output); } -} \ No newline at end of file + + static public function getTimeout() + { + return static::$timeout; + } + + static public function setTimeout($timeout) + { + static::$timeout = $timeout; + } +} diff --git a/tests/Composer/Test/Util/ProcessExecutorTest.php b/tests/Composer/Test/Util/ProcessExecutorTest.php index c7445308d..0ec924bb4 100644 --- a/tests/Composer/Test/Util/ProcessExecutorTest.php +++ b/tests/Composer/Test/Util/ProcessExecutorTest.php @@ -33,6 +33,14 @@ class ProcessExecutorTest extends TestCase $this->assertEquals("foo".PHP_EOL, $output); } + public function testTimeout() + { + ProcessExecutor::setTimeout(1); + $process = new ProcessExecutor; + $this->assertEquals(1, $process->getTimeout()); + ProcessExecutor::setTimeout(60); + } + public function testSplitLines() { $process = new ProcessExecutor;