For middleware to use with Relay, please review middlewares/psr15-middlewares.

Relay is a PSR-15 server request handler (aka “dispatcher”) for a queue of PSR-15 middleware entries.

Request Handling

First, create an array or traversable $queue of middleware entries:

$queue[] = new FooMiddleware();
$queue[] = new BarMiddleware();
$queue[] = new BazMiddleware();
// ...
$queue[] = new class implements Psr\Http\Server\MiddlewareInterface {
    public function process(
        Psr\Http\Message\ServerRequestInterface $request,
        Psr\Http\Server\RequestHandlerInterface $handler
    ): Psr\Http\Message\ResponseInterface {
        return new Response();

Then create a Relay with the $queue and call the handle() method with a server request.

 * @var \Psr\Http\Message\ServerRequestInterface $request
 * @var \Psr\Http\Message\ResponseInterface $response

use Relay\Relay;

$relay = new Relay($queue);
$response = $relay->handle($request);

You may also use RelayBuilder to create a Relay.

 * @var \Psr\Http\Message\RequestInterface $request
 * @var \Psr\Http\Message\ResponseInterface $response

use Relay\RelayBuilder;

$relayBuilder = new RelayBuilder();
$relay = $relayBuilder->newInstance($queue);
$response = $relay->handle($request);

Relay will execute the queue in first-in-first-out order.

Queue Entry Resolvers

You may wish to use $queue entries other than already-instantiated objects. If so, you can pass a $resolver callable to Relay that will convert the $queue entry to an instance. Thus, using a $resolver allows you to pass in your own factory mechanism for $queue entries.

For example, this $resolver will naively convert $queue string entries to new class instances:

$resolver = function ($entry) {
    return new $entry();

You can then add $queue entries as class names, and Relay will use the $resolver to create the objects in turn.

$queue[] = 'FooMiddleware';
$queue[] = 'BarMiddleware';
$queue[] = 'BazMiddleware';
$queue[] = 'ResponseFactoryMiddleware';

$relay = new Relay($queue, $resolver);

You can also pass a $resolver to Relay when using RelayBuilder.

// ...

$relayBuilder = new RelayBuilder($resolver);
$relay = $relayBuilder->newInstance($queue);

Callable Middleware

Relay can also handle any middleware entries that are callables with the following signature:

use Psr\Http\Message\ServerRequestInterface as Request;
use Psr\Http\Message\ResponseInterface as Response;

function (
    Request $request, // the request
    callable $next // the next middleware or handler
) : Response {
    // ...

Callable middleware may be intermingled with PSR-15 middleware.