Completed
Push — master ( 988ea9...868c80 )
by smiley
07:26
created

Response   A

Complexity

Total Complexity 8

Size/Duplication

Total Lines 145
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 1

Importance

Changes 0
Metric Value
dl 0
loc 145
rs 10
c 0
b 0
f 0
wmc 8
lcom 1
cbo 1
1
<?php
2
/**
3
 * Class Response
4
 *
5
 * @filesource   Response.php
6
 * @created      11.08.2018
7
 * @package      chillerlan\HTTP\Psr7
8
 * @author       smiley <[email protected]>
9
 * @copyright    2018 smiley
10
 * @license      MIT
11
 */
12
13
namespace chillerlan\HTTP\Psr7;
14
15
use Fig\Http\Message\StatusCodeInterface;
16
use Psr\Http\Message\ResponseInterface;
17
18
final class Response extends Message implements ResponseInterface, StatusCodeInterface{
19
20
	/**
21
	 * Status codes and reason phrases
22
	 *
23
	 * @var array
24
	 */
25
	public const REASON_PHRASES = [
26
		//Informational 1xx
27
		self::STATUS_CONTINUE                        => 'Continue',
28
		self::STATUS_SWITCHING_PROTOCOLS             => 'Switching Protocols',
29
		self::STATUS_PROCESSING                      => 'Processing',
30
		self::STATUS_EARLY_HINTS                     => 'Early Hints',
31
		//Successful 2xx
32
		self::STATUS_OK                              => 'OK',
33
		self::STATUS_CREATED                         => 'Created',
34
		self::STATUS_ACCEPTED                        => 'Accepted',
35
		self::STATUS_NON_AUTHORITATIVE_INFORMATION   => 'Non-Authoritative Information',
36
		self::STATUS_NO_CONTENT                      => 'No Content',
37
		self::STATUS_RESET_CONTENT                   => 'Reset Content',
38
		self::STATUS_PARTIAL_CONTENT                 => 'Partial Content',
39
		self::STATUS_MULTI_STATUS                    => 'Multi-Status',
40
		self::STATUS_ALREADY_REPORTED                => 'Already Reported',
41
		self::STATUS_IM_USED                         => 'IM Used',
42
		//Redirection 3xx
43
		self::STATUS_MULTIPLE_CHOICES                => 'Multiple Choices',
44
		self::STATUS_MOVED_PERMANENTLY               => 'Moved Permanently',
45
		self::STATUS_FOUND                           => 'Found',
46
		self::STATUS_SEE_OTHER                       => 'See Other',
47
		self::STATUS_NOT_MODIFIED                    => 'Not Modified',
48
		self::STATUS_USE_PROXY                       => 'Use Proxy',
49
		self::STATUS_RESERVED                        => 'Reserved',
50
		self::STATUS_TEMPORARY_REDIRECT              => 'Temporary Redirect',
51
		self::STATUS_PERMANENT_REDIRECT              => 'Permanent Redirect',
52
		//Client Error 4xx
53
		self::STATUS_BAD_REQUEST                     => 'Bad Request',
54
		self::STATUS_UNAUTHORIZED                    => 'Unauthorized',
55
		self::STATUS_PAYMENT_REQUIRED                => 'Payment Required',
56
		self::STATUS_FORBIDDEN                       => 'Forbidden',
57
		self::STATUS_NOT_FOUND                       => 'Not Found',
58
		self::STATUS_METHOD_NOT_ALLOWED              => 'Method Not Allowed',
59
		self::STATUS_NOT_ACCEPTABLE                  => 'Not Acceptable',
60
		self::STATUS_PROXY_AUTHENTICATION_REQUIRED   => 'Proxy Authentication Required',
61
		self::STATUS_REQUEST_TIMEOUT                 => 'Request Timeout',
62
		self::STATUS_CONFLICT                        => 'Conflict',
63
		self::STATUS_GONE                            => 'Gone',
64
		self::STATUS_LENGTH_REQUIRED                 => 'Length Required',
65
		self::STATUS_PRECONDITION_FAILED             => 'Precondition Failed',
66
		self::STATUS_PAYLOAD_TOO_LARGE               => 'Request Entity Too Large',
67
		self::STATUS_URI_TOO_LONG                    => 'Request-URI Too Long',
68
		self::STATUS_UNSUPPORTED_MEDIA_TYPE          => 'Unsupported Media Type',
69
		self::STATUS_RANGE_NOT_SATISFIABLE           => 'Requested Range Not Satisfiable',
70
		self::STATUS_EXPECTATION_FAILED              => 'Expectation Failed',
71
		self::STATUS_IM_A_TEAPOT                     => 'I\'m a teapot',
72
		420                                          => 'Enhance Your Calm', // https://http.cat/420
73
		self::STATUS_MISDIRECTED_REQUEST             => 'Misdirected Request',
74
		self::STATUS_UNPROCESSABLE_ENTITY            => 'Unprocessable Entity',
75
		self::STATUS_LOCKED                          => 'Locked',
76
		self::STATUS_FAILED_DEPENDENCY               => 'Failed Dependency',
77
		self::STATUS_TOO_EARLY                       => 'Too Early',
78
		self::STATUS_UPGRADE_REQUIRED                => 'Upgrade Required',
79
		self::STATUS_PRECONDITION_REQUIRED           => 'Precondition Required',
80
		self::STATUS_TOO_MANY_REQUESTS               => 'Too Many Requests',
81
		self::STATUS_REQUEST_HEADER_FIELDS_TOO_LARGE => 'Request Header Fields Too Large',
82
		444                                          => 'Connection Closed Without Response',
83
		self::STATUS_UNAVAILABLE_FOR_LEGAL_REASONS   => 'Unavailable For Legal Reasons',
84
		499                                          => 'Client Closed Request',
85
		//Server Error 5xx
86
		self::STATUS_INTERNAL_SERVER_ERROR           => 'Internal Server Error',
87
		self::STATUS_NOT_IMPLEMENTED                 => 'Not Implemented',
88
		self::STATUS_BAD_GATEWAY                     => 'Bad Gateway',
89
		self::STATUS_SERVICE_UNAVAILABLE             => 'Service Unavailable',
90
		self::STATUS_GATEWAY_TIMEOUT                 => 'Gateway Timeout',
91
		self::STATUS_VERSION_NOT_SUPPORTED           => 'HTTP Version Not Supported',
92
		self::STATUS_VARIANT_ALSO_NEGOTIATES         => 'Variant Also Negotiates',
93
		self::STATUS_INSUFFICIENT_STORAGE            => 'Insufficient Storage',
94
		self::STATUS_LOOP_DETECTED                   => 'Loop Detected',
95
		self::STATUS_NOT_EXTENDED                    => 'Not Extended',
96
		self::STATUS_NETWORK_AUTHENTICATION_REQUIRED => 'Network Authentication Required',
97
		599                                          => 'Network Connect Timeout Error',
98
	];
99
100
	/**
101
	 * @var string
102
	 */
103
	private string $reasonPhrase;
0 ignored issues
show
Bug introduced by
This code did not parse for me. Apparently, there is an error somewhere around this line:

Syntax error, unexpected T_STRING, expecting T_FUNCTION or T_CONST
Loading history...
104
105
	/**
106
	 * @var int
107
	 */
108
	private int $statusCode;
109
110
	/**
111
	 * Response constructor.
112
	 *
113
	 * @param int|null                                               $status
114
	 * @param array|null                                             $headers
115
	 * @param string|null|resource|\Psr\Http\Message\StreamInterface $body
116
	 * @param string|null                                            $version
117
	 * @param string|null                                            $reason
118
	 */
119
	public function __construct(int $status = null, array $headers = null, $body = null, string $version = null, string $reason = null){
120
		parent::__construct($headers, $body, $version);
121
122
		$reason = $reason ?? '';
123
124
		$this->statusCode   = $status ?? $this::STATUS_OK;
125
		$this->reasonPhrase = $reason === '' && isset($this::REASON_PHRASES[$this->statusCode])
126
			? $this::REASON_PHRASES[$this->statusCode]
127
			: $reason;
128
129
	}
130
131
	/**
132
	 * @inheritDoc
133
	 */
134
	public function getStatusCode():int{
135
		return $this->statusCode;
136
	}
137
138
	/**
139
	 * @inheritDoc
140
	 */
141
	public function withStatus($code, $reasonPhrase = ''):ResponseInterface{
142
		$code         = (int)$code;
143
		$reasonPhrase = (string)$reasonPhrase;
144
145
		if($reasonPhrase === '' && isset($this::REASON_PHRASES[$code])){
146
			$reasonPhrase = $this::REASON_PHRASES[$code];
147
		}
148
149
		$clone               = clone $this;
150
		$clone->statusCode   = $code;
151
		$clone->reasonPhrase = $reasonPhrase;
152
153
		return $clone;
154
	}
155
156
	/**
157
	 * @inheritDoc
158
	 */
159
	public function getReasonPhrase():string{
160
		return $this->reasonPhrase;
161
	}
162
163
}
164