summaryrefslogtreecommitdiff
path: root/kohana/libraries/Router.php
diff options
context:
space:
mode:
authorBharat Mediratta <bharat@menalto.com>2008-10-31 22:12:14 +0000
committerBharat Mediratta <bharat@menalto.com>2008-10-31 22:12:14 +0000
commiteba717f95f586d2538007bd18da6e9b32b076c30 (patch)
tree15fc596a270f9de0d163c66c96e3c65fca5ee100 /kohana/libraries/Router.php
parentfff10f8b70376ef25722bd867df26bc5aefced43 (diff)
Merge over vendor code.
git-svn-id: http://gallery.svn.sourceforge.net/svnroot/gallery/trunk/eval/gx/gallery3/trunk@18408 57fcd75e-5312-0410-8df3-f5eb6fbb1595
Diffstat (limited to 'kohana/libraries/Router.php')
-rw-r--r--kohana/libraries/Router.php313
1 files changed, 313 insertions, 0 deletions
diff --git a/kohana/libraries/Router.php b/kohana/libraries/Router.php
new file mode 100644
index 00000000..09e45c03
--- /dev/null
+++ b/kohana/libraries/Router.php
@@ -0,0 +1,313 @@
+<?php defined('SYSPATH') or die('No direct script access.');
+/**
+ * Router
+ *
+ * $Id$
+ *
+ * @package Core
+ * @author Kohana Team
+ * @copyright (c) 2007-2008 Kohana Team
+ * @license http://kohanaphp.com/license.html
+ */
+class Router_Core {
+
+ protected static $routes;
+
+ public static $current_uri = '';
+ public static $query_string = '';
+ public static $complete_uri = '';
+ public static $routed_uri = '';
+ public static $url_suffix = '';
+
+ public static $segments;
+ public static $rsegments;
+
+ public static $controller;
+ public static $controller_path;
+
+ public static $method = 'index';
+ public static $arguments = array();
+
+ /**
+ * Router setup routine. Automatically called during Kohana setup process.
+ *
+ * @return void
+ */
+ public static function setup()
+ {
+ if ( ! empty($_SERVER['QUERY_STRING']))
+ {
+ // Set the query string to the current query string
+ self::$query_string = '?'.trim($_SERVER['QUERY_STRING'], '&/');
+ }
+
+ if (self::$routes === NULL)
+ {
+ // Load routes
+ self::$routes = Kohana::config('routes');
+ }
+
+ // Default route status
+ $default_route = FALSE;
+
+ if (self::$current_uri === '')
+ {
+ // Make sure the default route is set
+ if ( ! isset(self::$routes['_default']))
+ throw new Kohana_Exception('core.no_default_route');
+
+ // Use the default route when no segments exist
+ self::$current_uri = self::$routes['_default'];
+
+ // Default route is in use
+ $default_route = TRUE;
+ }
+
+ // Make sure the URL is not tainted with HTML characters
+ self::$current_uri = html::specialchars(self::$current_uri, FALSE);
+
+ // Remove all dot-paths from the URI, they are not valid
+ self::$current_uri = preg_replace('#\.[\s./]*/#', '', self::$current_uri);
+
+ // At this point segments, rsegments, and current URI are all the same
+ self::$segments = self::$rsegments = self::$current_uri = trim(self::$current_uri, '/');
+
+ // Set the complete URI
+ self::$complete_uri = self::$current_uri.self::$query_string;
+
+ // Explode the segments by slashes
+ self::$segments = ($default_route === TRUE OR self::$segments === '') ? array() : explode('/', self::$segments);
+
+ if ($default_route === FALSE AND count(self::$routes) > 1)
+ {
+ // Custom routing
+ self::$rsegments = self::routed_uri(self::$current_uri);
+ }
+
+ // The routed URI is now complete
+ self::$routed_uri = self::$rsegments;
+
+ // Routed segments will never be empty
+ self::$rsegments = explode('/', self::$rsegments);
+
+ // Prepare to find the controller
+ $controller_path = '';
+ $method_segment = NULL;
+
+ // Paths to search
+ $paths = Kohana::include_paths();
+
+ foreach (self::$rsegments as $key => $segment)
+ {
+ // Add the segment to the search path
+ $controller_path .= $segment;
+
+ $found = FALSE;
+ foreach ($paths as $dir)
+ {
+ // Search within controllers only
+ $dir .= 'controllers/';
+
+ if (is_dir($dir.$controller_path) OR is_file($dir.$controller_path.EXT))
+ {
+ // Valid path
+ $found = TRUE;
+
+ // The controller must be a file that exists with the search path
+ if ($c = str_replace('\\', '/', realpath($dir.$controller_path.EXT))
+ AND is_file($c) AND strpos($c, $dir) === 0)
+ {
+ // Set controller name
+ self::$controller = $segment;
+
+ // Change controller path
+ self::$controller_path = $c;
+
+ // Set the method segment
+ $method_segment = $key + 1;
+
+ // Stop searching
+ break;
+ }
+ }
+ }
+
+ if ($found === FALSE)
+ {
+ // Maximum depth has been reached, stop searching
+ break;
+ }
+
+ // Add another slash
+ $controller_path .= '/';
+ }
+
+ if ($method_segment !== NULL AND isset(self::$rsegments[$method_segment]))
+ {
+ // Set method
+ self::$method = self::$rsegments[$method_segment];
+
+ if (isset(self::$rsegments[$method_segment + 1]))
+ {
+ // Set arguments
+ self::$arguments = array_slice(self::$rsegments, $method_segment + 1);
+ }
+ }
+
+ // Last chance to set routing before a 404 is triggered
+ Event::run('system.post_routing');
+
+ if (self::$controller === NULL)
+ {
+ // No controller was found, so no page can be rendered
+ Event::run('system.404');
+ }
+ }
+
+ /**
+ * Attempts to determine the current URI using CLI, GET, PATH_INFO, ORIG_PATH_INFO, or PHP_SELF.
+ *
+ * @return void
+ */
+ public static function find_uri()
+ {
+ if (PHP_SAPI === 'cli')
+ {
+ // Command line requires a bit of hacking
+ if (isset($_SERVER['argv'][1]))
+ {
+ self::$current_uri = $_SERVER['argv'][1];
+
+ // Remove GET string from segments
+ if (($query = strpos(self::$current_uri, '?')) !== FALSE)
+ {
+ list (self::$current_uri, $query) = explode('?', self::$current_uri, 2);
+
+ // Parse the query string into $_GET
+ parse_str($query, $_GET);
+
+ // Convert $_GET to UTF-8
+ $_GET = utf8::clean($_GET);
+ }
+ }
+ }
+ elseif (current($_GET) === '' AND substr($_SERVER['QUERY_STRING'], -1) !== '=')
+ {
+ // The URI is the array key, eg: ?this/is/the/uri
+ self::$current_uri = key($_GET);
+
+ // Remove the URI from $_GET
+ unset($_GET[self::$current_uri]);
+
+ // Remove the URI from $_SERVER['QUERY_STRING']
+ $_SERVER['QUERY_STRING'] = ltrim(substr($_SERVER['QUERY_STRING'], strlen(self::$current_uri)), '/&');
+
+ // Fixes really strange handling of a suffix in a GET string
+ if ($suffix = Kohana::config('core.url_suffix') AND substr(self::$current_uri, -(strlen($suffix))) === '_'.substr($suffix, 1))
+ {
+ self::$current_uri = substr(self::$current_uri, 0, -(strlen($suffix)));
+ }
+ }
+ elseif (isset($_SERVER['PATH_INFO']) AND $_SERVER['PATH_INFO'])
+ {
+ self::$current_uri = $_SERVER['PATH_INFO'];
+ }
+ elseif (isset($_SERVER['ORIG_PATH_INFO']) AND $_SERVER['ORIG_PATH_INFO'])
+ {
+ self::$current_uri = $_SERVER['ORIG_PATH_INFO'];
+ }
+ elseif (isset($_SERVER['PHP_SELF']) AND $_SERVER['PHP_SELF'])
+ {
+ self::$current_uri = $_SERVER['PHP_SELF'];
+ }
+
+ // The front controller directory and filename
+ $fc = substr(realpath($_SERVER['SCRIPT_FILENAME']), strlen(DOCROOT));
+
+ if (($strpos_fc = strpos(self::$current_uri, $fc)) !== FALSE)
+ {
+ // Remove the front controller from the current uri
+ self::$current_uri = substr(self::$current_uri, $strpos_fc + strlen($fc));
+ }
+
+ // Remove slashes from the start and end of the URI
+ self::$current_uri = trim(self::$current_uri, '/');
+
+ if (self::$current_uri !== '')
+ {
+ if ($suffix = Kohana::config('core.url_suffix') AND strpos(self::$current_uri, $suffix) !== FALSE)
+ {
+ // Remove the URL suffix
+ self::$current_uri = preg_replace('#'.preg_quote($suffix).'$#u', '', self::$current_uri);
+
+ // Set the URL suffix
+ self::$url_suffix = $suffix;
+ }
+
+ // Reduce multiple slashes into single slashes
+ self::$current_uri = preg_replace('#//+#', '/', self::$current_uri);
+ }
+ }
+
+ /**
+ * Generates routed URI from given URI.
+ *
+ * @param string URI to convert
+ * @return string Routed uri
+ */
+ public static function routed_uri($uri)
+ {
+ if (self::$routes === NULL)
+ {
+ // Load routes
+ self::$routes = Kohana::config('routes');
+ }
+
+ // Prepare variables
+ $routed_uri = $uri = trim($uri, '/');
+
+ if (isset(self::$routes[$uri]))
+ {
+ // Literal match, no need for regex
+ $routed_uri = self::$routes[$uri];
+ }
+ else
+ {
+ // Loop through the routes and see if anything matches
+ foreach (self::$routes as $key => $val)
+ {
+ if ($key === '_default') continue;
+
+ // Trim slashes
+ $key = trim($key, '/');
+ $val = trim($val, '/');
+
+ if (preg_match('#^'.$key.'$#u', $uri))
+ {
+ if (strpos($val, '$') !== FALSE)
+ {
+ // Use regex routing
+ $routed_uri = preg_replace('#^'.$key.'$#u', $val, $uri);
+ }
+ else
+ {
+ // Standard routing
+ $routed_uri = $val;
+ }
+
+ // A valid route has been found
+ break;
+ }
+ }
+ }
+
+ if (isset(self::$routes[$routed_uri]))
+ {
+ // Check for double routing (without regex)
+ $routed_uri = self::$routes[$routed_uri];
+ }
+
+ return trim($routed_uri, '/');
+ }
+
+} // End Router \ No newline at end of file