Completed
Pull Request — master (#148)
by Alejandro
04:16
created

process()   A

Complexity

Conditions 3
Paths 4

Size

Total Lines 20
Code Lines 12

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 12
CRAP Score 3

Importance

Changes 0
Metric Value
cc 3
eloc 12
nc 4
nop 2
dl 0
loc 20
ccs 12
cts 12
cp 1
crap 3
rs 9.4285
c 0
b 0
f 0
1
<?php
2
declare(strict_types=1);
3
4
namespace Shlinkio\Shlink\Rest\Middleware\ShortCode;
5
6
use Psr\Http\Message\ResponseInterface;
7
use Psr\Http\Message\ServerRequestInterface;
8
use Psr\Http\Server\MiddlewareInterface;
9
use Psr\Http\Server\RequestHandlerInterface;
10
use Zend\Diactoros\Response;
11
use Zend\Diactoros\Response\JsonResponse;
12
13
class CreateShortCodeContentNegotiationMiddleware implements MiddlewareInterface
14
{
15
    private const PLAIN_TEXT = 'text';
16
    private const JSON = 'json';
17
18
    /**
19
     * Process an incoming server request and return a response, optionally delegating
20
     * response creation to a handler.
21
     * @throws \RuntimeException
22
     * @throws \InvalidArgumentException
23
     */
24 7
    public function process(ServerRequestInterface $request, RequestHandlerInterface $handler): ResponseInterface
25
    {
26
        /** @var JsonResponse $response */
27 7
        $response = $handler->handle($request);
28 7
        $acceptedType = $request->hasHeader('Accept')
29 3
            ? $this->determineAcceptTypeFromHeader($request->getHeaderLine('Accept'))
30 7
            : $this->determineAcceptTypeFromQuery($request->getQueryParams());
31
32
        // If JSON was requested, return the response from next handler as is
33 7
        if ($acceptedType === self::JSON) {
34 5
            return $response;
35
        }
36
37
        // If requested, return a plain text response containing the short URL only
38 2
        $resp = (new Response())->withHeader('Content-Type', 'text/plain');
39 2
        $body = $resp->getBody();
40 2
        $body->write($response->getPayload()['shortUrl'] ?? '');
41 2
        $body->rewind();
42 2
        return $resp;
43
    }
44
45 4
    private function determineAcceptTypeFromQuery(array $query): string
46
    {
47 4
        if (! isset($query['format'])) {
48 1
            return self::JSON;
49
        }
50
51 3
        $format = \strtolower((string) $query['format']);
52 3
        return $format === 'txt' ? self::PLAIN_TEXT : self::JSON;
53
    }
54
55 3
    private function determineAcceptTypeFromHeader(string $acceptValue): string
56
    {
57 3
        $accepts = \explode(',', $acceptValue);
58 3
        $accept = \strtolower(\array_shift($accepts));
59 3
        return \strpos($accept, 'text/plain') !== false ? self::PLAIN_TEXT : self::JSON;
60
    }
61
}
62