194 lines
6.8 KiB
PHP
194 lines
6.8 KiB
PHP
<?php
|
||
|
||
// Работа с адресной строкой
|
||
|
||
defined('ROOT_DIR') || exit;
|
||
|
||
trait Router {
|
||
private array $routerList = array();
|
||
private $fun_not_found;
|
||
|
||
// Получить адрес
|
||
public function router_get_uri()
|
||
{
|
||
return parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH);
|
||
}
|
||
|
||
// Регистрация роутера
|
||
public function router_add($page, $func, $methods = array("GET", "POST"))
|
||
{
|
||
$type = 'function';
|
||
if(gettype($func) == 'string') {
|
||
if(substr($func, strlen($func) - strlen(".php")) == ".php") $type = 'template';
|
||
else $type = 'function_name';
|
||
}
|
||
$this->routerList[] = array(
|
||
"page" => $page,
|
||
"func" => &$func,
|
||
"type" => $type,
|
||
"methods" => $methods
|
||
);
|
||
}
|
||
|
||
// Получение списка роутов
|
||
private function router_get_list(): array
|
||
{
|
||
return $this->routerList;
|
||
}
|
||
|
||
// Получить сегменты адреса
|
||
public function router_get_segments()
|
||
{
|
||
$uri = $this->router_get_uri();
|
||
return explode('/', trim($uri, '/'));
|
||
}
|
||
|
||
// Получить сегмент адреса
|
||
public function router_get_segment($segment_num)
|
||
{
|
||
$segments = $this->router_get_segments();
|
||
return $segments[$segment_num];
|
||
}
|
||
|
||
// Определить функцию не найденной страницы
|
||
public function router_set_not_found($fun)
|
||
{
|
||
$this->fun_not_found = &$fun;
|
||
}
|
||
|
||
// Когда страница не найдена
|
||
private function router_not_found()
|
||
{
|
||
http_response_code(404);
|
||
if(empty($this->fun_not_found))
|
||
echo "not found";
|
||
$fun = $this->fun_not_found;
|
||
$fun();
|
||
}
|
||
|
||
// Запускаем сканирование
|
||
public function router_init()
|
||
{
|
||
$uri = $this->router_get_uri();
|
||
$list = $this->router_get_list();
|
||
$method = $this->router_get_method();
|
||
foreach ($list as $key => $item) {
|
||
if(!in_array($method, $item["methods"], true)) continue;
|
||
if(substr($item["page"], -1) == "%"){
|
||
$clear_uri = substr($item["page"], 0, -1);
|
||
if(strpos($uri, $clear_uri) === 0) {
|
||
$this->event_start(base64_encode($item["page"]));
|
||
if($item["type"] == "template")
|
||
return $this->template_load($item["func"], array(), true);
|
||
return $item["func"]();
|
||
}
|
||
} else if ($uri == $item["page"]) {
|
||
$this->event_start(base64_encode($item["page"]));
|
||
if($item["type"] == "template")
|
||
return $this->template_load($item["func"], array(), true);
|
||
return $item["func"]();
|
||
}
|
||
}
|
||
$this->router_not_found();
|
||
return true;
|
||
}
|
||
|
||
// Получить метод запроса
|
||
public function router_get_method(): string
|
||
{
|
||
return strtolower($_SERVER['REQUEST_METHOD']);
|
||
}
|
||
|
||
// Получить текущий протокол
|
||
public function router_get_protocol(): string
|
||
{
|
||
if (
|
||
isset($_SERVER['REQUEST_SCHEME']) &&
|
||
($_SERVER['HTTPS'] == 'on' || $_SERVER['HTTPS'] == 1) ||
|
||
isset($_SERVER['HTTP_X_FORWARDED_PROTO']) &&
|
||
$_SERVER['HTTP_X_FORWARDED_PROTO'] == 'https' ||
|
||
isset($_SERVER['REQUEST_SCHEME']) &&
|
||
$_SERVER['REQUEST_SCHEME'] == "https"
|
||
) return "https";
|
||
return "http";
|
||
}
|
||
|
||
// Получить корневой адрес сайта
|
||
public function router_get_root_uri(): string
|
||
{
|
||
$protocol = $this->router_get_protocol();
|
||
return $protocol . "://" . $_SERVER['HTTP_HOST'];
|
||
}
|
||
|
||
// Получить канонический адрес
|
||
public function router_get_canonical_uri(): string
|
||
{
|
||
$canonical_link = parse_url($_SERVER["REQUEST_URI"], PHP_URL_PATH);
|
||
return $this->router_get_root_uri() . $canonical_link;
|
||
}
|
||
|
||
// Получить полный адрес
|
||
public function router_get_full_uri(): string
|
||
{
|
||
return ((!empty($_SERVER['HTTPS'])) ? 'https' : 'http') . '://' . $_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI'];
|
||
}
|
||
|
||
// Выполнить редирект на другой адрес
|
||
public function router_redirect($path)
|
||
{
|
||
$root = $this->router_get_root_uri();
|
||
header("Location: $root$path");
|
||
}
|
||
|
||
// Выполнить редирект на эту же страницу чтобы очистить POST
|
||
public function router_refresh()
|
||
{
|
||
$current_path = $_SERVER['REQUEST_URI'];
|
||
$this->router_redirect($current_path);
|
||
}
|
||
|
||
// Получить ссылку с измененными GET параметрами
|
||
public function router_format_get_params($params, $split = false, $exclude = array()): string
|
||
{
|
||
$string = "?";
|
||
$params_list = array();
|
||
$params = $this->router_edit_get_params($params, $split, $exclude);
|
||
foreach ($params as $key => $value)
|
||
$params_list[] = $key . "=" . $value;
|
||
return $string . implode("&", $params_list);
|
||
}
|
||
|
||
// Соединить GET параметры со значениями массива
|
||
public function router_edit_get_params($params, $split = false, $exclude = array())
|
||
{
|
||
$current_params = $_GET;
|
||
if($split) $params = array_merge($current_params, $params);
|
||
foreach ($exclude as $key => $value) unset($params[$value]);
|
||
return $params;
|
||
}
|
||
|
||
// Заполнить форму невидимыми полями по переданному массиву
|
||
public function router_params_to_form($params, $exclude = array(), $prefix = "", $nested = false)
|
||
{
|
||
foreach ($params as $key => $value) {
|
||
if(in_array($key, $exclude)) continue;
|
||
if(is_array($value)) {
|
||
if($nested) $this->router_params_to_form($value, $exclude = array(), $prefix . "[". $key . "]", true);
|
||
else $this->router_params_to_form($value, $exclude = array(), $prefix . $key, true);
|
||
continue;
|
||
}
|
||
if($nested) $this->router_get_hidden_input($prefix . "[" . $key . "]", $value, $prefix);
|
||
else $this->router_get_hidden_input($prefix . $key, $value, $prefix);
|
||
}
|
||
}
|
||
|
||
// Добавить невидимое поле на страницу
|
||
private function router_get_hidden_input($name, $value, $prefix = "")
|
||
{
|
||
$meta_dom = new DOM("input", false);
|
||
$meta_dom->setAttribute("type", "hidden");
|
||
$meta_dom->setAttribute("name", $prefix . $this->get_view($name));
|
||
$meta_dom->setAttribute("value", $this->get_view($value));
|
||
$meta_dom->view();
|
||
}
|
||
} |