call a successful route? public $success = false; # Variable: $controller # The Route's Controller. public $controller; /** * Function: __construct * Parse the URL and to determine what to do. * * Parameters: * $controller - The controller to use. */ private function __construct($controller) { $this->controller = $controller; $config = Config::current(); if (substr_count($_SERVER['REQUEST_URI'], "..") > 0 ) exit("GTFO."); elseif (isset($_GET['action']) and preg_match("/[^(\w+)]/", $_GET['action'])) exit("Nope!"); $this->action =& $_GET['action']; if (isset($_GET['feed'])) $this->feed = true; # Parse the current URL and extract information. $parse = parse_url($config->url); fallback($parse["path"], "/"); if (isset($controller->base)) $parse["path"] = trim($parse["path"], "/")."/".trim($controller->base, "/")."/"; $this->safe_path = str_replace("/", "\\/", $parse["path"]); $this->request = $parse["path"] == "/" ? $_SERVER['REQUEST_URI'] : preg_replace("/{$this->safe_path}?/", "", $_SERVER['REQUEST_URI'], 1) ; $this->arg = array_map("urldecode", explode("/", trim($this->request, "/"))); if (substr_count($this->arg[0], "?") > 0 and !preg_match("/\?\w+/", $this->arg[0])) exit("No-Go!"); if (method_exists($controller, "parse")) $controller->parse($this); Trigger::current()->call("parse_url", $this); $this->try[] = isset($this->action) ? oneof($this->action, "index") : (!substr_count($this->arg[0], "?") ? oneof(@$this->arg[0], "index") : "index") ; # Guess the action initially. # This is only required because of the view_site permission; # it has to know if they're viewing /login, in which case # it should allow the page to display. fallback($this->action, end($this->try)); } /** * Function: init * Attempt Controller actions until one of them doesn't return false. * * This will also call the @[controllername]_xxxxx@ and @route_xxxxx@ triggers. */ public function init() { $trigger = Trigger::current(); $trigger->call("route_init", $this); $try = $this->try; if (isset($this->action)) array_unshift($try, $this->action); $count = 0; foreach ($try as $key => $val) { if (is_numeric($key)) list($method, $args) = array($val, array()); else list($method, $args) = array($key, $val); $this->action = $method; $name = strtolower(str_replace("Controller", "", get_class($this->controller))); if ($trigger->exists($name."_".$method) or $trigger->exists("route_".$method)) $call = $trigger->call(array($name."_".$method, "route_".$method), $this->controller); else $call = false; if ($call !== true and method_exists($this->controller, $method)) $response = call_user_func_array(array($this->controller, $method), $args); else $response = false; if ($response !== false or $call !== false) { $this->success = true; break; } if (++$count == count($try) and isset($this->controller->fallback) and method_exists($this->controller, "display")) call_user_func_array(array($this->controller, "display"), $this->controller->fallback); } if ($this->action != "login" and $this->success) $_SESSION['redirect_to'] = self_url(); $trigger->call("route_done", $this); return true; } /** * Function: url * Attempts to change the specified clean URL to a dirty URL if clean URLs is disabled. * Use this for linking to things. The applicable URL conversions are passed through the * parse_urls trigger. * * Parameters: * $url - The clean URL. * $use_chyrp_url - Use @Config.chyrp_url@ instead of @Config.url@, when the @$url@ begins with "/"? * * Returns: * A clean or dirty URL, depending on @Config.clean_urls@. */ public function url($url, $controller = null) { $config = Config::current(); if ($url[0] == "/") return (ADMIN ? $config->chyrp_url.$url : $config->url.$url); else $url = substr($url, -1) == "/" ? $url : $url."/" ; fallback($controller, $this->controller); $base = !empty($controller->base) ? $config->url."/".$controller->base : $config->url ; if ($config->clean_urls) { # If their post URL doesn't have a trailing slash, remove it from these as well. if (substr($url, 0, 5) == "page/") # Different URL for viewing a page $url = substr($url, 5); return (substr($config->post_url, -1) == "/" or $url == "search/") ? $base."/".$url : $base."/".rtrim($url, "/") ; } $urls = fallback($controller->urls, array()); Trigger::current()->filter($urls, "parse_urls"); foreach (array_diff_assoc($urls, $controller->urls) as $key => $value) $urls[substr($key, 0, -1).preg_quote("feed/", $key[0]).$key[0]] = "/".$value."&feed"; $urls["|/([^/]+)/$|"] = "/?action=$1"; return $base.fix(preg_replace(array_keys($urls), array_values($urls), "/".$url, 1)); } /** * Function: add * Adds a route to Chyrp. Only needed for actions that have more than one parameter. * For example, for /tags/ you won't need to do this, but you will for /tag/tag-name/. * * Parameters: * $path - The path to add. Wrap variables with parentheses, e.g. "tag/(name)/". * $action - The action the path points to. * * See Also: * */ public function add($path, $action) { $config = Config::current(); $new_routes = $config->routes; $new_routes[$path] = $action; $config->set("routes", $new_routes); } /** * Function: remove * Removes a route added by . * * Parameters: * $path - The path to remove. * * See Also: * */ public function remove($path) { $config = Config::current(); unset($config->routes[$path]); $config->set("routes", $config->routes); } /** * Function: current * Returns a singleton reference to the current class. */ public static function & current($controller = null) { static $instance = null; if (!isset($controller) and empty($instance)) error(__("Error"), __("Route was initiated without a Controller."), debug_backtrace()); return $instance = (empty($instance)) ? new self($controller) : $instance ; } }