%PDF- %PDF-
Direktori : /home/lightco1/www/lightingrepublic.com.au/libraries/koowa/http/ |
Current File : /home/lightco1/www/lightingrepublic.com.au/libraries/koowa/http/url.php |
<?php /** * @version $Id$ * @package Koowa_Http * @copyright Copyright (C) 2007 - 2012 Johan Janssens. All rights reserved. * @license GNU GPLv3 <http://www.gnu.org/licenses/gpl.html> * @link http://www.nooku.org */ /** * HTTP Url Class * * This class helps you to create and manipulate urls, including query * strings and path elements. It does so by splitting up the pieces of the * url and allowing you modify them individually; you can then then fetch * them as a single url string. This helps when building complex links, * such as in a paged navigation system. * * The following is a simple example. Say that the page address is currently * `http://anonymous::guest@example.com/path/to/index.php/foo/bar?baz=dib#anchor`. * * You can use KHttpUrl to parse this complex string very easily: * * <code> * <?php * // Create a url object; * * $url = 'http://anonymous:guest@example.com/path/to/index.php/foo/bar.xml?baz=dib#anchor' * $url = KService::get('koowa:http.url', array('url' => $url) ); * * // the $ur properties are ... * // * // $url->scheme => 'http' * // $url->host => 'example.com' * // $url->user => 'anonymous' * // $url->pass => 'guest' * // $url->path => array('path', 'to', 'index.php', 'foo', 'bar') * // $url->format => 'xml' * // $url->query => array('baz' => 'dib') * // $url->fragment => 'anchor' * ?> * </code> * * Now that we have imported the url and had it parsed automatically, we * can modify the component parts, then fetch a new url string. * * <code> * <?php * // change to 'https://' * $url->scheme = 'https'; * * // remove the username and password * $url->user = ''; * $url->pass = ''; * * // change the value of 'baz' to 'zab' * $url->setQuery('baz', 'zab'); * * // add a new query element called 'zim' with a value of 'gir' * $url->query['zim'] = 'gir'; * * // reset the path to something else entirely. * // this will additionally set the format to 'php'. * $url->setPath('/something/else/entirely.php'); * * // add another path element * $url->path[] = 'another'; * * // and fetch it to a string. * $new_url = $url->get(); * * // the $new_url string is as follows; notice how the format * // is always applied to the last path-element. * // /something/else/entirely/another.php?baz=zab&zim=gir#anchor * * // Get the full URL to get the shceme and host * $full_url = $url->get(true); * * // the $full_url string is: * // https://example.com/something/else/entirely/another.php?baz=zab&zim=gir#anchor * ?> * </code> * * @author Johan Janssens <johan@nooku.org> * @category Koowa * @package Koowa_Http */ class KHttpUrl extends KObject { /** * The url parts * * @see get() */ const SCHEME = 1; const USER = 2; const PASS = 4; const HOST = 8; const PORT = 16; const PATH = 32; const FORMAT = 64; const QUERY = 128; const FRAGMENT = 256; const AUTH = 6; const AUTHORITY = 31; const BASE = 127; const FULL = 511; /** * The scheme [http|https|ftp|mailto|...] * * @var string */ public $scheme = ''; /** * The host specification (for example, 'example.com'). * * @var string */ public $host = ''; /** * The port number (for example, '80'). * * @var string */ public $port = ''; /** * The username, if any. * * @var string */ public $user = ''; /** * The password, if any. * * @var string */ public $pass = ''; /** * The path portion (for example, 'path/to/index.php'). * * @var string */ public $path = ''; /** * The dot-format extension of the last path element (for example, the "rss" * in "feed.rss"). * * @var string */ public $format = ''; /** * The query portion (for example baz=dib) * * Public access is allowed via __get() with $query. * * @var array * * @see setQuery() * @see getQuery() */ protected $_query = array(); /** * The fragment aka anchor portion (for example, the "foo" in "#foo"). * * @var string */ public $fragment = ''; /** * Url-encode only these characters in path elements. * * Characters are ' ' (space), '/', '?', '&', and '#'. * * @var array */ protected $_encode_path = array ( ' ' => '+', '/' => '%2F', '?' => '%3F', '&' => '%26', '#' => '%23', ); /** * Constructor * * @param object An optional KConfig object with configuration options */ public function __construct(KConfig $config = null) { //If no config is passed create it if(!isset($config)) $config = new KConfig(); parent::__construct($config); $this->set($config->url); } /** * Initializes the options for the object * * Called from {@link __construct()} as a first step of object instantiation. * * @param object An optional KConfig object with configuration options * @return void */ protected function _initialize(KConfig $config) { $config->append(array( 'url' => '', )); parent::_initialize($config); } /** * Implements the virtual $query property. * * @param string The virtual property to set. * @param string Set the virtual property to this value. */ public function __set($key, $val) { if ($key == 'query') { $this->setQuery($val); } if($key == 'path') { $this->setPath($val); } } /** * Implements access to $_query by reference so that it appears to be * a public $query property. * * @param string The virtual property to return. * @return array The value of the virtual property. */ public function &__get($key) { if ($key == 'query') { return $this->_query; } } /** * Get the full url, of the format scheme://user:pass@host/path?query#fragment'; * * @param integer A bitmask of binary or'ed HTTP_URL constants; FULL is the default * @return string */ public function get($parts = self::FULL) { $url = ''; //Add the scheme if(($parts & self::SCHEME) && !empty($this->scheme)) { $url .= urlencode($this->scheme).'://'; } //Add the username and password if(($parts & self::USER) && !empty($this->user)) { $url .= urlencode($this->user); if(($parts & self::PASS) && !empty($this->pass)) { $url .= ':' . urlencode($this->pass); } $url .= '@'; } // Add the host and port, if any. if(($parts & self::HOST) && !empty($this->host)) { $url .= urlencode($this->host); if(($parts & self::PORT) && !empty($this->port)) { $url .= ':' . (int) $this->port; } } // Add the rest of the url. we use trim() instead of empty() on string // elements to allow for string-zero values. if(($parts & self::PATH) && !empty($this->path)) { $url .= $this->_pathEncode($this->path); if(($parts & self::FORMAT) && trim($this->format) !== '') { $url .= '.' . urlencode($this->format); } } $query = $this->getQuery(); if(($parts & self::QUERY) && !empty($query)) { $url .= '?' . $this->getQuery(); } if(($parts & self::FRAGMENT) && trim($this->fragment) !== '') { $url .= '#' . urlencode($this->fragment); } return $url; } /** * Set the url * * @param string url * @return KHttpUrl */ public function set($url) { if(!empty($url)) { $segments = parse_url($url); foreach ($segments as $key => $value) { $this->$key = $value; } if($this->format = pathinfo($this->path, PATHINFO_EXTENSION)) { $this->path = str_replace('.'.$this->format, '', $this->path); } } return $this; } /** * Sets the query string in the url, for KHttpUrl::getQuery() and KHttpUrl::$query. * * This will overwrite any previous values. * * @param string|array The query string to use; for example `foo=bar&baz=dib`. * @return KHttpUrl */ public function setQuery($query) { if(!is_array($query)) { if(strpos($query, '&') !== false) { $query = str_replace('&','&',$query); } //Set the query vars parse_str($query, $this->_query); } if(is_array($query)) { $this->_query = $query; } return $this; } /** * Returns the query portion as a string or array * * @param boolean If TRUE return an array. Default FALSE * @return string|array The query string; e.g., `foo=bar&baz=dib`. */ public function getQuery($toArray = false) { $result = $toArray ? $this->_query : http_build_query($this->_query, '', '&'); return $result; } /** * Sets the KHttpUrl::$path array and $format from a string. * * This will overwrite any previous values. Also, resets the format based * on the final path value. * * @param string The path string to use; for example,"/foo/bar/baz/dib". * A leading slash will *not* create an empty first element; if the string * has a leading slash, it is ignored. * @return KHttpUrl */ public function setPath($path) { $spec = trim($path, '/'); $this->path = array(); if (! empty($path)) { $this->path = explode('/', $path); } foreach ($this->path as $key => $val) { $this->path[$key] = urldecode($val); } if ($val = end($this->path)) { // find the last dot in the value $pos = strrpos($val, '.'); if ($pos !== false) { $key = key($this->path); $this->format = substr($val, $pos + 1); $this->path[$key] = substr($val, 0, $pos); } } return $this; } /** * Return a string representation of this url. * * @see get() * @return string */ public function __toString() { return $this->get(self::FULL); } /** * Converts an array of path elements into a string. * * Does not use urlencode(); instead, only converts characters found in * KHttpUrl::$_encode_path. * * @param array The path elements. * @return string A url path string. */ protected function _pathEncode($spec) { if (is_string($spec)) { $spec = explode('/', $spec); } $keys = array_keys($this->_encode_path); $vals = array_values($this->_encode_path); $out = array(); foreach ((array) $spec as $elem) { $out[] = str_replace($keys, $vals, $elem); } return implode('/', $out); } }