Skip to content

Commit 3c8263a

Browse files
[Console] Fix dispatching throwables from ConsoleEvents::COMMAND
1 parent 5742958 commit 3c8263a

File tree

2 files changed

+59
-38
lines changed

2 files changed

+59
-38
lines changed

src/Symfony/Component/Console/Application.php

+32-30
Original file line numberDiff line numberDiff line change
@@ -117,10 +117,17 @@ public function run(InputInterface $input = null, OutputInterface $output = null
117117
$this->configureIO($input, $output);
118118

119119
try {
120+
$e = null;
120121
$exitCode = $this->doRun($input, $output);
121-
} catch (\Exception $e) {
122+
} catch (\Exception $x) {
123+
$e = $x;
124+
} catch (\Throwable $x) {
125+
$e = new FatalThrowableError($x);
126+
}
127+
128+
if (null !== $e) {
122129
if (!$this->catchExceptions) {
123-
throw $e;
130+
throw $x;
124131
}
125132

126133
if ($output instanceof ConsoleOutputInterface) {
@@ -839,47 +846,42 @@ protected function doRunCommand(Command $command, InputInterface $input, OutputI
839846
}
840847

841848
if (null === $this->dispatcher) {
842-
try {
843-
return $command->run($input, $output);
844-
} catch (\Exception $e) {
845-
throw $e;
846-
} catch (\Throwable $e) {
847-
throw new FatalThrowableError($e);
848-
}
849+
return $command->run($input, $output);
849850
}
850851

851852
$event = new ConsoleCommandEvent($command, $input, $output);
852-
$this->dispatcher->dispatch(ConsoleEvents::COMMAND, $event);
853+
$e = null;
853854

854-
if ($event->commandShouldRun()) {
855-
try {
856-
$e = null;
855+
try {
856+
$this->dispatcher->dispatch(ConsoleEvents::COMMAND, $event);
857+
858+
if ($event->commandShouldRun()) {
857859
$exitCode = $command->run($input, $output);
858-
} catch (\Exception $x) {
859-
$e = $x;
860-
} catch (\Throwable $x) {
861-
$e = new FatalThrowableError($x);
860+
} else {
861+
$exitCode = ConsoleCommandEvent::RETURN_CODE_DISABLED;
862862
}
863-
if (null !== $e) {
864-
$event = new ConsoleExceptionEvent($command, $input, $output, $e, $e->getCode());
865-
$this->dispatcher->dispatch(ConsoleEvents::EXCEPTION, $event);
866-
867-
if ($e !== $event->getException()) {
868-
$x = $e = $event->getException();
869-
}
870-
871-
$event = new ConsoleTerminateEvent($command, $input, $output, $e->getCode());
872-
$this->dispatcher->dispatch(ConsoleEvents::TERMINATE, $event);
863+
} catch (\Exception $x) {
864+
$e = $x;
865+
} catch (\Throwable $x) {
866+
$e = new FatalThrowableError($x);
867+
}
868+
if (null !== $e) {
869+
$event = new ConsoleExceptionEvent($command, $input, $output, $e, $e->getCode());
870+
$this->dispatcher->dispatch(ConsoleEvents::EXCEPTION, $event);
873871

874-
throw $x;
872+
if ($e !== $event->getException()) {
873+
$x = $e = $event->getException();
875874
}
876-
} else {
877-
$exitCode = ConsoleCommandEvent::RETURN_CODE_DISABLED;
875+
$exitCode = $e->getCode();
878876
}
879877

880878
$event = new ConsoleTerminateEvent($command, $input, $output, $exitCode);
881879
$this->dispatcher->dispatch(ConsoleEvents::TERMINATE, $event);
882880

881+
if (null !== $e) {
882+
throw $x;
883+
}
884+
883885
return $event->getExitCode();
884886
}
885887

src/Symfony/Component/Console/Tests/ApplicationTest.php

+27-8
Original file line numberDiff line numberDiff line change
@@ -977,15 +977,28 @@ public function testRunDispatchesAllEventsWithException()
977977
$this->assertContains('before.foo.caught.after.', $tester->getDisplay());
978978
}
979979

980-
public function testRunWithError()
980+
public function testRunDispatchesAllEventsWithExceptionInListener()
981981
{
982-
if (method_exists($this, 'expectException')) {
983-
$this->expectException('Exception');
984-
$this->expectExceptionMessage('dymerr');
985-
} else {
986-
$this->setExpectedException('Exception', 'dymerr');
987-
}
982+
$dispatcher = $this->getDispatcher();
983+
$dispatcher->addListener('console.command', function () {
984+
throw new \RuntimeException('foo');
985+
});
986+
987+
$application = new Application();
988+
$application->setDispatcher($dispatcher);
989+
$application->setAutoExit(false);
990+
991+
$application->register('foo')->setCode(function (InputInterface $input, OutputInterface $output) {
992+
$output->write('foo.');
993+
});
994+
995+
$tester = new ApplicationTester($application);
996+
$tester->run(array('command' => 'foo'));
997+
$this->assertContains('before.caught.after.', $tester->getDisplay());
998+
}
988999

1000+
public function testRunWithError()
1001+
{
9891002
$application = new Application();
9901003
$application->setAutoExit(false);
9911004
$application->setCatchExceptions(false);
@@ -997,7 +1010,13 @@ public function testRunWithError()
9971010
});
9981011

9991012
$tester = new ApplicationTester($application);
1000-
$tester->run(array('command' => 'dym'));
1013+
1014+
try {
1015+
$tester->run(array('command' => 'dym'));
1016+
$this->fail('Error expected.');
1017+
} catch (\Error $e) {
1018+
$this->assertSame('dymerr', $e->getMessage());
1019+
}
10011020
}
10021021

10031022
/**

0 commit comments

Comments
 (0)