Skip to content
This repository was archived by the owner on Jan 29, 2020. It is now read-only.

Commit 59c76c9

Browse files
committed
Implement request/response decoration
Currently, the `Zend\Stratigility\Next` implementation requires that the request and response passed to it are the Stratigility-specific decorators. As such, the `ErrorMiddlewarePipe` is required to decorate the incoming request and response. I chose to use reflection here so as not to duplicate logic; ideally, we can remove that requirement from the Stratigility library in the future.
1 parent b7becdc commit 59c76c9

File tree

2 files changed

+45
-1
lines changed

2 files changed

+45
-1
lines changed

src/ErrorMiddlewarePipe.php

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@
1111

1212
use Psr\Http\Message\ServerRequestInterface as Request;
1313
use Psr\Http\Message\ResponseInterface as Response;
14+
use ReflectionMethod;
1415
use ReflectionProperty;
1516
use Zend\Stratigility\FinalHandler;
1617
use Zend\Stratigility\MiddlewarePipe;
@@ -63,6 +64,11 @@ public function __construct(MiddlewarePipe $pipeline)
6364
*/
6465
public function __invoke($error, Request $request, Response $response, callable $out = null)
6566
{
67+
// Decorate instances with Stratigility decorators; required to work
68+
// with Next implementation.
69+
$request = $this->decorateRequest($request);
70+
$response = $this->decorateResponse($response);
71+
6672
$pipeline = $this->getInternalPipeline();
6773
$done = $out ?: new FinalHandler([], $response);
6874
$next = new Next($pipeline, $done);
@@ -85,4 +91,34 @@ private function getInternalPipeline()
8591
$r->setAccessible(true);
8692
return $r->getValue($this->pipeline);
8793
}
94+
95+
/**
96+
* Decorate the request with the Stratigility decorator.
97+
*
98+
* Proxies to the composed MiddlewarePipe's equivalent method.
99+
*
100+
* @param Request $request
101+
* @return \Zend\Stratigility\Http\Request
102+
*/
103+
private function decorateRequest(Request $request)
104+
{
105+
$r = new ReflectionMethod($this->pipeline, 'decorateRequest');
106+
$r->setAccessible(true);
107+
return $r->invoke($this->pipeline, $request);
108+
}
109+
110+
/**
111+
* Decorate the response with the Stratigility decorator.
112+
*
113+
* Proxies to the composed MiddlewarePipe's equivalent method.
114+
*
115+
* @param Response $response
116+
* @return \Zend\Stratigility\Http\Response
117+
*/
118+
private function decorateResponse(Response $response)
119+
{
120+
$r = new ReflectionMethod($this->pipeline, 'decorateResponse');
121+
$r->setAccessible(true);
122+
return $r->invoke($this->pipeline, $response);
123+
}
88124
}

test/ErrorMiddlewarePipeTest.php

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
use Psr\Http\Message\ResponseInterface as Response;
1515
use Psr\Http\Message\UriInterface as Uri;
1616
use Zend\Expressive\ErrorMiddlewarePipe;
17+
use Zend\Stratigility\Http\Response as StratigilityResponse;
1718
use Zend\Stratigility\MiddlewarePipe;
1819

1920
class ErrorMiddlewarePipeTest extends TestCase
@@ -56,14 +57,21 @@ public function testWillDispatchErrorMiddlewareComposedInInternalPipeline()
5657
$uri->getPath()->willReturn('/');
5758
$request = $this->prophesize(Request::class);
5859
$request->getUri()->willReturn($uri->reveal());
60+
61+
// The following is required due to Stratigility decorating requests:
62+
$request->withAttribute('originalUri', $uri->reveal())->will(function () use ($request) {
63+
return $request->reveal();
64+
});
65+
5966
$response = $this->prophesize(Response::class);
6067

6168
$final = function ($request, $response, $err = null) {
6269
$this->fail('Final handler should not be triggered');
6370
};
6471

6572
$result = $this->errorPipe->__invoke($error, $request->reveal(), $response->reveal(), $final);
66-
$this->assertSame($response->reveal(), $result);
73+
$this->assertInstanceOf(StratigilityResponse::class, $result);
74+
$this->assertSame($response->reveal(), $result->getOriginalResponse());
6775
$this->assertTrue($triggered->first);
6876
$this->assertFalse($triggered->second);
6977
$this->assertTrue($triggered->third);

0 commit comments

Comments
 (0)