Passed
Pull Request — master (#4)
by Randy
02:01
created

JSend::render()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 9
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 9
rs 9.6666
c 0
b 0
f 0
cc 1
eloc 6
nc 1
nop 2
1
<?php
2
3
namespace Demv\JSend;
4
5
use Seld\JsonLint\JsonParser;
6
use function Dgame\Ensurance\ensure;
7
8
/**
9
 * Class JSend
10
 * @package Demv\JSend
11
 */
12
final class JSend
13
{
14
    /**
15
     * @param array $response
16
     *
17
     * @return JSendResponseInterface
18
     */
19
    private static function interpret(array $response): JSendResponseInterface
20
    {
21
        ensure($response)->isArray()->hasKey('status')->orThrow('Key "status" is required');
22
23
        $status = Status::instance($response['status']);
24
        if ($status->isSuccess() || $status->isFail()) {
25
            ensure($response)->isArray()->hasKey('data')->orThrow('Key "data" is required');
26
27
            return new JSendResponse($status, $response['data']);
28
        }
29
30
        return new JSendErrorResponse($status, $response);
31
    }
32
33
    /**
34
     * @param string $json
35
     *
36
     * @return JSendResponseInterface
37
     * @throws \Seld\JsonLint\ParsingException
38
     */
39
    public static function decode(string $json): JSendResponseInterface
40
    {
41
        $parser = new JsonParser();
42
        $result = $parser->parse($json, JsonParser::PARSE_TO_ASSOC | JsonParser::DETECT_KEY_CONFLICTS);
43
44
        return self::interpret($result);
45
    }
46
47
    /**
48
     * @param array $response
49
     * @param int   $options
50
     *
51
     * @return string
52
     */
53
    public static function encode(array $response, int $options = 0): string
54
    {
55
        ensure($response)->isNotEmpty()->orThrow('Empty response cannot be converted to valid JSend-JSON');
56
        ensure($response)->isArray()->hasKey('status')->orThrow('Key "status" is required');
57
        $status = Status::instance($response['status']);
58
        if ($status->isError()) {
59
            ensure($response)->isArray()->hasKey('message')->orThrow('Need a descriptive error-message');
60
        }
61
62
        return json_encode($response, $options);
63
    }
64
65
    /**
66
     * @param JSendResponseInterface $response
67
     *
68
     * @return int|null
69
     */
70
    public static function getDefaultHttpStatusCode(JSendResponseInterface $response): ?int
71
    {
72
        if ($response->getStatus()->isError()) {
73
            return $response->getError()->getCode() ?? 400;
74
        }
75
76
        if ($response->getStatus()->isSuccess()) {
77
            return 200;
78
        }
79
80
        return null;
81
    }
82
83
    /**
84
     * @param JSendResponseInterface $response
85
     * @param int|null               $code
86
     */
87
    public static function render(JSendResponseInterface $response, int $code = null): void
88
    {
89
        $code = $code ?? self::getDefaultHttpStatusCode($response);
90
        ensure($code)->isInt()->isBetween(100, 500);
91
92
        header('Content-Type: application/json; charset="UTF-8"', true, $code);
93
        print json_encode($response);
94
        exit;
95
    }
96
}
97