PageRenderTime 42ms CodeModel.GetById 12ms RepoModel.GetById 0ms app.codeStats 0ms

/lib/Controller/PageManager.php

http://github.com/atk4/atk4
PHP | 242 lines | 116 code | 28 blank | 98 comment | 30 complexity | 5c99ae6b26aa57a33bf4c09a93924443 MD5 | raw file
Possible License(s): MPL-2.0-no-copyleft-exception
  1. <?php
  2. /**
  3. * This is a generic page manager. For web applications it calculates
  4. * base URI, sets up path manager with the URI locations, determines
  5. * which page was requested.
  6. *
  7. * This class works with PathFinder, App_Web, and Location.
  8. *
  9. * Terminology:
  10. *
  11. * Project - entirety of your files including shared folders,
  12. * documestation, migrations scripts, support files etc etc.
  13. * Project concept is introduced in Agile Toolkit 4.3
  14. *
  15. * Interface - (such as "admin", "frontend", "cli", "api")
  16. * is located in the project folder and contains interface
  17. * specific pages, librares and templates.
  18. *
  19. * Location - represents a physical location on the filesystem,
  20. * where files can be located either through file access or
  21. * whrough URL access.
  22. *
  23. *
  24. * you can access variabless below through $this->app->pm->base_url
  25. * concatinate them to get full URL
  26. */
  27. class Controller_PageManager extends AbstractController
  28. {
  29. /**
  30. * Base URL defines the absolute destination of our server. Because some
  31. * other resources may be located outside of our Base Path, we need to
  32. * know a Base URL.
  33. *
  34. * For CLI scripts, you need to set this manually. Also if you are
  35. * going to use URLs in emails, you should use this.
  36. *
  37. * See also: URL::useAbsoluteURL();
  38. *
  39. * @var string
  40. */
  41. public $base_url; // http://yoursite.com:81
  42. /**
  43. * Base PATH points to the top location of our project. Basically it's
  44. * where the project is installed in the webroot. This is determined
  45. * by thelocation of catch-all file. It is determined by SCRIPT_NAME
  46. * which should be supported by most web installations. It will also
  47. * work when mod_rewrite is not used.
  48. *
  49. * You can use $base_path in your script to put it say on a logo link
  50. *
  51. * Also - some other parts of the library may have a different path,
  52. * for example base_path could be = /admin/, and atk4_path could be /amodules/
  53. *
  54. * If project is installed in web-root, then $base_path will be "/"
  55. *
  56. * path always starts and ends with slash
  57. *
  58. * @var string
  59. */
  60. public $base_path; // /admin/
  61. /**
  62. * This is a third and a final part of the URLs. This points to a page
  63. * which were reuqested. You can pass path to getDestinationURL() function,
  64. * as a first argument. Also $path is used to determine which page class
  65. * to load.
  66. *
  67. * Page must never start with slash. Also if path is empty, then
  68. * the "index" is used automatically.
  69. *
  70. * @var string
  71. */
  72. public $page; // user/add
  73. /**
  74. * @var string
  75. */
  76. public $template_filename;
  77. // {{{ Inherited properties
  78. /** @var App_Web */
  79. public $app;
  80. // }}}
  81. public function init()
  82. {
  83. parent::init();
  84. $this->app->pm = $this;
  85. // Firstly, the original URL is retrieved. This function should
  86. // take care of all possible rewrite engines and bring up a real
  87. // URL which matches the one in the browser. Also e will need to
  88. // determine a relative path for the requested page
  89. }
  90. public function setURL($url)
  91. {
  92. $url = parse_url($url);
  93. $scheme = isset($url['scheme']) ? $url['scheme'].'://' : '';
  94. $host = isset($url['host']) ? $url['host'] : '';
  95. $port = isset($url['port']) ? ':'.$url['port'] : '';
  96. $user = isset($url['user']) ? $url['user'] : '';
  97. $pass = isset($url['pass']) ? ':'.$url['pass'] : '';
  98. $pass = ($user || $pass) ? "$pass@" : '';
  99. $path = isset($url['path']) ? $url['path'] : '';
  100. if (substr($path, -1) != '/') {
  101. $path .= '/';
  102. }
  103. $this->base_url = $scheme.$user.$pass.$host.$port;
  104. $this->base_path = $path;
  105. $this->app->page = 'index';
  106. return $this;
  107. }
  108. /**
  109. * Detect server environment and tries to guess absolute and relative
  110. * URLs to your application.
  111. *
  112. * See docs: doc/application/routing/parsing
  113. */
  114. public function parseRequestedURL()
  115. {
  116. // This is the re-constructions of teh proper URL.
  117. // 1. Schema
  118. $url = $this->app->getConfig('atk/base_url', null);
  119. if (is_null($url)) {
  120. // Detect it
  121. $url = 'http';
  122. $https = (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] == 'on') || $_SERVER['SERVER_PORT'] == 443;
  123. if ($https) {
  124. $url .= 's';
  125. }
  126. // 2. Continue building. We are adding hostname next and port.
  127. $url .= '://'.$_SERVER['SERVER_NAME'];
  128. //if($_SERVER["SERVER_PORT"]!="80")$url .= ":".$_SERVER['SERVER_PORT'];
  129. if (($_SERVER['SERVER_PORT'] == '80' && !$https) || ($_SERVER['SERVER_PORT'] == '443' && $https)) {
  130. ;
  131. } else {
  132. $url .= ':'.$_SERVER['SERVER_PORT'];
  133. }
  134. }
  135. // We have now arrived at base_url as defined
  136. $this->base_url = $url;
  137. // 3. Next we need a base_part of our URL. There are many different
  138. // variables and approaches we tried it, REDIRECT_URL_ROOT, REDIRECT_URL,
  139. // etc, however most reliable is $this->unix_dirname(SCRIPT_NAME)
  140. $path = $this->unix_dirname($_SERVER['SCRIPT_NAME']);
  141. if (substr($path, -1) != '/') {
  142. $path .= '/';
  143. }
  144. // We have now arrived at base_path as defined
  145. $this->base_path = $path;
  146. // 4. We now look at RequestURI and extract base_path from the beginning
  147. if (isset($_GET['page'])) {
  148. $page = $_GET['page'];
  149. $this->page = $page;
  150. } else {
  151. $request_uri = $this->getRequestURI();
  152. if (strpos($request_uri, $path) !== 0) {
  153. throw $this->exception('URL matching problem')
  154. ->addMoreInfo('RequestURI', $request_uri)
  155. ->addMoreInfo('BasePath', $path);
  156. }
  157. $page = substr($request_uri, strlen($path));
  158. if (!$page) {
  159. $page = 'index';
  160. }
  161. // Preserve actual page
  162. $this->page = $page;
  163. // Remove postfix from page if any
  164. $page = preg_replace('/\..*$/', '', $page);
  165. $page = preg_replace('/\/$/', '', $page);
  166. $page = str_replace('/', '_', $page);
  167. if (substr($page, -1) == '_') {
  168. $page = substr($page, 0, -1);
  169. }
  170. }
  171. if (strpos($page, '.') !== false) {
  172. throw $this->exception('Page may not contain periods (.)')
  173. ->addMoreInfo('page', $page);
  174. }
  175. // We have now arrived at the page as per specification.
  176. $this->app->page = str_replace('/', '_', $page);
  177. $this->template_filename = $this->app->page;
  178. if (substr($this->template_filename, -1) == '/') {
  179. $this->template_filename .= 'index';
  180. }
  181. }
  182. public function debug()
  183. {
  184. $this->debug = true;
  185. parent::debug('base_path='.$this->base_path);
  186. parent::debug('page='.$this->app->page);
  187. parent::debug('template_filename='.$this->template_filename);
  188. }
  189. public function getRequestURI()
  190. {
  191. // WARNING. This function URI excludes query string
  192. if (isset($_SERVER['HTTP_X_REWRITE_URL'])) { // IIS
  193. $request_uri = $_SERVER['HTTP_X_REWRITE_URL'];
  194. } elseif (isset($_SERVER['REQUEST_URI'])) { // Apache
  195. $request_uri = $_SERVER['REQUEST_URI'];
  196. } elseif (isset($_SERVER['ORIG_PATH_INFO'])) { // IIS 5.0, PHP as CGI
  197. $request_uri = $_SERVER['ORIG_PATH_INFO'];
  198. // This one comes without QUERRY string
  199. } else {
  200. throw new BaseException('Unable to determine RequestURI. This shouldn\'t be called at all in CLI');
  201. }
  202. $request_uri = explode('?', $request_uri, 2);
  203. return $request_uri[0];
  204. }
  205. public function unix_dirname($path)
  206. {
  207. $chunks = explode('/', $path);
  208. array_pop($chunks);
  209. if (empty($chunks)) {
  210. return '/';
  211. }
  212. return implode('/', $chunks);
  213. }
  214. }