user = $user; $this->logger = new Logger("Router", $user->getSQL()); $this->routes = []; $this->statusCodeRoutes = []; $this->addRoute(new ApiRoute()); } public function run(string $url): string { // TODO: do we want a global try cache and return status page 500 on any error? // or do we want to have a global status page function here? $url = strtok($url, "?"); foreach ($this->routes as $route) { $pathParams = $route->match($url); if ($pathParams !== false) { return $route->call($this, $pathParams); } } return $this->returnStatusCode(404); } public function returnStatusCode(int $code, array $params = []): string { http_response_code($code); $params["status_code"] = $code; $params["status_description"] = HTTP_STATUS_DESCRIPTIONS[$code] ?? "Unknown Error"; $route = $this->statusCodeRoutes[strval($code)] ?? null; if ($route) { return $route->call($this, $params); } else { $req = new \Api\Template\Render($this->user); $res = $req->execute(["file" => "error_document.twig", "parameters" => $params]); if ($res) { return $req->getResult()["html"]; } else { var_dump($req->getLastError()); $description = htmlspecialchars($params["status_description"]); return "$code - $description"; } } } public function addRoute(AbstractRoute $route) { if (preg_match("/^\d+$/", $route->getPattern())) { $this->statusCodeRoutes[$route->getPattern()] = $route; } else { $this->routes[] = $route; } } public function writeCache(string $file): bool { $routes = ""; foreach ($this->routes as $route) { $constructor = $route->generateCache(); $routes .= "\n \$this->addRoute($constructor);"; } $date = (new \DateTime())->format("Y/m/d H:i:s"); $code = "logger->severe("Could not write Router cache file: $file"); return false; } return true; } public function getUser(): User { return $this->user; } public function getLogger(): Logger { return $this->logger; } public static function cleanURL(string $url, bool $cleanGET = true): string { // strip GET parameters if ($cleanGET) { if (($index = strpos($url, "?")) !== false) { $url = substr($url, 0, $index); } } // strip document reference part if (($index = strpos($url, "#")) !== false) { $url = substr($url, 0, $index); } // strip leading slash return preg_replace("/^\/+/", "", $url); } }