From e97025b9a5f8193cc0616a6372a9aa898fab4a7a Mon Sep 17 00:00:00 2001 From: Matthew Weier O'Phinney Date: Fri, 9 Mar 2018 09:17:17 -0600 Subject: [PATCH] Additional changes to work with zend-expressive-router 2.4 - Updates the ApplicationConfigInjectionTrait to use `prepareMiddleware()` before calling `route()`; this ensures that `Route` instances only ever receive middleware instances. - Provides changes to tests to ensure they work with the 2.4 version of the router. Primarily this means mocking the `MiddlewareInterface` when providing middleware to pipe or route against when we are not testing for that particular middleware. Additionally, it modifies the "assertRoute" expectations to simply ensure we _have_ middleware, but not the type; decorators are often in play, even in the existing 2.X series. --- src/ApplicationConfigInjectionTrait.php | 9 ++++++- test/Application/ConfigInjectionTest.php | 8 +++--- test/Container/ApplicationFactoryTest.php | 18 +++++++------ test/Middleware/DispatchMiddlewareTest.php | 31 +++++++++++++++------- 4 files changed, 44 insertions(+), 22 deletions(-) diff --git a/src/ApplicationConfigInjectionTrait.php b/src/ApplicationConfigInjectionTrait.php index 026e11de..8dc667ca 100644 --- a/src/ApplicationConfigInjectionTrait.php +++ b/src/ApplicationConfigInjectionTrait.php @@ -163,7 +163,14 @@ public function injectRoutesFromConfig(array $config = null) } $name = isset($spec['name']) ? $spec['name'] : null; - $route = $this->route($spec['path'], $spec['middleware'], $methods, $name); + $middleware = $this->prepareMiddleware( + $spec['middleware'], + $this->router, + $this->responsePrototype, + $this->container + ); + + $route = $this->route($spec['path'], $middleware, $methods, $name); if (isset($spec['options'])) { $options = $spec['options']; diff --git a/test/Application/ConfigInjectionTest.php b/test/Application/ConfigInjectionTest.php index dffcc25e..f02486e9 100644 --- a/test/Application/ConfigInjectionTest.php +++ b/test/Application/ConfigInjectionTest.php @@ -7,6 +7,7 @@ namespace ZendTest\Expressive\Application; +use Interop\Http\ServerMiddleware\MiddlewareInterface; use PHPUnit\Framework\Assert; use PHPUnit\Framework\TestCase; use Prophecy\Prophecy\ObjectProphecy; @@ -58,7 +59,7 @@ public static function assertRoute($spec, array $routes) return false; } - if ($route->getMiddleware() !== $spec['middleware']) { + if (! $route->getMiddleware()) { return false; } @@ -99,7 +100,7 @@ public static function assertPipelineContainsInstanceOf($class, $pipeline, $mess public function callableMiddlewares() { return [ - ['HelloWorld'], + [InvokableMiddleware::class], [ function () { }, @@ -115,6 +116,7 @@ function () { */ public function testInjectRoutesFromConfigSetsUpRoutesFromConfig($middleware) { + $pingMiddleware = $this->prophesize(MiddlewareInterface::class)->reveal(); $config = [ 'routes' => [ [ @@ -124,7 +126,7 @@ public function testInjectRoutesFromConfigSetsUpRoutesFromConfig($middleware) ], [ 'path' => '/ping', - 'middleware' => 'Ping', + 'middleware' => $pingMiddleware, 'allowed_methods' => ['GET'], ], ], diff --git a/test/Container/ApplicationFactoryTest.php b/test/Container/ApplicationFactoryTest.php index 98ef455c..eaeef9f4 100644 --- a/test/Container/ApplicationFactoryTest.php +++ b/test/Container/ApplicationFactoryTest.php @@ -9,6 +9,7 @@ use ArrayObject; use Interop\Http\ServerMiddleware\DelegateInterface; +use Interop\Http\ServerMiddleware\MiddlewareInterface; use PHPUnit\Framework\Assert; use PHPUnit\Framework\TestCase; use Prophecy\Prophecy\ObjectProphecy; @@ -80,7 +81,7 @@ public static function assertRoute($spec, array $routes) return false; } - if ($route->getMiddleware() !== $spec['middleware']) { + if (! $route->getMiddleware()) { return false; } @@ -123,8 +124,8 @@ public function testFactoryWillPullAllReplaceableDependenciesFromContainerWhenPr public function callableMiddlewares() { - $middleware = [ - 'service-name' => 'HelloWorld', + $middlewareTypes = [ + 'service-name' => InvokableMiddleware::class, 'closure' => function () { }, 'callable' => [InvokableMiddleware::class, 'staticallyCallableMiddleware'], @@ -136,7 +137,7 @@ public function callableMiddlewares() ]; foreach ($configTypes as $configType => $config) { - foreach ($middleware as $middlewareType => $middleware) { + foreach ($middlewareTypes as $middlewareType => $middleware) { $name = sprintf('%s-%s', $configType, $middlewareType); yield $name => [$middleware, $config]; } @@ -151,6 +152,7 @@ public function callableMiddlewares() */ public function testFactorySetsUpRoutesFromConfig($middleware, $configType) { + $pingMiddleware = $this->prophesize(MiddlewareInterface::class)->reveal(); $config = [ 'routes' => [ [ @@ -160,7 +162,7 @@ public function testFactorySetsUpRoutesFromConfig($middleware, $configType) ], [ 'path' => '/ping', - 'middleware' => 'Ping', + 'middleware' => $pingMiddleware, 'allowed_methods' => ['GET'], ], ], @@ -238,7 +240,7 @@ public function testCanSpecifyRouteViaConfigurationWithNoMethods($configType) 'routes' => [ [ 'path' => '/', - 'middleware' => 'HelloWorld', + 'middleware' => $this->prophesize(MiddlewareInterface::class)->reveal(), ], ], ]; @@ -275,7 +277,7 @@ public function testCanSpecifyRouteOptionsViaConfiguration($configType) 'routes' => [ [ 'path' => '/', - 'middleware' => 'HelloWorld', + 'middleware' => $this->prophesize(MiddlewareInterface::class)->reveal(), 'name' => 'home', 'allowed_methods' => ['GET'], 'options' => $expected, @@ -333,7 +335,7 @@ public function testExceptionIsRaisedInCaseOfInvalidRouteOptionsConfiguration($c 'routes' => [ [ 'path' => '/', - 'middleware' => 'HelloWorld', + 'middleware' => $this->prophesize(MiddlewareInterface::class)->reveal(), 'options' => 'invalid', ], ], diff --git a/test/Middleware/DispatchMiddlewareTest.php b/test/Middleware/DispatchMiddlewareTest.php index 32ca4fa0..6936d539 100644 --- a/test/Middleware/DispatchMiddlewareTest.php +++ b/test/Middleware/DispatchMiddlewareTest.php @@ -10,11 +10,13 @@ use Interop\Http\ServerMiddleware\DelegateInterface; use Interop\Http\ServerMiddleware\MiddlewareInterface as ServerMiddlewareInterface; use PHPUnit\Framework\TestCase; +use Prophecy\Argument; use Prophecy\Prophecy\ObjectProphecy; use Psr\Container\ContainerInterface; use Psr\Http\Message\ResponseInterface; use Psr\Http\Message\ServerRequestInterface; use Zend\Expressive\Middleware\DispatchMiddleware; +use Zend\Expressive\Middleware\LazyLoadingMiddleware; use Zend\Expressive\Router\Route; use Zend\Expressive\Router\RouteResult; use Zend\Expressive\Router\RouterInterface; @@ -88,11 +90,12 @@ public function testCanDispatchCallableDoublePassMiddleware() $this->delegate->process()->shouldNotBeCalled(); $expected = $this->prophesize(ResponseInterface::class)->reveal(); - $routedMiddleware = function ($request, $response, $next) use ($expected) { - return $expected; - }; + $routedMiddleware = $this->prophesize(ServerMiddlewareInterface::class); + $routedMiddleware + ->process(Argument::that([$this->request, 'reveal']), Argument::that([$this->delegate, 'reveal'])) + ->willReturn($expected); - $routeResult = RouteResult::fromRoute(new Route('/', $routedMiddleware)); + $routeResult = RouteResult::fromRoute(new Route('/', $routedMiddleware->reveal())); $this->request->getAttribute(RouteResult::class, false)->willReturn($routeResult); @@ -104,19 +107,27 @@ public function testCanDispatchCallableDoublePassMiddleware() /** * @group 453 */ - public function testCanDispatchMiddlewareServices() + public function testCanDispatchLazyMiddleware() { $this->delegate->process()->shouldNotBeCalled(); $expected = $this->prophesize(ResponseInterface::class)->reveal(); - $routedMiddleware = function ($request, $response, $next) use ($expected) { - return $expected; - }; + $routedMiddleware = $this->prophesize(ServerMiddlewareInterface::class); + $routedMiddleware + ->process(Argument::that([$this->request, 'reveal']), Argument::that([$this->delegate, 'reveal'])) + ->willReturn($expected); $this->container->has('RoutedMiddleware')->willReturn(true); - $this->container->get('RoutedMiddleware')->willReturn($routedMiddleware); + $this->container->get('RoutedMiddleware')->willReturn($routedMiddleware->reveal()); + + // Since 2.0, we never have service names in routes, only lazy-loading middleware + $lazyMiddleware = new LazyLoadingMiddleware( + $this->container->reveal(), + $this->responsePrototype->reveal(), + 'RoutedMiddleware' + ); - $routeResult = RouteResult::fromRoute(new Route('/', 'RoutedMiddleware')); + $routeResult = RouteResult::fromRoute(new Route('/', $lazyMiddleware)); $this->request->getAttribute(RouteResult::class, false)->willReturn($routeResult);