diff --git a/src/Client/Connection.php b/src/Client/Connection.php index ece39ff..0ce9b97 100644 --- a/src/Client/Connection.php +++ b/src/Client/Connection.php @@ -17,10 +17,10 @@ use Psr\Http\Message\RequestInterface; use Psr\Http\Message\ResponseInterface; use Ripple\Coroutine\Coroutine; -use Ripple\Coroutine\WaitGroup; use Ripple\Socket; use Ripple\Stream\Exception\ConnectionException; use Ripple\Stream\Exception\RuntimeException; +use Ripple\WaitGroup; use Throwable; use function Co\cancel; @@ -340,7 +340,7 @@ public function process(): ResponseInterface|null } $this->versionString = $base[0]; - $this->statusCode = intval($base[1]); + $this->statusCode = (int)$base[1]; $this->statusMessage = $base[2]; /*** Parse header*/ @@ -351,13 +351,13 @@ public function process(): ResponseInterface|null } } - if ($this->chunk = isset($this->headers['TRANSFER-ENCODING']) && $this->headers['TRANSFER-ENCODING'] === 'chunked') { + if ($this->chunk = (isset($this->headers['TRANSFER-ENCODING']) && $this->headers['TRANSFER-ENCODING'] === 'chunked')) { $this->step = 3; $this->buffer = substr($buffer, $headerEnd + 4); } else { - $contentLength = $this->headers['CONTENT-LENGTH'] ?? $this->headers['CONTENT-LENGTH'] ?? null; + $contentLength = $this->headers['CONTENT-LENGTH'] ?? null; if ($contentLength !== null) { - $this->contentLength = intval($contentLength); + $this->contentLength = (int)$contentLength; $buffer = substr($buffer, $headerEnd + 4); $this->output($buffer); $this->bodyLength += strlen($buffer); diff --git a/src/Enum/Status.php b/src/Enum/Status.php index bf35cc3..596626d 100644 --- a/src/Enum/Status.php +++ b/src/Enum/Status.php @@ -13,136 +13,156 @@ namespace Ripple\Http\Enum; /** - * + * HTTP状态码枚举 */ -enum Status +enum Status: int { - public const CONTINUE = 100; - public const SWITCHING_PROTOCOLS = 101; - public const PROCESSING = 102; - public const EARLY_HINTS = 103; - public const OK = 200; - public const CREATED = 201; - public const ACCEPTED = 202; - public const NON_AUTHORITATIVE_INFORMATION = 203; - public const NO_CONTENT = 204; - public const RESET_CONTENT = 205; - public const PARTIAL_CONTENT = 206; - public const MULTI_STATUS = 207; - public const ALREADY_REPORTED = 208; - public const IM_USED = 226; - public const MULTIPLE_CHOICES = 300; - public const MOVED_PERMANENTLY = 301; - public const FOUND = 302; - public const SEE_OTHER = 303; - public const NOT_MODIFIED = 304; - public const USE_PROXY = 305; - public const SWITCH_PROXY = 306; - public const TEMPORARY_REDIRECT = 307; - public const PERMANENT_REDIRECT = 308; - public const BAD_REQUEST = 400; - public const UNAUTHORIZED = 401; - public const PAYMENT_REQUIRED = 402; - public const FORBIDDEN = 403; - public const NOT_FOUND = 404; - public const METHOD_NOT_ALLOWED = 405; - public const NOT_ACCEPTABLE = 406; - public const PROXY_AUTHENTICATION_REQUIRED = 407; - public const REQUEST_TIMEOUT = 408; - public const CONFLICT = 409; - public const GONE = 410; - public const LENGTH_REQUIRED = 411; - public const PRECONDITION_FAILED = 412; - public const PAYLOAD_TOO_LARGE = 413; - public const URI_TOO_LONG = 414; - public const UNSUPPORTED_MEDIA_TYPE = 415; - public const RANGE_NOT_SATISFIABLE = 416; - public const EXPECTATION_FAILED = 417; - public const IM_A_TEAPOT = 418; - public const MISDIRECTED_REQUEST = 421; - public const UNPROCESSABLE_ENTITY = 422; - public const LOCKED = 423; - public const FAILED_DEPENDENCY = 424; - public const TOO_EARLY = 425; - public const UPGRADE_REQUIRED = 426; - public const PRECONDITION_REQUIRED = 428; - public const TOO_MANY_REQUESTS = 429; - public const REQUEST_HEADER_FIELDS_TOO_LARGE = 431; - public const UNAVAILABLE_FOR_LEGAL_REASONS = 451; - public const INTERNAL_SERVER_ERROR = 500; - public const NOT_IMPLEMENTED = 501; - public const BAD_GATEWAY = 502; - public const SERVICE_UNAVAILABLE = 503; - public const GATEWAY_TIMEOUT = 504; - public const HTTP_VERSION_NOT_SUPPORTED = 505; - public const VARIANT_ALSO_NEGOTIATES = 506; - public const INSUFFICIENT_STORAGE = 507; - public const LOOP_DETECTED = 508; - public const NOT_EXTENDED = 510; - public const NETWORK_AUTHENTICATION_REQUIRED = 511; + case CONTINUE = 100; + case SWITCHING_PROTOCOLS = 101; + case PROCESSING = 102; + case EARLY_HINTS = 103; + case OK = 200; + case CREATED = 201; + case ACCEPTED = 202; + case NON_AUTHORITATIVE_INFORMATION = 203; + case NO_CONTENT = 204; + case RESET_CONTENT = 205; + case PARTIAL_CONTENT = 206; + case MULTI_STATUS = 207; + case ALREADY_REPORTED = 208; + case IM_USED = 226; + case MULTIPLE_CHOICES = 300; + case MOVED_PERMANENTLY = 301; + case FOUND = 302; + case SEE_OTHER = 303; + case NOT_MODIFIED = 304; + case USE_PROXY = 305; + case SWITCH_PROXY = 306; + case TEMPORARY_REDIRECT = 307; + case PERMANENT_REDIRECT = 308; + case BAD_REQUEST = 400; + case UNAUTHORIZED = 401; + case PAYMENT_REQUIRED = 402; + case FORBIDDEN = 403; + case NOT_FOUND = 404; + case METHOD_NOT_ALLOWED = 405; + case NOT_ACCEPTABLE = 406; + case PROXY_AUTHENTICATION_REQUIRED = 407; + case REQUEST_TIMEOUT = 408; + case CONFLICT = 409; + case GONE = 410; + case LENGTH_REQUIRED = 411; + case PRECONDITION_FAILED = 412; + case PAYLOAD_TOO_LARGE = 413; + case URI_TOO_LONG = 414; + case UNSUPPORTED_MEDIA_TYPE = 415; + case RANGE_NOT_SATISFIABLE = 416; + case EXPECTATION_FAILED = 417; + case IM_A_TEAPOT = 418; + case MISDIRECTED_REQUEST = 421; + case UNPROCESSABLE_ENTITY = 422; + case LOCKED = 423; + case FAILED_DEPENDENCY = 424; + case TOO_EARLY = 425; + case UPGRADE_REQUIRED = 426; + case PRECONDITION_REQUIRED = 428; + case TOO_MANY_REQUESTS = 429; + case REQUEST_HEADER_FIELDS_TOO_LARGE = 431; + case UNAVAILABLE_FOR_LEGAL_REASONS = 451; + case INTERNAL_SERVER_ERROR = 500; + case NOT_IMPLEMENTED = 501; + case BAD_GATEWAY = 502; + case SERVICE_UNAVAILABLE = 503; + case GATEWAY_TIMEOUT = 504; + case HTTP_VERSION_NOT_SUPPORTED = 505; + case VARIANT_ALSO_NEGOTIATES = 506; + case INSUFFICIENT_STORAGE = 507; + case LOOP_DETECTED = 508; + case NOT_EXTENDED = 510; + case NETWORK_AUTHENTICATION_REQUIRED = 511; + + /** + * 获取状态码对应的消息 + * + * @return string + */ + public function getMessage(): string + { + return match ($this) { + self::CONTINUE => 'Continue', + self::SWITCHING_PROTOCOLS => 'Switching Protocols', + self::PROCESSING => 'Processing', + self::EARLY_HINTS => 'Early Hints', + self::OK => 'OK', + self::CREATED => 'Created', + self::ACCEPTED => 'Accepted', + self::NON_AUTHORITATIVE_INFORMATION => 'Non-Authoritative Information', + self::NO_CONTENT => 'No Content', + self::RESET_CONTENT => 'Reset Content', + self::PARTIAL_CONTENT => 'Partial Content', + self::MULTI_STATUS => 'Multi-Status', + self::ALREADY_REPORTED => 'Already Reported', + self::IM_USED => 'IM Used', + self::MULTIPLE_CHOICES => 'Multiple Choices', + self::MOVED_PERMANENTLY => 'Moved Permanently', + self::FOUND => 'Found', + self::SEE_OTHER => 'See Other', + self::NOT_MODIFIED => 'Not Modified', + self::USE_PROXY => 'Use Proxy', + self::SWITCH_PROXY => 'Switch Proxy', + self::TEMPORARY_REDIRECT => 'Temporary Redirect', + self::PERMANENT_REDIRECT => 'Permanent Redirect', + self::BAD_REQUEST => 'Bad Request', + self::UNAUTHORIZED => 'Unauthorized', + self::PAYMENT_REQUIRED => 'Payment Required', + self::FORBIDDEN => 'Forbidden', + self::NOT_FOUND => 'Not Found', + self::METHOD_NOT_ALLOWED => 'Method Not Allowed', + self::NOT_ACCEPTABLE => 'Not Acceptable', + self::PROXY_AUTHENTICATION_REQUIRED => 'Proxy Authentication Required', + self::REQUEST_TIMEOUT => 'Request Timeout', + self::CONFLICT => 'Conflict', + self::GONE => 'Gone', + self::LENGTH_REQUIRED => 'Length Required', + self::PRECONDITION_FAILED => 'Precondition Failed', + self::PAYLOAD_TOO_LARGE => 'Payload Too Large', + self::URI_TOO_LONG => 'URI Too Long', + self::UNSUPPORTED_MEDIA_TYPE => 'Unsupported Media Type', + self::RANGE_NOT_SATISFIABLE => 'Range Not Satisfiable', + self::EXPECTATION_FAILED => 'Expectation Failed', + self::IM_A_TEAPOT => 'I\'m a teapot', + self::MISDIRECTED_REQUEST => 'Misdirected Request', + self::UNPROCESSABLE_ENTITY => 'Unprocessable Entity', + self::LOCKED => 'Locked', + self::FAILED_DEPENDENCY => 'Failed Dependency', + self::TOO_EARLY => 'Too Early', + self::UPGRADE_REQUIRED => 'Upgrade Required', + self::PRECONDITION_REQUIRED => 'Precondition Required', + self::TOO_MANY_REQUESTS => 'Too Many Requests', + self::REQUEST_HEADER_FIELDS_TOO_LARGE => 'Request Header Fields Too Large', + self::UNAVAILABLE_FOR_LEGAL_REASONS => 'Unavailable For Legal Reasons', + self::INTERNAL_SERVER_ERROR => 'Internal Server Error', + self::NOT_IMPLEMENTED => 'Not Implemented', + self::BAD_GATEWAY => 'Bad Gateway', + self::SERVICE_UNAVAILABLE => 'Service Unavailable', + self::GATEWAY_TIMEOUT => 'Gateway Timeout', + self::HTTP_VERSION_NOT_SUPPORTED => 'HTTP Version Not Supported', + self::VARIANT_ALSO_NEGOTIATES => 'Variant Also Negotiates', + self::INSUFFICIENT_STORAGE => 'Insufficient Storage', + self::LOOP_DETECTED => 'Loop Detected', + self::NOT_EXTENDED => 'Not Extended', + self::NETWORK_AUTHENTICATION_REQUIRED => 'Network Authentication Required', + }; + } - public const MESSAGES = [ - Status::CONFLICT => 'Conflict', - Status::CREATED => 'Created', - Status::OK => 'OK', - Status::BAD_REQUEST => 'Bad Request', - Status::FORBIDDEN => 'Forbidden', - Status::GONE => 'Gone', - Status::INTERNAL_SERVER_ERROR => 'Internal Server Error', - Status::METHOD_NOT_ALLOWED => 'Method Not Allowed', - Status::MOVED_PERMANENTLY => 'Moved Permanently', - Status::MULTIPLE_CHOICES => 'Multiple Choices', - Status::NOT_FOUND => 'Not Found', - Status::NOT_IMPLEMENTED => 'Not Implemented', - Status::NOT_MODIFIED => 'Not Modified', - Status::PAYLOAD_TOO_LARGE => 'Payload Too Large', - Status::SERVICE_UNAVAILABLE => 'Service Unavailable', - Status::UNAUTHORIZED => 'Unauthorized', - Status::UNSUPPORTED_MEDIA_TYPE => 'Unsupported Media Type', - Status::ACCEPTED => 'Accepted', - Status::ALREADY_REPORTED => 'Already Reported', - Status::EARLY_HINTS => 'Early Hints', - Status::EXPECTATION_FAILED => 'Expectation Failed', - Status::FAILED_DEPENDENCY => 'Failed Dependency', - Status::IM_A_TEAPOT => 'I\'m a teapot', - Status::IM_USED => 'IM Used', - Status::INSUFFICIENT_STORAGE => 'Insufficient Storage', - Status::LENGTH_REQUIRED => 'Length Required', - Status::LOCKED => 'Locked', - Status::LOOP_DETECTED => 'Loop Detected', - Status::MULTI_STATUS => 'Multi-Status', - Status::NETWORK_AUTHENTICATION_REQUIRED => 'Network Authentication Required', - Status::NON_AUTHORITATIVE_INFORMATION => 'Non-Authoritative Information', - Status::NOT_ACCEPTABLE => 'Not Acceptable', - Status::NOT_EXTENDED => 'Not Extended', - Status::NO_CONTENT => 'No Content', - Status::PARTIAL_CONTENT => 'Partial Content', - Status::PAYMENT_REQUIRED => 'Payment Required', - Status::PERMANENT_REDIRECT => 'Permanent Redirect', - Status::PRECONDITION_FAILED => 'Precondition Failed', - Status::PRECONDITION_REQUIRED => 'Precondition Required', - Status::PROCESSING => 'Processing', - Status::PROXY_AUTHENTICATION_REQUIRED => 'Proxy Authentication Required', - Status::RANGE_NOT_SATISFIABLE => 'Range Not Satisfiable', - Status::RESET_CONTENT => 'Reset Content', - Status::SEE_OTHER => 'See Other', - Status::SWITCHING_PROTOCOLS => 'Switching Protocols', - Status::TEMPORARY_REDIRECT => 'Temporary Redirect', - Status::TOO_EARLY => 'Too Early', - Status::TOO_MANY_REQUESTS => 'Too Many Requests', - Status::UNAVAILABLE_FOR_LEGAL_REASONS => 'Unavailable For Legal Reasons', - Status::UNPROCESSABLE_ENTITY => 'Unprocessable Entity', - Status::UPGRADE_REQUIRED => 'Upgrade Required', - Status::URI_TOO_LONG => 'URI Too Long', - Status::VARIANT_ALSO_NEGOTIATES => 'Variant Also Negotiates', - Status::FOUND => 'Found', - Status::USE_PROXY => 'Use Proxy', - Status::SWITCH_PROXY => 'Switch Proxy', - Status::REQUEST_TIMEOUT => 'Request Timeout', - Status::MISDIRECTED_REQUEST => 'Misdirected Request', - Status::REQUEST_HEADER_FIELDS_TOO_LARGE => 'Request Header Fields Too Large', - Status::BAD_GATEWAY => 'Bad Gateway', - Status::GATEWAY_TIMEOUT => 'Gateway Timeout', - Status::HTTP_VERSION_NOT_SUPPORTED => 'HTTP Version Not Supported', - ]; + /** + * 获取状态码对应的消息(使用状态码) + * + * @param int $code 状态码 + * @return string|null 状态消息,不存在则返回null + */ + public static function getMessageForCode(int $code): ?string + { + return self::tryFrom($code)?->getMessage(); + } } diff --git a/src/Server/Connection.php b/src/Server/Connection.php index 92bab49..33cb506 100644 --- a/src/Server/Connection.php +++ b/src/Server/Connection.php @@ -329,7 +329,7 @@ private function handlePostRequest(string $body): void if (!isset($this->server['HTTP_CONTENT_LENGTH'])) { throw new RuntimeException('Content-Length is not set 1'); } - $this->contentLength = intval($this->server['HTTP_CONTENT_LENGTH']); + $this->contentLength = (int)$this->server['HTTP_CONTENT_LENGTH']; if (str_contains($contentType, 'multipart/form-data')) { $this->handleMultipartFormData($body, $contentType); } else {