You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

105 lines
2.7 KiB

  1. <?php
  2. /**
  3. * Класс для работы с роутерами
  4. *
  5. */
  6. final class Router
  7. {
  8. protected $routes = array();
  9. /**
  10. * Добавить роутер
  11. *
  12. * @param string $name - имя роутера
  13. * @param string $path - путь
  14. * @param string $action - имя действия
  15. * @param array $params - массив параметров
  16. */
  17. function add($name, $path, $action, $params = array())
  18. {
  19. $this->routes[$name] = new Route($path, $action, $params);
  20. }
  21. /**
  22. * Установить декоратор для роута (действия), отличный от стандартного
  23. *
  24. * @param string $name - имя роута (действия)
  25. * @param string $decorator - имя декоратора
  26. */
  27. function setDecorator($name, $decorator)
  28. {
  29. if (isset($this->routes[$name])) {
  30. $this->routes[$name]->decorator = $decorator.DECORATOR_POSTFIX;
  31. }
  32. }
  33. /**
  34. * Найти роутер соответствующий заданному пути
  35. *
  36. * @param stirng $path - путь
  37. * @return Route - роутер
  38. */
  39. function proccess($path)
  40. {
  41. $path = explode('/', $path);
  42. foreach ($this->routes as $name => $route) {
  43. if ($route->match($path)) {
  44. $route->action .= ACTION_POSTFIX;
  45. Env::setParams($route->params);
  46. return $route;
  47. }
  48. }
  49. throw new Exception(E_404);
  50. }
  51. }
  52. /**
  53. * Роутер
  54. *
  55. */
  56. final class Route
  57. {
  58. const URL_VARIABLE = '&';
  59. protected $path;
  60. public $decorator = DEFAULT_DECORATOR;
  61. public $action;
  62. public $params;
  63. function __construct($path, $action, $params=array())
  64. {
  65. $this->path = $path;
  66. $this->action = $action;
  67. $this->params = $params;
  68. }
  69. /**
  70. * Проверяет соответствие роутера и пути
  71. *
  72. * @param string $path - путь для сравнения
  73. * @return boolean - соответствует или нет
  74. */
  75. function match($path_arr)
  76. {
  77. $parts = explode('/', $this->path);
  78. $cnt = count($parts);
  79. if (end($parts) == self::URL_VARIABLE) {
  80. $cnt--;
  81. } elseif ($cnt != count($path_arr)) {
  82. return false;
  83. }
  84. for ($i=0; $i<$cnt; $i++) {
  85. if (substr($parts[$i], 0, 1) == self::URL_VARIABLE) {
  86. $this->params[substr($parts[$i], 1)] = $path_arr[$i];
  87. } elseif ($parts[$i] != $path_arr[$i]) {
  88. return false;
  89. }
  90. }
  91. return true;
  92. }
  93. }
  94. ?>