That’s the most accurate description thus far Larry, yes. Why can’t I write 
that simply eh? :)


On 21 February 2017 at 18:27:56, Larry Garfield (la...@garfieldtech.com) wrote:

If I am following you, your issue is more that you would want to see three 
different types of middleware: Passthrough a request (with modification), turn 
request to response, and passthrough response (with modification).  Is that 
more accurate?  The core of a middleware dispacher would then be:

foreach ($requestHandlers as $h) {
  $req = $h->process($req);
}
$res = $coreHandler->process($req);
foreach ($responseHandlers as $h) {
  $res = $h->process($res);
}

Is that more what you're talking about?

--Larry Garfield

On 02/21/2017 12:21 PM, John Porter wrote:
Sadly, I have not explained very well have I, as no one seems to grasp what I 
am on about.

The middleware does not need to know about the exchange at all, it is only 
responsible for receiving a Message and returning a Message. I am currently 
coding up the example to show you all.

Woody, for your scenario, the RequestMiddlewareInterface would return a 
ResponseInterface instance, this is why the return value is only typed to 
MessageInterface; to allow that short circuit to be returned, so that the stack 
can terminate.

I think my example (with tests) will highlight this better than I can explain; 
bear with me.


On 21 February 2017 at 18:13:35, Michael Mayer (mich...@schnittstabil.de) wrote:

As far as I can see, the essential difference between PSR-15 and your proposal 
is about the responsibility for dispatching the next middleware:
1. with your version: it is determined at compile time, by implementing the 
appropriate interface; thus the stack should be responsible for it only.
2. with the PSR-15 version: it is determined at run time, thus the stack and 
the middleware are responsible for dispatching the next middleware.

Django, StackPHP and Guzzle for example, have chosen an approach which seems to 
align better to your version. In essence, their middlewares could be typed as:

(RequestInterface -> ResponseInterface) -> (RequestInterface -> 
ResponseInterface)

Or, if we want to use PHP interfaces only, then we could type them:

interface ExchangeInterface
{
    public function __invoke(RequestInterface $request): ResponseInterface;
}

interface MiddlewareInterface
{
    public function __invoke(ExchangeInterface $next): ExchangeInterface;
}

At first glance that could solve your issues with the current PSR-15, the 
exchanger does not seem to be responsible for dispatching the next exchanger 
and middlewares are simple exchange factories. And moreover we do not need 
middleware dispatchers anymore.

Unfortunately that isn't very attractive in PHP, a middleware would look like:

class UnicornMiddleware implements MiddlewareInterface
{
    public function __invoke(ExchangeInterface $next): ExchangeInterface {
        return new class($next) implements ExchangeInterface {
            private $next;

            public function __construct($next)
            {
                $this->next = $next;
            }

            public function __invoke(RequestInterface $request): 
ResponseInterface
            {
                return (($this->next)($request))->withHeader('X-PoweredBy', 
'Unicorns');
            }
        };
    }
}

That's probably one of the reasons why StackPHP uses `__construct` and Guzzle 
uses closures. But even worse, the inner ExchangeInterface instance is still 
responsible for dispatching the next middleware :(

Are the PSR-15 interfaces so bad? From the perspective of a functional 
programmer, we can do some simple currying to change the typing to get better 
interfaces:

(RequestInterface -> ResponseInterface) -> (RequestInterface -> 
ResponseInterface)
// using curry:
(RequestInterface -> ResponseInterface) -> RequestInterface -> ResponseInterface
// and again:
((RequestInterface -> ResponseInterface) -> RequestInterface) -> 
ResponseInterface

Again, if we use PHP `interfaces` only, the last version could look like this 
in PHP:

interface ExchangeInterface
{
    public function __invoke(RequestInterface $request): ResponseInterface;
}

interface MiddlewareInterface
{
    public function __invoke(ExchangeInterface $next, RequestInterface 
$request);
}

Aside from the parameter order, the similarities to the PSR-15 version are 
already obvious (Sadly, the names and implied contracts are very different and 
PSR-15 does not describe a functional middleware pattern anymore :cry: ).

Anyway, the example above becomes much simpler with the current PSR-15 
interfaces:

class UnicornMiddleware implements ServerMiddlewareInterface
{
    public function process(ServerRequestInterface $request, DelegateInterface 
$delegate) {
        return $delegate->process($request)->withHeader('X-PoweredBy', 
'Unicorns');
    }
}

Thus I believe your proposal does not fit better to the middleware pattern.

--
You received this message because you are subscribed to a topic in the Google 
Groups "PHP Framework Interoperability Group" group.
To unsubscribe from this topic, visit 
https://groups.google.com/d/topic/php-fig/vCKxyraoqnc/unsubscribe.
To unsubscribe from this group and all its topics, send an email to 
php-fig+unsubscr...@googlegroups.com.
To post to this group, send email to php-fig@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/php-fig/b0794cd8-089a-4753-bbf5-9a3d0e833b06%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.
--
You received this message because you are subscribed to the Google Groups "PHP 
Framework Interoperability Group" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to php-fig+unsubscr...@googlegroups.com.
To post to this group, send email to php-fig@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/php-fig/etPan.58ac8529.344f83e6.2227%40designermonkey.co.uk.
For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to a topic in the Google 
Groups "PHP Framework Interoperability Group" group.
To unsubscribe from this topic, visit 
https://groups.google.com/d/topic/php-fig/vCKxyraoqnc/unsubscribe.
To unsubscribe from this group and all its topics, send an email to 
php-fig+unsubscr...@googlegroups.com.
To post to this group, send email to php-fig@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/php-fig/8f66492b-db0c-8017-f758-0f14fdce90fd%40garfieldtech.com.
For more options, visit https://groups.google.com/d/optout.

-- 
You received this message because you are subscribed to the Google Groups "PHP 
Framework Interoperability Group" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to php-fig+unsubscr...@googlegroups.com.
To post to this group, send email to php-fig@googlegroups.com.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/php-fig/etPan.58ac88de.4658988a.2227%40designermonkey.co.uk.
For more options, visit https://groups.google.com/d/optout.

Reply via email to