From 3b1984f9c9ce25fd7db69397ec071bb21789e44a Mon Sep 17 00:00:00 2001 From: Martin Kluska Date: Fri, 9 Dec 2022 15:48:48 +0100 Subject: [PATCH] feat(Testing): Add Bus dispatcher assert / expectation --- .../Contracts/Bus/DispatcherAssert.php | 161 ++++++++++++++++++ .../Bus/DispatcherDispatchExpectation.php | 14 ++ .../Bus/DispatcherDispatchNowExpectation.php | 15 ++ .../Bus/DispatcherDispatchSyncExpectation.php | 15 ++ ...DispatcherGetCommandHandlerExpectation.php | 14 ++ ...DispatcherHasCommandHandlerExpectation.php | 14 ++ .../Bus/DispatcherMapExpectation.php | 13 ++ .../Bus/DispatcherPipeThroughExpectation.php | 13 ++ .../Contracts/Bus/DispatcherAssertTest.php | 151 ++++++++++++++++ .../Testing/Laravel/Contracts/Bus/TestJob.php | 9 + 10 files changed, 419 insertions(+) create mode 100644 src/Testing/Laravel/Contracts/Bus/DispatcherAssert.php create mode 100644 src/Testing/Laravel/Contracts/Bus/DispatcherDispatchExpectation.php create mode 100644 src/Testing/Laravel/Contracts/Bus/DispatcherDispatchNowExpectation.php create mode 100644 src/Testing/Laravel/Contracts/Bus/DispatcherDispatchSyncExpectation.php create mode 100644 src/Testing/Laravel/Contracts/Bus/DispatcherGetCommandHandlerExpectation.php create mode 100644 src/Testing/Laravel/Contracts/Bus/DispatcherHasCommandHandlerExpectation.php create mode 100644 src/Testing/Laravel/Contracts/Bus/DispatcherMapExpectation.php create mode 100644 src/Testing/Laravel/Contracts/Bus/DispatcherPipeThroughExpectation.php create mode 100644 tests/Feature/Testing/Laravel/Contracts/Bus/DispatcherAssertTest.php create mode 100644 tests/Feature/Testing/Laravel/Contracts/Bus/TestJob.php diff --git a/src/Testing/Laravel/Contracts/Bus/DispatcherAssert.php b/src/Testing/Laravel/Contracts/Bus/DispatcherAssert.php new file mode 100644 index 00000000..2ce8e866 --- /dev/null +++ b/src/Testing/Laravel/Contracts/Bus/DispatcherAssert.php @@ -0,0 +1,161 @@ + $dispatch + * @param array $dispatchSync + * @param array $dispatchNow + * @param array $hasCommandHandler + * @param array $getCommandHandler + * @param array $pipeThrough + * @param array $map + */ + public function __construct( + array $dispatch = [], + array $dispatchSync = [], + array $dispatchNow = [], + array $hasCommandHandler = [], + array $getCommandHandler = [], + array $pipeThrough = [], + array $map = [], + ) { + $this->setExpectations(DispatcherDispatchExpectation::class, array_values(array_filter($dispatch))); + $this->setExpectations(DispatcherDispatchSyncExpectation::class, array_values(array_filter($dispatchSync))); + $this->setExpectations(DispatcherDispatchNowExpectation::class, array_values(array_filter($dispatchNow))); + $this->setExpectations( + DispatcherHasCommandHandlerExpectation::class, + array_values(array_filter($hasCommandHandler)) + ); + $this->setExpectations( + DispatcherGetCommandHandlerExpectation::class, + array_values(array_filter($getCommandHandler)) + ); + $this->setExpectations(DispatcherPipeThroughExpectation::class, array_values(array_filter($pipeThrough))); + $this->setExpectations(DispatcherMapExpectation::class, array_values(array_filter($map))); + } + + /** + * Dispatch a command to its appropriate handler. + * + * @param mixed $command + * @return mixed + */ + public function dispatch($command) + { + $expectation = $this->getExpectation(DispatcherDispatchExpectation::class); + $message = $this->getDebugMessage(); + + Assert::assertEquals($expectation->command, $command, $message); + + return $expectation->return; + } + + /** + * Dispatch a command to its appropriate handler in the current process. + * + * Queueable jobs will be dispatched to the "sync" queue. + * + * @param mixed $command + * @param mixed $handler + * @return mixed + */ + public function dispatchSync($command, $handler = null) + { + $expectation = $this->getExpectation(DispatcherDispatchSyncExpectation::class); + $message = $this->getDebugMessage(); + + Assert::assertEquals($expectation->command, $command, $message); + Assert::assertEquals($expectation->handler, $handler, $message); + + return $expectation->return; + } + + /** + * Dispatch a command to its appropriate handler in the current process. + * + * @param mixed $command + * @param mixed $handler + * @return mixed + */ + public function dispatchNow($command, $handler = null) + { + $expectation = $this->getExpectation(DispatcherDispatchNowExpectation::class); + $message = $this->getDebugMessage(); + + Assert::assertEquals($expectation->command, $command, $message); + Assert::assertEquals($expectation->handler, $handler, $message); + + return $expectation->return; + } + + /** + * Determine if the given command has a handler. + * + * @param mixed $command + * @return bool + */ + public function hasCommandHandler($command) + { + $expectation = $this->getExpectation(DispatcherHasCommandHandlerExpectation::class); + $message = $this->getDebugMessage(); + + Assert::assertEquals($expectation->command, $command, $message); + + return $expectation->return; + } + + /** + * Retrieve the handler for a command. + * + * @param mixed $command + * @return bool|mixed + */ + public function getCommandHandler($command) + { + $expectation = $this->getExpectation(DispatcherGetCommandHandlerExpectation::class); + $message = $this->getDebugMessage(); + + Assert::assertEquals($expectation->command, $command, $message); + + return $expectation->return; + } + + /** + * Set the pipes commands should be piped through before dispatching. + * + * @return $this + */ + public function pipeThrough(array $pipes) + { + $expectation = $this->getExpectation(DispatcherPipeThroughExpectation::class); + $message = $this->getDebugMessage(); + + Assert::assertEquals($expectation->pipes, $pipes, $message); + + return $this; + } + + /** + * Map a command to a handler. + * + * @return $this + */ + public function map(array $map) + { + $expectation = $this->getExpectation(DispatcherMapExpectation::class); + $message = $this->getDebugMessage(); + + Assert::assertEquals($expectation->map, $map, $message); + + return $this; + } +} diff --git a/src/Testing/Laravel/Contracts/Bus/DispatcherDispatchExpectation.php b/src/Testing/Laravel/Contracts/Bus/DispatcherDispatchExpectation.php new file mode 100644 index 00000000..849480a4 --- /dev/null +++ b/src/Testing/Laravel/Contracts/Bus/DispatcherDispatchExpectation.php @@ -0,0 +1,14 @@ + new DispatcherAssert( + dispatch: [new DispatcherDispatchExpectation(return: [], command: $testJob)] + ), + call: static fn (DispatcherAssert $assert) => $assert->dispatch(command: $testJob), + checkResult: true, + expectedResult: [] + ), + new AssertExpectationEntity( + methodName: 'dispatch', + createAssert: static fn () => new DispatcherAssert( + dispatch: [new DispatcherDispatchExpectation(return: null, command: $testJob)] + ), + call: static fn (DispatcherAssert $assert) => $assert->dispatch(command: $testJob), + checkResult: true, + expectedResult: null + ), + new AssertExpectationEntity( + methodName: 'dispatchSync', + createAssert: static fn () => new DispatcherAssert( + dispatchSync: [new DispatcherDispatchSyncExpectation(return: [], command: $testJob)] + ), + call: static fn (DispatcherAssert $assert) => $assert->dispatchSync(command: $testJob), + checkResult: true, + expectedResult: [] + ), + new AssertExpectationEntity( + methodName: 'dispatchSync', + createAssert: static fn () => new DispatcherAssert( + dispatchSync: [new DispatcherDispatchSyncExpectation(return: null, command: $testJob)] + ), + call: static fn (DispatcherAssert $assert) => $assert->dispatchSync(command: $testJob), + checkResult: true, + expectedResult: null + ), + new AssertExpectationEntity( + methodName: 'dispatchNow', + createAssert: static fn () => new DispatcherAssert( + dispatchNow: [new DispatcherDispatchNowExpectation(return: [], command: $testJob)] + ), + call: static fn (DispatcherAssert $assert) => $assert->dispatchNow(command: $testJob), + checkResult: true, + expectedResult: [] + ), + new AssertExpectationEntity( + methodName: 'dispatchNow', + createAssert: static fn () => new DispatcherAssert( + dispatchNow: [new DispatcherDispatchNowExpectation(return: null, command: $testJob)] + ), + call: static fn (DispatcherAssert $assert) => $assert->dispatchNow(command: $testJob), + checkResult: true, + expectedResult: null + ), + new AssertExpectationEntity( + methodName: 'hasCommandHandler', + createAssert: static fn () => new DispatcherAssert( + hasCommandHandler: [ + new DispatcherHasCommandHandlerExpectation(return: true, command: $testJob), + ] + ), + call: static fn (DispatcherAssert $assert) => $assert->hasCommandHandler(command: $testJob), + checkResult: true, + expectedResult: true + ), + new AssertExpectationEntity( + methodName: 'hasCommandHandler', + createAssert: static fn () => new DispatcherAssert( + hasCommandHandler: [ + new DispatcherHasCommandHandlerExpectation(return: false, command: $testJob), + ] + ), + call: static fn (DispatcherAssert $assert) => $assert->hasCommandHandler(command: $testJob), + checkResult: true, + expectedResult: false + ), + new AssertExpectationEntity( + methodName: 'getCommandHandler', + createAssert: static fn () => new DispatcherAssert( + getCommandHandler: [ + new DispatcherGetCommandHandlerExpectation(return: $testJob, command: $testJob), + ] + ), + call: static fn (DispatcherAssert $assert) => $assert->getCommandHandler(command: $testJob), + checkResult: true, + expectedResult: $testJob + ), + new AssertExpectationEntity( + methodName: 'getCommandHandler', + createAssert: static fn () => new DispatcherAssert( + getCommandHandler: [ + new DispatcherGetCommandHandlerExpectation(return: false, command: $testJob), + ] + ), + call: static fn (DispatcherAssert $assert) => $assert->getCommandHandler(command: $testJob), + checkResult: true, + expectedResult: false + ), + new AssertExpectationEntity( + methodName: 'pipeThrough', + createAssert: static fn () => new DispatcherAssert( + pipeThrough: [new DispatcherPipeThroughExpectation(pipes: [TestJob::class])] + ), + call: static fn (DispatcherAssert $assert) => $assert->pipeThrough(pipes: [TestJob::class]), + checkResult: true, + checkResultIsSelf: true + ), + new AssertExpectationEntity( + methodName: 'map', + createAssert: static fn () => new DispatcherAssert( + map: [new DispatcherMapExpectation(map: [TestJob::class])] + ), + call: static fn (DispatcherAssert $assert) => $assert->map(map: [TestJob::class]), + checkResult: true, + checkResultIsSelf: true + ), + ]; + } + + protected function createEmptyAssert(): AbstractExpectationCallsMap + { + return new DispatcherAssert(); + } +} diff --git a/tests/Feature/Testing/Laravel/Contracts/Bus/TestJob.php b/tests/Feature/Testing/Laravel/Contracts/Bus/TestJob.php new file mode 100644 index 00000000..0753a9cd --- /dev/null +++ b/tests/Feature/Testing/Laravel/Contracts/Bus/TestJob.php @@ -0,0 +1,9 @@ +