diff --git a/composer.json b/composer.json index 362d9630..5d0f767b 100644 --- a/composer.json +++ b/composer.json @@ -35,9 +35,7 @@ "autoload": { "psr-4": { "Kiri\\": "kiri-engine/", - "Http\\Message\\": "http-message/", - "Http\\Coroutine\\": "http-coroutine/", - "Http\\Handler\\": "http-handler/", + "Http\\": "http-core/", "Server\\": "http-server/", "Gii\\": "kiri-gii/", "Annotation\\": "kiri-note/" diff --git a/http-handler/Abstracts/BaseContext.php b/http-handler/Abstracts/BaseContext.php deleted file mode 100644 index 78f00ef6..00000000 --- a/http-handler/Abstracts/BaseContext.php +++ /dev/null @@ -1,13 +0,0 @@ -middlewares) || !isset($this->middlewares[$this->offset])) { - return $this->dispatcher($request); - } - - $middleware = $this->middlewares[$this->offset]; - if (!($middleware instanceof MiddlewareInterface)) { - throw new Exception('get_implements_class($middleware) not found method process.'); - } - - $this->offset++; - - return $middleware->process($request, $this); - } - - - /** - * @param ServerRequestInterface $request - * @return mixed - * @throws Exception - */ - public function dispatcher(ServerRequestInterface $request): mixed - { - $response = call_user_func($this->handler->callback, ...$this->handler->params); - if (!($response instanceof ResponseInterface)) { - $response = $this->transferToResponse($response); - } - $response->withHeader('Run-Time', $this->_runTime($request)); - return $response; - } - - - /** - * @param ServerRequest $request - * @return float - */ - private function _runTime(ServerRequestInterface $request): float - { - $float = microtime(true) - time(); - - $serverParams = $request->getServerParams(); - - $rTime = $serverParams['request_time_float'] - $serverParams['request_time']; - - return round($float - $rTime, 6); - } - - - /** - * @param mixed $responseData - * @return \Server\Constrict\ResponseInterface - * @throws Exception - */ - private function transferToResponse(mixed $responseData): ResponseInterface - { - $interface = response()->withStatus(200); - if (!$interface->hasContentType()) { - $interface->withContentType('application/json;charset=utf-8'); - } - if (str_contains($interface->getContentType(), 'xml')) { - if (is_object($responseData)) { - $responseData = get_object_vars($responseData); - } - $interface->getBody()->write(Help::toXml($responseData)); - } else if (is_array($responseData)) { - $interface->getBody()->write(json_encode($responseData)); - } else { - $interface->getBody()->write((string)$responseData); - } - return $interface; - } - - -} diff --git a/http-handler/Abstracts/HandlerManager.php b/http-handler/Abstracts/HandlerManager.php deleted file mode 100644 index 742cedee..00000000 --- a/http-handler/Abstracts/HandlerManager.php +++ /dev/null @@ -1,70 +0,0 @@ - $handlers) { - $array[] = [ - 'path' => $path, - 'method' => implode(',', array_keys($handlers)) - ]; - } - return $array; - } - -} diff --git a/http-handler/Abstracts/HttpService.php b/http-handler/Abstracts/HttpService.php deleted file mode 100644 index dc026ae4..00000000 --- a/http-handler/Abstracts/HttpService.php +++ /dev/null @@ -1,52 +0,0 @@ -getLogger(); - $logger->write($message, $category); - } - - /** - * @param $name - * @return mixed - * @throws Exception - */ - public function __get($name): mixed - { - if (method_exists($this, $name)) { - return $this->{$name}(); - } - $handler = 'get' . ucfirst($name); - if (method_exists($this, $handler)) { - return $this->{$handler}(); - } - if (property_exists($this, $name)) { - return $this->$name; - } - $message = sprintf('method %s::%s not exists.', static::class, $name); - throw new Exception($message); - } - -} diff --git a/http-handler/Abstracts/Middleware.php b/http-handler/Abstracts/Middleware.php deleted file mode 100644 index 0ef5e1d5..00000000 --- a/http-handler/Abstracts/Middleware.php +++ /dev/null @@ -1,20 +0,0 @@ - - */ - private static array $_middlewares = []; - - - /** - * @param $class - * @param $method - * @param array|string|null $middlewares - * @return bool - */ - public static function add($class, $method, array|string|null $middlewares): bool - { - [$class, $method] = static::setDefault($class, $method); - if (empty($middlewares)) { - return false; - } - if (is_string($middlewares)) { - $middlewares = [$middlewares]; - } - $source = &static::$_middlewares[$class][$method]; - foreach ($middlewares as $middleware) { - $middleware = di($middleware); - if (in_array($middleware, $source)) { - continue; - } - $source[] = $middleware; - } - return true; - } - - - /** - * @param $class - * @param $method - * @return array - */ - private static function setDefault($class, $method): array - { - if (is_object($class)) { - $class = $class::class; - } - if (!isset(static::$_middlewares[$class])) { - static::$_middlewares[$class] = []; - } - if (!isset(static::$_middlewares[$class][$method])) { - static::$_middlewares[$class][$method] = []; - } - return [$class, $method]; - } - - - /** - * @param $handler - * @return Iterator|null - */ - public static function get($handler): ?array - { - if (!($handler instanceof Closure)) { - return static::$_middlewares[$handler[0]][$handler[1]] ?? null; - } - return null; - } - - -} diff --git a/http-handler/Annotation/ControllerTarget.php b/http-handler/Annotation/ControllerTarget.php deleted file mode 100644 index 8fe601af..00000000 --- a/http-handler/Annotation/ControllerTarget.php +++ /dev/null @@ -1,9 +0,0 @@ -getAccessControlRequestMethod(); - $allowHeaders = $request->getAccessControlAllowHeaders(); - - if (empty($requestMethod)) $requestMethod = '*'; - if (empty($allowHeaders)) $allowHeaders = '*'; - - $this->response->withAccessControlAllowOrigin('*')->withAccessControlRequestMethod($requestMethod) - ->withAccessControlAllowHeaders($allowHeaders); - - return $handler->handle($request); - } - -} diff --git a/http-handler/DataGrip.php b/http-handler/DataGrip.php deleted file mode 100644 index 9d3aaf66..00000000 --- a/http-handler/DataGrip.php +++ /dev/null @@ -1,10 +0,0 @@ -execute($request); - } -} diff --git a/http-handler/Formatter/FileFormatter.php b/http-handler/Formatter/FileFormatter.php deleted file mode 100644 index b7a59678..00000000 --- a/http-handler/Formatter/FileFormatter.php +++ /dev/null @@ -1,50 +0,0 @@ -data = $context; - return $this; - } - - /** - * @return mixed - */ - public function getData(): mixed - { - $data = $this->data; - $this->clear(); - return $data; - } - - - public function clear(): void - { - $this->data = null; - unset($this->data); - } -} diff --git a/http-handler/Formatter/HtmlFormatter.php b/http-handler/Formatter/HtmlFormatter.php deleted file mode 100644 index cf7bc317..00000000 --- a/http-handler/Formatter/HtmlFormatter.php +++ /dev/null @@ -1,61 +0,0 @@ -data = $context; - return $this; - } - - /** - * @return mixed - */ - public function getData(): mixed - { - $data = $this->data; - $this->clear(); - return $data; - } - - public function clear(): void - { - $this->data = null; - unset($this->data); - } -} diff --git a/http-handler/Formatter/IFormatter.php b/http-handler/Formatter/IFormatter.php deleted file mode 100644 index 9d3a2702..00000000 --- a/http-handler/Formatter/IFormatter.php +++ /dev/null @@ -1,33 +0,0 @@ -data = $context; - return $this; - } - - /** - * @return mixed - */ - public function getData(): mixed - { - $data = $this->data; - $this->clear(); - return $data; - } - - - public function clear(): void - { - $this->data = null; - unset($this->data); - } -} diff --git a/http-handler/Formatter/XmlFormatter.php b/http-handler/Formatter/XmlFormatter.php deleted file mode 100644 index b010cc00..00000000 --- a/http-handler/Formatter/XmlFormatter.php +++ /dev/null @@ -1,89 +0,0 @@ -'); - - $this->toXml($dom, $context); - - $this->data = $dom->saveXML(); - } - return $this; - } - - /** - * @return string|null - */ - public function getData(): ?string - { - $data = $this->data; - $this->clear(); - return $data; - } - - /** - * @param SimpleXMLElement $dom - * @param $data - */ - public function toXml(SimpleXMLElement $dom, $data) - { - foreach ($data as $key => $val) { - if (is_numeric($key)) { - $key = 'item' . $key; - } - if (is_array($val)) { - $node = $dom->addChild($key); - $this->toXml($node, $val); - } else if (is_object($val)) { - $val = get_object_vars($val); - $node = $dom->addChild($key); - $this->toXml($node, $val); - } else { - $dom->addChild($key, htmlspecialchars((string)$val)); - } - } - } - - public function clear(): void - { - $this->data = null; - unset($this->data); - } -} diff --git a/http-handler/Handler.php b/http-handler/Handler.php deleted file mode 100644 index fdc6f67a..00000000 --- a/http-handler/Handler.php +++ /dev/null @@ -1,94 +0,0 @@ -route = $route; - - $this->_injectParams($callback); - - $this->callback = $callback; - - $dispatcher = Kiri::getDi()->get(EventProvider::class); - $dispatcher->on(OnAfterWorkerStart::class, function () { - if ($this->callback instanceof Closure) { - return; - } - $this->_middlewares = MiddlewareManager::get($this->callback); - - $aspect = NoteManager::getSpecify_annotation(Aspect::class, $this->callback[0], $this->callback[1]); - - $this->callback[0] = Kiri::getDi()->get($this->callback[0]); - if (!is_null($aspect)) { - $this->recover($aspect); - } - }); - } - - - /** - * @param Aspect $aspect - */ - public function recover(Aspect $aspect) - { - $aspect = Kiri::getDi()->get($aspect->aspect); - if (empty($aspect)) { - return; - } - $callback = $this->callback; - $params = $this->params; - - $this->params = []; - $this->callback = static function () use ($aspect, $callback, $params) { - $aspect->before(); - $result = $aspect->invoke($callback, $params); - $aspect->after($result); - return $result; - }; - } - - - /** - * @param array|Closure $callback - * @throws \ReflectionException - */ - private function _injectParams(array|Closure $callback) - { - $container = Kiri::getDi(); - if (!($callback instanceof Closure)) { - $this->params = $container->getMethodParameters($callback[0], $callback[1]); - } else { - $this->params = $container->getFunctionParameters($callback); - } - } -} diff --git a/http-handler/Pipeline.php b/http-handler/Pipeline.php deleted file mode 100644 index 7a74c389..00000000 --- a/http-handler/Pipeline.php +++ /dev/null @@ -1,179 +0,0 @@ -passable = $passable; - return $this; - } - - - /** - * @param $middle - * @return $this - */ - public function overall($middle): static - { - $this->overall = $middle; - return $this; - } - - - /** - * 调用栈 - * @param $pipes - * @return $this - */ - public function through($pipes): static - { - if (empty($pipes)) return $this; - if (empty($this->pipes)) { - $this->pipes = is_array($pipes) ? $pipes : func_get_args(); - } else { - foreach ($pipes as $pipe) { - $this->pipes[] = $pipe; - } - } - return $this; - } - - /** - * 执行 - * @param callable $destination - * @return static - */ - public function then(callable $destination): static - { - $parameters = $this->passable; - if (!empty($this->overall)) { - array_unshift($this->pipes, $this->overall); - } - if (is_array($destination)) { - $destination = $this->aspect_caller($destination, $parameters); - } - $this->pipeline = array_reduce(array_reverse($this->pipes), $this->carry(), - static function () use ($destination, $parameters) { - return call_user_func($destination, ...$parameters); - } - ); - return $this->clear(); - } - - - /** - * @return $this - */ - private function clear(): static - { - $this->pipes = []; - $this->passable = null; - $this->overall = null; - return $this; - } - - - /** - * @param $destination - * @param $parameters - * @return Closure|array - */ - private function aspect_caller($destination, $parameters): Closure|array - { - [$controller, $action] = $destination; - /** @var Aspect $aop */ - $aop = NoteManager::getSpecify_annotation(Aspect::class, $controller::class, $action); - if (!empty($aop)) { - $aop = Kiri::getDi()->get($aop->aspect); - $destination = static function () use ($aop, $destination, $parameters) { - /** @var IAspect $aop */ - $aop->before(); - $aop->after($data = $aop->invoke($destination, $parameters)); - return $data; - }; - } - return $destination; - } - - - /** - * @param $request - * @return mixed - */ - public function interpreter($request): mixed - { - return call_user_func($this->pipeline, $request); - } - - - /** - * 设置异常处理器 - * @param callable $handler - * @return $this - */ - public function whenException(callable $handler): static - { - $this->exceptionHandler = $handler; - return $this; - } - - - /** - * @return Closure - */ - protected function carry(): Closure - { - return static function ($stack, $pipe) { - return static function ($passable) use ($stack, $pipe) { - if ($pipe instanceof MiddlewareInterface) { - $pipe = [$pipe, 'process']; - } - return $pipe($passable, $stack); - }; - }; - } - - /** - * 异常处理 - * @param $passable - * @param Throwable $e - * @return mixed - * @throws Throwable - */ - protected function handleException($passable, Throwable $e): mixed - { - if ($this->exceptionHandler) { - return call_user_func($this->exceptionHandler, $passable, $e); - } - throw $e; - } - -} diff --git a/http-handler/Router.php b/http-handler/Router.php deleted file mode 100644 index 416d2bca..00000000 --- a/http-handler/Router.php +++ /dev/null @@ -1,263 +0,0 @@ -get(Router::class); - $router->addRoute('SOCKET', $route, $handler); - } - - - /** - * @param $route - * @param $handler - * @return void - * @throws - */ - public static function post($route, $handler): void - { - $router = Kiri::getDi()->get(Router::class); - $router->addRoute('POST', $route, $handler); - } - - /** - * @param $route - * @param $handler - * @return void - * @throws - */ - public static function get($route, $handler): void - { - $router = Kiri::getDi()->get(Router::class); - $router->addRoute('GET', $route, $handler); - } - - - /** - * @param $route - * @param $handler - * @return void - * @throws - */ - public static function options($route, $handler): void - { - $router = Kiri::getDi()->get(Router::class); - $router->addRoute('OPTIONS', $route, $handler); - } - - - /** - * @param $route - * @param $handler - * @throws - */ - public static function any($route, $handler): void - { - $router = Kiri::getDi()->get(Router::class); - foreach ($router->methods as $method) { - $router->addRoute($method, $route, $handler); - } - } - - /** - * @param $route - * @param $handler - * @return void - * @throws - */ - public static function delete($route, $handler): void - { - $router = Kiri::getDi()->get(Router::class); - $router->addRoute('DELETE', $route, $handler); - } - - - /** - * @param $route - * @param $handler - * @return void - * @throws Exception - */ - public static function head($route, $handler): void - { - $router = Kiri::getDi()->get(Router::class); - $router->addRoute('HEAD', $route, $handler); - } - - - /** - * @param $route - * @param $handler - * @return void - * @throws - */ - public static function put($route, $handler): void - { - $router = Kiri::getDi()->get(Router::class); - $router->addRoute('PUT', $route, $handler); - } - - - /** - * @param string|array $method - * @param string $route - * @param string|Closure $closure - * @throws \ReflectionException - */ - public function addRoute(string|array $method, string $route, string|Closure $closure) - { - if (!is_array($method)) $method = [$method]; - $route = $this->getPath($route); - if (is_string($closure)) { - $closure = explode('@', $closure); - $closure[0] = $this->addNamespace($closure[0]); - if (!class_exists($closure[0])) { - return; - } - $this->addMiddlewares(...$closure); - } - foreach ($method as $value) { - HandlerManager::add($route, $value, new Handler($route, $closure)); - } - } - - - /** - * @param array $config - * @param Closure $closure - */ - public static function group(array $config, Closure $closure) - { - $router = Kiri::getDi()->get(Router::class); - - array_push($router->groupTack, $config); - - call_user_func($closure, $router); - - array_pop($router->groupTack); - } - - - /** - * @param string $route - * @return string - */ - protected function getPath(string $route): string - { - $route = ltrim($route, '/'); - $prefix = array_column($this->groupTack, 'prefix'); - if (empty($prefix = array_filter($prefix))) { - return '/' . $route; - } - return '/' . implode('/', $prefix) . '/' . $route; - } - - - /** - * @param $controller - * @param $method - */ - protected function addMiddlewares($controller, $method) - { - $middleware = array_column($this->groupTack, 'middleware'); - if (empty($middleware = array_filter($middleware))) { - return; - } - foreach ($middleware as $value) { - MiddlewareManager::add($controller, $method, $value); - } - } - - - /** - * @param $class - * @return string|null - */ - protected function addNamespace($class): ?string - { - $middleware = array_column($this->groupTack, 'namespace'); - if (empty($middleware = array_filter($middleware))) { - return $class; - } - $middleware[] = $class; - return implode('\\', array_map(function ($value) { - return trim($value, '\\'); - }, $middleware)); - } - - - /** - * @throws Exception - */ - public function read_files() - { - $this->loadRouteDir(APP_PATH . 'routes'); - } - - - /** - * @param $path - * @throws Exception - * 加载目录下的路由文件 - */ - private function loadRouteDir($path) - { - $files = glob($path . '/*'); - for ($i = 0; $i < count($files); $i++) { - if (is_dir($files[$i])) { - $this->loadRouteDir($files[$i]); - } else { - $this->loadRouterFile($files[$i]); - } - } - } - - - /** - * @param $files - * @throws Exception - */ - private function loadRouterFile($files) - { - try { - include_once "$files"; - } catch (Throwable $exception) { - di(Logger::class)->error('router', [ - $exception->getMessage(), - $exception->getFile(), - $exception->getLine(), - ]); - } finally { - if (isset($exception)) { - unset($exception); - } - } - } - - -} diff --git a/http-message/ContentType.php b/http-message/ContentType.php deleted file mode 100644 index a3a3ce23..00000000 --- a/http-message/ContentType.php +++ /dev/null @@ -1,372 +0,0 @@ -version; - } - - - /** - * @param $version - * @return static - */ - public function withProtocolVersion($version): static - { - $this->version = $version; - return $this; - } - - /** - * @return array - */ - public function getHeaders(): array - { - return $this->headers; - } - - - /** - * @param $name - * @return bool - */ - public function hasHeader($name): bool - { - return array_key_exists($name, $this->headers); - } - - - /** - * @param $name - * @return string|array|null - */ - #[Pure] public function getHeader($name): string|null|array - { - if (!$this->hasHeader($name)) { - return null; - } - return $this->headers[$name]; - } - - - /** - * @return array - */ - public function parse_curl_header(): array - { - $_headers = []; - foreach ($this->headers as $key => $val) { - $_headers[] = $key . ': ' . implode(';', $val); - } - return $_headers; - } - - - /** - * @throws \Exception - */ - public function withData(string $headerString): static - { - [$headers, $body] = explode("\r\n\r\n", $headerString); - - $this->stream = new Stream($body); - - return $this->slip_headers($headers); - } - - - /** - * @param $headers - * @return $this - * @throws \Exception - */ - private function slip_headers($headers): static - { - $headers = explode("\r\n", $headers); - - $this->resolve_status(array_shift($headers)); - - foreach ($headers as $header) { - [$key, $value] = explode(': ', $header); - $this->withHeader($key, $value); - } - return $this; - } - - - /** - * @param string $protocol - */ - private function resolve_status(string $protocol) - { - if ($this instanceof ResponseInterface) { - [$sch, $status, $message] = explode(' ', $protocol); - [$sch, $protocolVersion] = explode('/', $sch); - $this->withProtocolVersion($protocolVersion) - ->withStatus(intval($status)); - } - } - - - /** - * @param $key - * @param $value - */ - private function addRequestHeader($key, $value) - { - $this->headers[$key] = [$value]; - } - - - /** - * @param $name - * @return string|null - */ - #[Pure] public function getHeaderLine($name): string|null - { - if ($this->hasHeader($name)) { - return implode(';', $this->headers[$name]); - } - return null; - } - - - /** - * @return string|null - */ - #[Pure] public function getContentType(): ?string - { - return $this->getHeaderLine('Content-Type'); - } - - - /** - * @param $name - * @param $value - * @return static - */ - public function withHeader($name, $value): static - { - if (!is_array($value)) { - $value = [$value]; - } - $this->headers[$name] = $value; - return $this; - } - - - /** - * @param array $headers - * @return static - */ - public function withHeaders(array $headers): static - { - $this->headers = $headers; - return $this; - } - - - /** - * @param $name - * @param $value - * @return static - * @throws - */ - public function withAddedHeader($name, $value): static - { - if (!array_key_exists($name, $this->headers)) { - throw new \Exception('Headers `' . $name . '` not exists.'); - } - $this->headers[$name][] = $value; - return $this; - } - - - /** - * @param $name - * @return static - */ - public function withoutHeader($name): static - { - unset($this->headers[$name]); - return $this; - } - - - /** - * @return null|array - */ - public function getCookieParams(): ?array - { - return $this->cookieParams; - } - - - /** - * @param array|null $cookies - * @return static - */ - public function withCookieParams(?array $cookies): static - { - $this->cookieParams = $cookies; - return $this; - } - - /** - * @return StreamInterface - */ - public function getBody(): StreamInterface - { - return $this->stream; - } - - - /** - * @param StreamInterface $body - * @return static - */ - public function withBody(StreamInterface $body): static - { - $this->stream = $body; - return $this; - } - - - /** - * @return string|null - */ - #[Pure] public function getAccessControlAllowOrigin(): ?string - { - return $this->getHeaderLine('Access-Control-Allow-Origin'); - } - - - /** - * @return string|null - */ - #[Pure] public function getAccessControlAllowHeaders(): ?string - { - return $this->getHeaderLine('Access-Control-Allow-Headers'); - } - - - /** - * @return string|null - */ - #[Pure] public function getAccessControlRequestMethod(): ?string - { - return $this->getHeaderLine('Access-Control-Request-Method'); - } - - - protected function setStore($key, callable $callback) - { - - } - -} diff --git a/http-message/OnDownload.php b/http-message/OnDownload.php deleted file mode 100644 index 5a447a9b..00000000 --- a/http-message/OnDownload.php +++ /dev/null @@ -1,105 +0,0 @@ - 'image/png', - 'jpeg' => 'image/jpeg', - 'gif' => 'image/gif', - 'bmp' => 'image/bmp', - 'ico' => 'image/vnd.microsoft.icon', - 'tiff' => 'image/tiff', - 'svg' => 'image/svg+xml', - ]; - - - /** - * @param string $path - * @param false $isChunk - * @param int $size - * @param int $offset - * @return $this - */ - public function path(string $path, bool $isChunk = false, int $size = -1, int $offset = 0): OnDownload - { - $this->path = $path; - $this->isChunk = $isChunk; - $this->size = $size; - $this->offset = $offset; - return $this->emitter(); - } - - - /** - * @return $this - */ - public function emitter(): static - { - $explode = explode('/', $this->path); - $this->withHeader('Pragma', 'public'); - $this->withHeader('Expires', '0'); - $this->withHeader('Cache-Control', 'must-revalidate, post-check=0, pre-check=0'); - $this->withHeader('Content-Disposition', 'attachment;filename=' . end($explode)); - $this->withHeader('Content-Type', $type = get_file_extension($this->path)); - if (!in_array($type, self::IMAGES)) { - $this->withHeader('Content-Transfer-Encoding', 'binary'); - } - if ($this->isChunk) { - $resource = fopen($this->path, 'r'); - - $state = fstat($resource); - - $this->withHeader('Content-length', $state['size']); - } - return $this; - } - - - /** - * @param \Swoole\Http\Response $response - */ - public function dispatch(mixed $response) - { - if (!$this->isChunk) { - $response->sendfile($this->path); - } else { - $this->chunk($response); - } - } - - - /** - * @param \Swoole\Http\Response $response - */ - private function chunk(\Swoole\Http\Response $response): void - { - $resource = fopen($this->path, 'r'); - - $state = fstat($resource); - - $offset = $this->offset; - while ($file = fread($resource, $this->size)) { - $response->write($file); - fseek($resource, $offset); - if ($offset >= $state['size']) { - break; - } - $offset += $this->size; - } - $response->end(); - } -} diff --git a/http-message/Parse.php b/http-message/Parse.php deleted file mode 100644 index 90b91274..00000000 --- a/http-message/Parse.php +++ /dev/null @@ -1,35 +0,0 @@ - Xml::toArray($content), - '[', '{' => json_decode($content, true), - default => call_user_func(function () use ($content) { - parse_str($content, $array); - return $array; - }) - }; - } - -} diff --git a/http-message/Request.php b/http-message/Request.php deleted file mode 100644 index 7f198052..00000000 --- a/http-message/Request.php +++ /dev/null @@ -1,115 +0,0 @@ -authority = $authIdentity; - } - - - /** - * @return string - */ - public function getRequestTarget(): string - { - throw new BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @param mixed $requestTarget - * @return static - */ - public function withRequestTarget($requestTarget): static - { - throw new BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @return string - */ - public function getMethod(): string - { - return $this->method; - } - - - /** - * @param string $method - * @return RequestInterface - */ - public function withMethod($method): RequestInterface - { - $this->method = $method; - return $this; - } - - - /** - * @param string $method - * @return bool - */ - public function isMethod(string $method): bool - { - return $this->method == $method; - } - - - /** - * @return UriInterface - */ - public function getUri(): UriInterface - { - return $this->uriInterface; - } - - - /** - * @param UriInterface $uri - * @param false $preserveHost - * @return $this|Request - */ - public function withUri(UriInterface $uri, $preserveHost = false): RequestInterface - { - $this->uriInterface = $uri; - return $this; - } -} diff --git a/http-message/Response.php b/http-message/Response.php deleted file mode 100644 index 78bce7f1..00000000 --- a/http-message/Response.php +++ /dev/null @@ -1,222 +0,0 @@ -stream = new Stream(); - } - - - /** - * @return int - */ - public function getStatusCode(): int - { - return $this->statusCode; - } - - - /** - * @param int $code - * @param string $reasonPhrase - * @return $this|Response - */ - public function withStatus($code, $reasonPhrase = ''): static - { - $this->statusCode = $code; - $this->reasonPhrase = $reasonPhrase; - return $this; - } - - - /** - * @return string - */ - public function getReasonPhrase(): string - { - return $this->reasonPhrase; - } - - - /** - * @return string|null - */ - #[Pure] public function getAccessControlAllowOrigin(): ?string - { - return $this->getHeaderLine('Access-Control-Allow-Origin'); - } - - - /** - * @return string|null - */ - #[Pure] public function getAccessControlAllowHeaders(): ?string - { - return $this->getHeaderLine('Access-Control-Allow-Headers'); - } - - - /** - * @return string|null - */ - #[Pure] public function getAccessControlRequestMethod(): ?string - { - return $this->getHeaderLine('Access-Control-Request-Method'); - } - - - /** - * @param string $type - * @return Response - */ - public function withContentType(string $type): static - { - return $this->withHeader('Content-Type', $type); - } - - - /** - * @return bool - */ - #[Pure] public function hasContentType(): bool - { - return $this->hasHeader('Content-Type'); - } - - /** - * @param string|null $value - * @return Response - */ - public function withAccessControlAllowHeaders(?string $value): static - { - return $this->withHeader('Access-Control-Allow-Headers', $value); - } - - - /** - * @param string|null $value - * @return Response - */ - public function withAccessControlRequestMethod(?string $value): static - { - return $this->withHeader('Access-Control-Request-Method', $value); - } - - - /** - * @param string|null $value - * @return Response - */ - public function withAccessControlAllowOrigin(?string $value): static - { - return $this->withHeader('Access-Control-Allow-Origin', $value); - } - - - /** - * @param $data - * @param string $contentType - * @return static - */ - public function json($data, string $contentType = 'application/json'): static - { - $this->stream->write(json_encode($data)); - - return $this->withContentType($contentType); - } - - - /** - * @param $data - * @param string $contentType - * @return static - */ - public function html($data, string $contentType = 'text/html'): static - { - if (!is_string($data)) { - $data = json_encode($data); - } - - $this->stream->write((string)$data); - - return $this->withContentType($contentType); - } - - - /** - * @param $data - * @param string $contentType - * @return static - */ - public function xml($data, string $contentType = 'application/xml'): static - { - $this->stream->write(Help::toXml($data)); - - return $this->withContentType($contentType); - } - - - /** - * @param string $charset - * @return $this - */ - public function withCharset(string $charset): static - { - $type = explode('charset', $this->getContentType())[0]; - $this->withContentType( - rtrim($type,';') . ';charset=' . $charset - ); - return $this; - } - - - /** - * @param $path - * @param bool $isChunk - * @param int $size - * @param int $offset - * @return OnDownloadInterface - * @throws Exception - */ - public function file($path, bool $isChunk = false, int $size = -1, int $offset = 0): OnDownloadInterface - { - $path = realpath($path); - if (!file_exists($path) || !is_readable($path)) { - throw new Exception('Cannot read file "' . $path . '", no permission'); - } - return (new OnDownload())->path($path, $isChunk, $size, $offset); - } -} diff --git a/http-message/ServerRequest.php b/http-message/ServerRequest.php deleted file mode 100644 index 46b7076a..00000000 --- a/http-message/ServerRequest.php +++ /dev/null @@ -1,208 +0,0 @@ -serverParams = $server; - return $this; - } - - /** - * @param \Swoole\Http\Request $server - * @return static - */ - public function withServerTarget(\Swoole\Http\Request $server): static - { - $this->serverTarget = $server; - return $this; - } - - - /** - * @param \Swoole\Http\Request $request - * @return static|ServerRequestInterface - * @throws \Exception - */ - public static function createServerRequest(\Swoole\Http\Request $request): static|ServerRequestInterface - { - $serverRequest = new ServerRequest(); - $serverRequest->withData($request->getData()); - $serverRequest->withServerParams($request->server); - $serverRequest->withServerTarget($request); - $serverRequest->withCookieParams($request->cookie); - $serverRequest->withUri(Uri::parseUri($request)); - $serverRequest->withQueryParams($request->get ?? []); - $serverRequest->withUploadedFiles($request->files ?? []); - $serverRequest->withMethod($request->getMethod()); - $serverRequest->withParsedBody($request->post); - return $serverRequest; - } - - - /** - * @return null|array - */ - public function getServerParams(): ?array - { - return $this->serverParams; - } - - - /** - * @return array|null - */ - public function getQueryParams(): ?array - { - return $this->queryParams; - } - - - /** - * @param array $query - * @return ServerRequestInterface - */ - public function withQueryParams(array $query): ServerRequestInterface - { - $this->queryParams = $query; - return $this; - } - - - /** - * @return array|null - */ - public function getUploadedFiles(): ?array - { - return $this->uploadedFiles; - } - - - /** - * @param array $uploadedFiles - * @return ServerRequestInterface - */ - public function withUploadedFiles(array $uploadedFiles): ServerRequestInterface - { - $this->uploadedFiles = $uploadedFiles; - return $this; - } - - - /** - * @return array|object|null - */ - public function getParsedBody(): object|array|null - { - if (empty($this->parsedBody)) { - $callback = Context::getContext(self::PARSE_BODY); - - $this->parsedBody = $callback($this->getBody(), $this->serverTarget->post); - } - return $this->parsedBody; - } - - - /** - * @param array|object|null $data - * @return ServerRequestInterface - */ - public function withParsedBody($data): ServerRequestInterface - { - $functions = function (StreamInterface $stream) use ($data) { - $content = Parse::data($stream->getContents()); - if (!empty($content)) { - return $content; - } - return $data; - }; - Context::setContext(self::PARSE_BODY, $functions); - return $this; - } - - - /** - * @return array - */ - public function getAttributes(): array - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @param string $name - * @param null $default - * @return mixed - */ - public function getAttribute($name, $default = null): mixed - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @param string $name - * @param mixed $value - * @return ServerRequestInterface - */ - public function withAttribute($name, $value): ServerRequestInterface - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @param string $name - * @return ServerRequestInterface - */ - public function withoutAttribute($name): ServerRequestInterface - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } -} diff --git a/http-message/StatusCode.php b/http-message/StatusCode.php deleted file mode 100644 index 858168f4..00000000 --- a/http-message/StatusCode.php +++ /dev/null @@ -1,93 +0,0 @@ - 'Continue 初始的请求已经接受,客户应当继续发送请求的其余部分。(HTTP 1.1新)', - self::CODE_101 => 'Switching Protocols 服务器将遵从客户的请求转换到另外一种协议(HTTP 1.1新)', - self::CODE_200 => '(成功) 服务器已成功处理了请求。 通常,这表示服务器提供了请求的网页。', - self::CODE_201 => '(已创建) 请求成功并且服务器创建了新的资源。', - self::CODE_202 => '(已接受) 服务器已接受请求,但尚未处理。', - self::CODE_203 => '(非授权信息) 服务器已成功处理了请求,但返回的信息可能来自另一来源。', - self::CODE_204 => '(无内容) 服务器成功处理了请求,但没有返回任何内容。', - self::CODE_205 => '(重置内容) 服务器成功处理了请求,但没有返回任何内容。', - self::CODE_206 => '(部分内容) 服务器成功处理了部分 GET 请求。', - self::CODE_300 => '(多种选择) 针对请求,服务器可执行多种操作。 服务器可根据请求者 (user agent) 选择一项操作,或提供操作列表供请求者选择。', - self::CODE_301 => '(永久移动) 请求的网页已永久移动到新位置。 服务器返回此响应(对 GET 或 HEAD 请求的响应)时,会自动将请求者转到新位置。', - self::CODE_302 => '(临时移动) 服务器目前从不同位置的网页响应请求,但请求者应继续使用原有位置来进行以后的请求。', - self::CODE_303 => '(查看其他位置) 请求者应当对不同的位置使用单独的 GET 请求来检索响应时,服务器返回此代码。', - self::CODE_304 => '(未修改) 自从上次请求后,请求的网页未修改过。 服务器返回此响应时,不会返回网页内容。', - self::CODE_305 => '(使用代理) 请求者只能使用代理访问请求的网页。 如果服务器返回此响应,还表示请求者应使用代理。', - self::CODE_307 => '(临时重定向) 服务器目前从不同位置的网页响应请求,但请求者应继续使用原有位置来进行以后的请求。', - self::CODE_400 => '(错误请求) 服务器不理解请求的语法。', - self::CODE_401 => '(未授权) 请求要求身份验证。 对于需要登录的网页,服务器可能返回此响应。', - self::CODE_403 => '(禁止) 服务器拒绝请求。', - self::CODE_404 => '(未找到) 服务器找不到请求的网页。', - self::CODE_405 => '(方法禁用) 禁用请求中指定的方法。', - self::CODE_406 => '(不接受) 无法使用请求的内容特性响应请求的网页。', - self::CODE_407 => '(需要代理授权) 此状态代码与 401(未授权)类似,但指定请求者应当授权使用代理。', - self::CODE_408 => '(请求超时) 服务器等候请求时发生超时。', - self::CODE_409 => '(冲突) 服务器在完成请求时发生冲突。 服务器必须在响应中包含有关冲突的信息。', - self::CODE_410 => '(已删除) 如果请求的资源已永久删除,服务器就会返回此响应。', - self::CODE_411 => '(需要有效长度) 服务器不接受不含有效内容长度标头字段的请求。', - self::CODE_412 => '(未满足前提条件) 服务器未满足请求者在请求中设置的其中一个前提条件。', - self::CODE_413 => '(请求实体过大) 服务器无法处理请求,因为请求实体过大,超出服务器的处理能力。', - self::CODE_414 => '(请求的 URI 过长) 请求的 URI(通常为网址)过长,服务器无法处理。', - self::CODE_415 => '(不支持的媒体类型) 请求的格式不受请求页面的支持。', - self::CODE_416 => '(请求范围不符合要求) 如果页面无法提供请求的范围,则服务器会返回此状态代码。', - self::CODE_417 => '(未满足期望值) 服务器未满足"期望"请求标头字段的要求。', - self::CODE_423 => ' 锁定的错误。', - self::CODE_500 => '(服务器内部错误) 服务器遇到错误,无法完成请求。', - self::CODE_501 => '(尚未实施) 服务器不具备完成请求的功能。 例如,服务器无法识别请求方法时可能会返回此代码。', - self::CODE_502 => '(错误网关) 服务器作为网关或代理,从上游服务器收到无效响应。', - self::CODE_503 => '(服务不可用) 服务器目前无法使用(由于超载或停机维护)。 通常,这只是暂时状态。', - self::CODE_504 => '(网关超时) 服务器作为网关或代理,但是没有及时从上游服务器收到请求。', - self::CODE_505 => '(HTTP 版本不受支持) 服务器不支持请求中所用的 HTTP 协议版本。', - ]; - -} diff --git a/http-message/Stream.php b/http-message/Stream.php deleted file mode 100644 index 11bd1a92..00000000 --- a/http-message/Stream.php +++ /dev/null @@ -1,237 +0,0 @@ -content = $stream; - if (!is_resource($stream)) { - $this->size = strlen($stream); - } else { - $state = fstat($this->content); - if ($state) { - $this->size = $state['size']; - } - } - } - - - /** - * @return string - */ - public function __toString() - { - return $this->content; - } - - - /** - * - */ - public function close() - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @return resource|null - */ - public function detach() - { - if (!is_resource($this->content)) { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - $steam = stream_context_create(); - stream_copy_to_stream($this->content, $steam); - return $steam; - } - - - /** - * @return int - */ - public function getSize(): int - { - return $this->size; - } - - - /** - * @return bool|int - */ - public function tell(): bool|int - { - if (!is_resource($this->content)) { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - return ftell($this->content); - } - - - /** - * @return bool - */ - public function eof(): bool - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @return bool - */ - public function isSeekable(): bool - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @param int $offset - * @param int $whence - */ - public function seek($offset, $whence = SEEK_SET) - { - if (!is_resource($this->content)) { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - fseek($this->content, $offset, $whence); - } - - - /** - * - */ - public function rewind() - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @return bool - */ - public function isWritable(): bool - { - if (!is_resource($this->content)) { - return true; - } - if (is_writable($this->content)) { - return true; - } - return false; - } - - - /** - * @param string $string - * @return int - */ - public function write($string): int - { - if (is_resource($this->content)) { - fwrite($this->content, $string); - $state = fstat($this->content); - if ($state) { - $this->size = $state['size']; - } - } else { - $this->content = $string; - $this->size = strlen($string); - } - return $this->size; - } - - - /** - * @return bool - */ - public function isReadable(): bool - { - if (!is_resource($this->content)) { - return true; - } - if (is_readable($this->content)) { - return true; - } - return false; - } - - - /** - * @param int $length - * @return false|string - */ - public function read($length): bool|string - { - if (is_resource($this->content)) { - return fread($this->content, $length); - } else { - return $this->content; - } - } - - - /** - * @return string|bool - */ - public function getContents(): string|bool - { - if (is_resource($this->content)) { - return stream_get_contents($this->content); - } else { - return $this->content; - } - } - - - /** - * @param null $key - * @return array - */ - #[ArrayShape([ - "timed_out" => "bool", - "blocked" => "bool", - "eof" => "bool", - "unread_bytes" => "int", - "stream_type" => "string", - "wrapper_type" => "string", - "wrapper_data" => "mixed", - "mode" => "string", - "seekable" => "bool", - "uri" => "string", - "crypto" => "array", - "mediatype" => "string", - ])] - public function getMetadata($key = null): array - { - if (is_resource($this->content)) { - return stream_get_meta_data($this->content); - } - throw new \BadMethodCallException('Not Accomplish Method.'); - } -} diff --git a/http-message/Uploaded.php b/http-message/Uploaded.php deleted file mode 100644 index 4d434ee4..00000000 --- a/http-message/Uploaded.php +++ /dev/null @@ -1,118 +0,0 @@ - "There is no error, the file uploaded with success", - 1 => "The uploaded file exceeds the upload_max_filesize directive in php.ini", - 2 => "The uploaded file exceeds the MAX_FILE_SIZE directive that was specified in the HTML form", - 3 => "The uploaded file was only partially uploaded", - 4 => "No file was uploaded", - 6 => "Missing a temporary folder" - ]; - - - /** - * @var resource - */ - private mixed $stream; - - - /** - * @param string $tmp_name - * @param string $name - * @param string $type - * @param int $size - * @param int $error - */ - public function __construct( - public string $tmp_name, - public string $name, - public string $type, - public int $size, - public int $error - ) - { - } - - - /** - * @return StreamInterface - * @throws Exception - */ - public function getStream(): StreamInterface - { - if ($this->stream instanceof Stream) { - return $this->stream; - } - - $this->stream = new Stream(fopen($this->tmp_name, 'r+')); - - return $this->stream; - } - - - /** - * @param string $targetPath - * @return StreamInterface - * @throws Exception - */ - public function moveTo($targetPath): StreamInterface - { - @move_uploaded_file($this->tmp_name, $targetPath); - if (!file_exists($targetPath)) { - throw new Exception('File save fail.'); - } - - if ($this->stream instanceof Stream) { - $this->stream->close(); - $this->stream = null; - } - - $this->tmp_name = $targetPath; - return $this->getStream(); - } - - - /** - * @return int - */ - public function getSize(): int - { - return $this->size; - } - - /** - * @return int - */ - public function getError(): int - { - return $this->error; - } - - - /** - * @return string - */ - public function getClientFilename(): string - { - return $this->name; - } - - - /** - * @return string - */ - public function getClientMediaType(): string - { - return $this->type; - } -} diff --git a/http-message/Uri.php b/http-message/Uri.php deleted file mode 100644 index 68e610a0..00000000 --- a/http-message/Uri.php +++ /dev/null @@ -1,256 +0,0 @@ -scheme; - } - - - /** - * @return string - */ - public function getAuthority(): string - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @return string - */ - public function getUserInfo(): string - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - /** - * @return string - */ - public function getHost(): string - { - return $this->host; - } - - - /** - * @return int|null - */ - public function getPort(): ?int - { - return $this->port; - } - - - /** - * @return string - */ - public function getPath(): string - { - return $this->path; - } - - - /** - * @return string - */ - public function getQuery(): string - { - return $this->queryString; - } - - - /** - * @return string - */ - public function getFragment(): string - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @param string $scheme - * @return $this|Uri - */ - public function withScheme($scheme): UriInterface - { - $this->scheme = $scheme; - return $this; - } - - - /** - * @param string $user - * @param null $password - * @return Uri - */ - public function withUserInfo($user, $password = null): UriInterface - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @param string $host - * @return $this|Uri - */ - public function withHost($host): UriInterface - { - $this->host = $host; - return $this; - } - - - /** - * @param int|null $port - * @return $this|Uri - */ - public function withPort($port): UriInterface - { - $this->port = $port; - return $this; - } - - - /** - * @param string $path - * @return $this|Uri - */ - public function withPath($path): UriInterface - { - $this->path = $path; - return $this; - } - - - /** - * @param string $query - * @return $this|Uri - */ - public function withQuery($query): UriInterface - { - $this->queryString = $query; - return $this; - } - - - /** - * @param string $fragment - * @return Uri - */ - public function withFragment($fragment): UriInterface - { - throw new \BadMethodCallException('Not Accomplish Method.'); - } - - - /** - * @return string - */ - public function __toString(): string - { - $domain = sprintf('%s://%s', $this->scheme, $this->host); - if (!in_array($this->port, [80, 443])) { - $domain .= ':' . $this->port; - } - if (empty($this->query) && empty($this->fragment)) { - return $domain . $this->path; - } - return sprintf('%s?%s#%s', $domain . $this->path, - $this->queryString, $this->fragment); - } - - - /** - * @return int - */ - public function getDefaultPort(): int - { - return $this->scheme == 'https' ? 443 : 80; - } - - - /** - * @param Request $request - * @return UriInterface - */ - public static function parseUri(Request $request): UriInterface - { - $server = $request->server; - $header = $request->header; - $uri = new static(); - $uri = $uri->withScheme(!empty($server['https']) && $server['https'] !== 'off' ? 'https' : 'http'); - if (isset($request->header['x-forwarded-proto'])) { - $uri->withScheme($request->header['x-forwarded-proto'])->withPort(443); - } - - $hasPort = false; - if (isset($server['http_host'])) { - $hostHeaderParts = explode(':', $server['http_host']); - $uri = $uri->withHost($hostHeaderParts[0]); - if (isset($hostHeaderParts[1])) { - $hasPort = true; - $uri = $uri->withPort($hostHeaderParts[1]); - } - } elseif (isset($server['server_name'])) { - $uri = $uri->withHost($server['server_name']); - } elseif (isset($server['server_addr'])) { - $uri = $uri->withHost($server['server_addr']); - } elseif (isset($header['host'])) { - $hasPort = true; - if (strpos($header['host'], ':')) { - [$host, $port] = explode(':', $header['host'], 2); - if ($port != $uri->getDefaultPort()) { - $uri = $uri->withPort($port); - } - } else { - $host = $header['host']; - } - - $uri = $uri->withHost($host); - } - - if (!$hasPort && isset($server['server_port'])) { - $uri = $uri->withPort($server['server_port']); - } - - $hasQuery = false; - if (isset($server['request_uri'])) { - $requestUriParts = explode('?', $server['request_uri']); - $uri = $uri->withPath($requestUriParts[0]); - if (isset($requestUriParts[1])) { - $hasQuery = true; - $uri = $uri->withQuery($requestUriParts[1]); - } - } - - if (!$hasQuery && isset($server['query_string'])) { - $uri = $uri->withQuery($server['query_string']); - } - - return $uri; - } -} diff --git a/http-server/Abstracts/PageNotFoundException.php b/http-server/Abstracts/PageNotFoundException.php deleted file mode 100644 index 09b99498..00000000 --- a/http-server/Abstracts/PageNotFoundException.php +++ /dev/null @@ -1,23 +0,0 @@ -HTTP 404 Not Found