diff --git a/src/Symfony/Component/Console/Helper/QuestionHelper.php b/src/Symfony/Component/Console/Helper/QuestionHelper.php index 134f6231e52fe..be36f4356da89 100644 --- a/src/Symfony/Component/Console/Helper/QuestionHelper.php +++ b/src/Symfony/Component/Console/Helper/QuestionHelper.php @@ -509,14 +509,16 @@ private function getShell() private function isTty(): bool { - $inputStream = !$this->inputStream && \defined('STDIN') ? STDIN : $this->inputStream; + if (!\defined('STDIN')) { + return true; + } if (\function_exists('stream_isatty')) { - return stream_isatty($inputStream); + return stream_isatty(STDIN); } if (\function_exists('posix_isatty')) { - return posix_isatty($inputStream); + return posix_isatty(STDIN); } return true; diff --git a/src/Symfony/Component/Console/Tests/Helper/QuestionHelperTest.php b/src/Symfony/Component/Console/Tests/Helper/QuestionHelperTest.php index ddb0c90e19974..a6efa64a1f5c5 100644 --- a/src/Symfony/Component/Console/Tests/Helper/QuestionHelperTest.php +++ b/src/Symfony/Component/Console/Tests/Helper/QuestionHelperTest.php @@ -11,6 +11,7 @@ namespace Symfony\Component\Console\Tests\Helper; +use Symfony\Component\Console\Application; use Symfony\Component\Console\Exception\InvalidArgumentException; use Symfony\Component\Console\Formatter\OutputFormatter; use Symfony\Component\Console\Helper\FormatterHelper; @@ -21,6 +22,7 @@ use Symfony\Component\Console\Question\ConfirmationQuestion; use Symfony\Component\Console\Question\Question; use Symfony\Component\Console\Terminal; +use Symfony\Component\Console\Tester\ApplicationTester; /** * @group tty @@ -844,6 +846,38 @@ public function testTraversableMultiselectAutocomplete() $this->assertEquals(['AcmeDemoBundle', 'AsseticBundle'], $dialog->ask($this->createStreamableInputInterfaceMock($inputStream), $this->createOutputInterface(), $question)); } + public function testQuestionValidatorRepeatsThePrompt() + { + $tries = 0; + $application = new Application(); + $application->setAutoExit(false); + $application->register('question') + ->setCode(function ($input, $output) use (&$tries) { + $question = new Question('This is a promptable question'); + $question->setValidator(function ($value) use (&$tries) { + ++$tries; + if (!$value) { + throw new \Exception(); + } + + return $value; + }); + + (new QuestionHelper())->ask($input, $output, $question); + + return 0; + }) + ; + + $tester = new ApplicationTester($application); + $tester->setInputs(['', 'not-empty']); + + $statusCode = $tester->run(['command' => 'question'], ['interactive' => true]); + + $this->assertSame(2, $tries); + $this->assertSame($statusCode, 0); + } + protected function getInputStream($input) { $stream = fopen('php://memory', 'r+', false);