Blame | Letzte Änderung | Log anzeigen | RSS feed
<?php/* SVN FILE: $Id: basics.php 7945 2008-12-19 02:16:01Z gwoo $ *//*** Basic Cake functionality.** Core functions for including other source files, loading models and so forth.** PHP versions 4 and 5** CakePHP(tm) : Rapid Development Framework (http://www.cakephp.org)* Copyright 2005-2008, Cake Software Foundation, Inc. (http://www.cakefoundation.org)** Licensed under The MIT License* Redistributions of files must retain the above copyright notice.** @filesource* @copyright Copyright 2005-2008, Cake Software Foundation, Inc. (http://www.cakefoundation.org)* @link http://www.cakefoundation.org/projects/info/cakephp CakePHP(tm) Project* @package cake* @subpackage cake.cake* @since CakePHP(tm) v 0.2.9* @version $Revision: 7945 $* @modifiedby $LastChangedBy: gwoo $* @lastmodified $Date: 2008-12-18 18:16:01 -0800 (Thu, 18 Dec 2008) $* @license http://www.opensource.org/licenses/mit-license.php The MIT License*//*** Basic defines for timing functions.*/define('SECOND', 1);define('MINUTE', 60 * SECOND);define('HOUR', 60 * MINUTE);define('DAY', 24 * HOUR);define('WEEK', 7 * DAY);define('MONTH', 30 * DAY);define('YEAR', 365 * DAY);/*** Patch for PHP < 5.0*/if (!function_exists('clone')) {if (version_compare(PHP_VERSION, '5.0') < 0) {eval ('function clone($object){return $object;}');}}/*** Loads configuration files. Receives a set of configuration files* to load.* Example:* <code>* config('config1', 'config2');* </code>** @return boolean Success*/function config() {$args = func_get_args();foreach ($args as $arg) {if ($arg === 'database' && file_exists(CONFIGS . 'database.php')) {include_once(CONFIGS . $arg . '.php');} elseif (file_exists(CONFIGS . $arg . '.php')) {include_once(CONFIGS . $arg . '.php');if (count($args) == 1) {return true;}} else {if (count($args) == 1) {return false;}}}return true;}/*** Loads component/components from LIBS. Takes optional number of parameters.** Example:* <code>* uses('flay', 'time');* </code>** @param string $name Filename without the .php part*/function uses() {$args = func_get_args();foreach ($args as $file) {require_once(LIBS . strtolower($file) . '.php');}}/*** Prints out debug information about given variable.** Only runs if debug level is greater than zero.** @param boolean $var Variable to show debug information for.* @param boolean $showHtml If set to true, the method prints the debug data in a screen-friendly way.* @param boolean $showFrom If set to true, the method prints from where the function was called.* @link http://book.cakephp.org/view/458/Basic-Debugging*/function debug($var = false, $showHtml = false, $showFrom = true) {if (Configure::read() > 0) {if ($showFrom) {$calledFrom = debug_backtrace();echo '<strong>' . substr(str_replace(ROOT, '', $calledFrom[0]['file']), 1) . '</strong>';echo ' (line <strong>' . $calledFrom[0]['line'] . '</strong>)';}echo "\n<pre class=\"cake-debug\">\n";$var = print_r($var, true);if ($showHtml) {$var = str_replace('<', '<', str_replace('>', '>', $var));}echo $var . "\n</pre>\n";}}if (!function_exists('getMicrotime')) {/*** Returns microtime for execution time checking** @return float Microtime*/function getMicrotime() {list($usec, $sec) = explode(' ', microtime());return ((float)$usec + (float)$sec);}}if (!function_exists('sortByKey')) {/*** Sorts given $array by key $sortby.** @param array $array Array to sort* @param string $sortby Sort by this key* @param string $order Sort order asc/desc (ascending or descending).* @param integer $type Type of sorting to perform* @return mixed Sorted array*/function sortByKey(&$array, $sortby, $order = 'asc', $type = SORT_NUMERIC) {if (!is_array($array)) {return null;}foreach ($array as $key => $val) {$sa[$key] = $val[$sortby];}if ($order == 'asc') {asort($sa, $type);} else {arsort($sa, $type);}foreach ($sa as $key => $val) {$out[] = $array[$key];}return $out;}}if (!function_exists('array_combine')) {/*** Combines given identical arrays by using the first array's values as keys,* and the second one's values as values. (Implemented for backwards compatibility with PHP4)** @param array $a1 Array to use for keys* @param array $a2 Array to use for values* @return mixed Outputs either combined array or false.*/function array_combine($a1, $a2) {$a1 = array_values($a1);$a2 = array_values($a2);$c1 = count($a1);$c2 = count($a2);if ($c1 != $c2) {return false;}if ($c1 <= 0) {return false;}$output = array();for ($i = 0; $i < $c1; $i++) {$output[$a1[$i]] = $a2[$i];}return $output;}}/*** Convenience method for htmlspecialchars.** @param string $text Text to wrap through htmlspecialchars* @param string $charset Character set to use when escaping. Defaults to config value in 'App.encoding' or 'UTF-8'* @return string Wrapped text* @link http://book.cakephp.org/view/703/h*/function h($text, $charset = null) {if (is_array($text)) {return array_map('h', $text);}if (empty($charset)) {$charset = Configure::read('App.encoding');}if (empty($charset)) {$charset = 'UTF-8';}return htmlspecialchars($text, ENT_QUOTES, $charset);}/*** Returns an array of all the given parameters.** Example:* <code>* a('a', 'b')* </code>** Would return:* <code>* array('a', 'b')* </code>** @return array Array of given parameters* @link http://book.cakephp.org/view/694/a*/function a() {$args = func_get_args();return $args;}/*** Constructs associative array from pairs of arguments.** Example:* <code>* aa('a','b')* </code>** Would return:* <code>* array('a'=>'b')* </code>** @return array Associative array* @link http://book.cakephp.org/view/695/aa*/function aa() {$args = func_get_args();$argc = count($args);for ($i = 0; $i < $argc; $i++) {if ($i + 1 < $argc) {$a[$args[$i]] = $args[$i + 1];} else {$a[$args[$i]] = null;}$i++;}return $a;}/*** Convenience method for echo().** @param string $text String to echo* @link http://book.cakephp.org/view/700/e*/function e($text) {echo $text;}/*** Convenience method for strtolower().** @param string $str String to lowercase* @return string Lowercased string* @link http://book.cakephp.org/view/705/low*/function low($str) {return strtolower($str);}/*** Convenience method for strtoupper().** @param string $str String to uppercase* @return string Uppercased string* @link http://book.cakephp.org/view/710/up*/function up($str) {return strtoupper($str);}/*** Convenience method for str_replace().** @param string $search String to be replaced* @param string $replace String to insert* @param string $subject String to search* @return string Replaced string* @link http://book.cakephp.org/view/708/r*/function r($search, $replace, $subject) {return str_replace($search, $replace, $subject);}/*** Print_r convenience function, which prints out <PRE> tags around* the output of given array. Similar to debug().** @see debug()* @param array $var Variable to print out* @param boolean $showFrom If set to true, the method prints from where the function was called* @link http://book.cakephp.org/view/707/pr*/function pr($var) {if (Configure::read() > 0) {echo '<pre>';print_r($var);echo '</pre>';}}/*** Display parameters.** @param mixed $p Parameter as string or array* @return string*/function params($p) {if (!is_array($p) || count($p) == 0) {return null;}if (is_array($p[0]) && count($p) == 1) {return $p[0];}return $p;}/*** Merge a group of arrays** @param array First array* @param array Second array* @param array Third array* @param array Etc...* @return array All array parameters merged into one* @link http://book.cakephp.org/view/696/am*/function am() {$r = array();$args = func_get_args();foreach ($args as $a) {if (!is_array($a)) {$a = array($a);}$r = array_merge($r, $a);}return $r;}/*** Gets an environment variable from available sources, and provides emulation* for unsupported or inconsistent environment variables (i.e. DOCUMENT_ROOT on* IIS, or SCRIPT_NAME in CGI mode). Also exposes some additional custom* environment information.** @param string $key Environment variable name.* @return string Environment variable setting.* @link http://book.cakephp.org/view/701/env*/function env($key) {if ($key == 'HTTPS') {if (isset($_SERVER) && !empty($_SERVER)) {return (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on');}return (strpos(env('SCRIPT_URI'), 'https://') === 0);}if ($key == 'SCRIPT_NAME') {if (env('CGI_MODE') && isset($_ENV['SCRIPT_URL'])) {$key = 'SCRIPT_URL';}}$val = null;if (isset($_SERVER[$key])) {$val = $_SERVER[$key];} elseif (isset($_ENV[$key])) {$val = $_ENV[$key];} elseif (getenv($key) !== false) {$val = getenv($key);}if ($key === 'REMOTE_ADDR' && $val === env('SERVER_ADDR')) {$addr = env('HTTP_PC_REMOTE_ADDR');if ($addr !== null) {$val = $addr;}}if ($val !== null) {return $val;}switch ($key) {case 'SCRIPT_FILENAME':if (defined('SERVER_IIS') && SERVER_IIS === true) {return str_replace('\\\\', '\\', env('PATH_TRANSLATED'));}break;case 'DOCUMENT_ROOT':$name = env('SCRIPT_NAME');$filename = env('SCRIPT_FILENAME');$offset = 0;if (!strpos($name, '.php')) {$offset = 4;}return substr($filename, 0, strlen($filename) - (strlen($name) + $offset));break;case 'PHP_SELF':return str_replace(env('DOCUMENT_ROOT'), '', env('SCRIPT_FILENAME'));break;case 'CGI_MODE':return (PHP_SAPI === 'cgi');break;case 'HTTP_BASE':$host = env('HTTP_HOST');if (substr_count($host, '.') !== 1) {return preg_replace('/^([^.])*/i', null, env('HTTP_HOST'));}return '.' . $host;break;}return null;}if (!function_exists('file_put_contents')) {/*** Writes data into file.** If file exists, it will be overwritten. If data is an array, it will be join()ed with an empty string.** @param string $fileName File name.* @param mixed $data String or array.* @return boolean Success*/function file_put_contents($fileName, $data) {if (is_array($data)) {$data = join('', $data);}$res = @fopen($fileName, 'w+b');if ($res) {$write = @fwrite($res, $data);if ($write === false) {return false;} else {@fclose($res);return $write;}}return false;}}/*** Reads/writes temporary data to cache files or session.** @param string $path File path within /tmp to save the file.* @param mixed $data The data to save to the temporary file.* @param mixed $expires A valid strtotime string when the data expires.* @param string $target The target of the cached data; either 'cache' or 'public'.* @return mixed The contents of the temporary file.* @deprecated Please use Cache::write() instead*/function cache($path, $data = null, $expires = '+1 day', $target = 'cache') {if (Configure::read('Cache.disable')) {return null;}$now = time();if (!is_numeric($expires)) {$expires = strtotime($expires, $now);}switch (low($target)) {case 'cache':$filename = CACHE . $path;break;case 'public':$filename = WWW_ROOT . $path;break;case 'tmp':$filename = TMP . $path;break;}$timediff = $expires - $now;$filetime = false;if (file_exists($filename)) {$filetime = @filemtime($filename);}if ($data === null) {if (file_exists($filename) && $filetime !== false) {if ($filetime + $timediff < $now) {@unlink($filename);} else {$data = @file_get_contents($filename);}}} elseif (is_writable(dirname($filename))) {@file_put_contents($filename, $data);}return $data;}/*** Used to delete files in the cache directories, or clear contents of cache directories** @param mixed $params As String name to be searched for deletion, if name is a directory all files in directory will be deleted.* If array, names to be searched for deletion.* If clearCache() without params, all files in app/tmp/cache/views will be deleted** @param string $type Directory in tmp/cache defaults to view directory* @param string $ext The file extension you are deleting* @return true if files found and deleted false otherwise*/function clearCache($params = null, $type = 'views', $ext = '.php') {if (is_string($params) || $params === null) {$params = preg_replace('/\/\//', '/', $params);$cache = CACHE . $type . DS . $params;if (is_file($cache . $ext)) {@unlink($cache . $ext);return true;} elseif (is_dir($cache)) {$files = glob($cache . '*');if ($files === false) {return false;}foreach ($files as $file) {if (is_file($file)) {@unlink($file);}}return true;} else {$cache = array(CACHE . $type . DS . '*' . $params . $ext,CACHE . $type . DS . '*' . $params . '_*' . $ext);$files = array();while ($search = array_shift($cache)) {$results = glob($search);if ($results !== false) {$files = array_merge($files, $results);}}if (empty($files)) {return false;}foreach ($files as $file) {if (is_file($file)) {@unlink($file);}}return true;}} elseif (is_array($params)) {foreach ($params as $file) {clearCache($file, $type, $ext);}return true;}return false;}/*** Recursively strips slashes from all values in an array** @param array $values Array of values to strip slashes* @return mixed What is returned from calling stripslashes* @link http://book.cakephp.org/view/709/stripslashes_deep*/function stripslashes_deep($values) {if (is_array($values)) {foreach ($values as $key => $value) {$values[$key] = stripslashes_deep($value);}} else {$values = stripslashes($values);}return $values;}/*** Returns a translated string if one is found; Otherwise, the submitted message.** @param string $singular Text to translate* @param boolean $return Set to true to return translated string, or false to echo* @return mixed translated string if $return is false string will be echoed* @link http://book.cakephp.org/view/693/__*/function __($singular, $return = false) {if (!$singular) {return;}if (!class_exists('I18n')) {App::import('Core', 'i18n');}if ($return === false) {echo I18n::translate($singular);} else {return I18n::translate($singular);}}/*** Returns correct plural form of message identified by $singular and $plural for count $count.* Some languages have more than one form for plural messages dependent on the count.** @param string $singular Singular text to translate* @param string $plural Plural text* @param integer $count Count* @param boolean $return true to return, false to echo* @return mixed plural form of translated string if $return is false string will be echoed*/function __n($singular, $plural, $count, $return = false) {if (!$singular) {return;}if (!class_exists('I18n')) {App::import('Core', 'i18n');}if ($return === false) {echo I18n::translate($singular, $plural, null, 5, $count);} else {return I18n::translate($singular, $plural, null, 5, $count);}}/*** Allows you to override the current domain for a single message lookup.** @param string $domain Domain* @param string $msg String to translate* @param string $return true to return, false to echo* @return translated string if $return is false string will be echoed*/function __d($domain, $msg, $return = false) {if (!$msg) {return;}if (!class_exists('I18n')) {App::import('Core', 'i18n');}if ($return === false) {echo I18n::translate($msg, null, $domain);} else {return I18n::translate($msg, null, $domain);}}/*** Allows you to override the current domain for a single plural message lookup.* Returns correct plural form of message identified by $singular and $plural for count $count* from domain $domain.** @param string $domain Domain* @param string $singular Singular string to translate* @param string $plural Plural* @param integer $count Count* @param boolean $return true to return, false to echo* @return plural form of translated string if $return is false string will be echoed*/function __dn($domain, $singular, $plural, $count, $return = false) {if (!$singular) {return;}if (!class_exists('I18n')) {App::import('Core', 'i18n');}if ($return === false) {echo I18n::translate($singular, $plural, $domain, 5, $count);} else {return I18n::translate($singular, $plural, $domain, 5, $count);}}/*** Allows you to override the current domain for a single message lookup.* It also allows you to specify a category.** The category argument allows a specific category of the locale settings to be used for fetching a message.* Valid categories are: LC_CTYPE, LC_NUMERIC, LC_TIME, LC_COLLATE, LC_MONETARY, LC_MESSAGES and LC_ALL.** Note that the category must be specified with a numeric value, instead of the constant name. The values are:* LC_CTYPE 0* LC_NUMERIC 1* LC_TIME 2* LC_COLLATE 3* LC_MONETARY 4* LC_MESSAGES 5* LC_ALL 6** @param string $domain Domain* @param string $msg Message to translate* @param integer $category Category* @param boolean $return true to return, false to echo* @return translated string if $return is false string will be echoed*/function __dc($domain, $msg, $category, $return = false) {if (!$msg) {return;}if (!class_exists('I18n')) {App::import('Core', 'i18n');}if ($return === false) {echo I18n::translate($msg, null, $domain, $category);} else {return I18n::translate($msg, null, $domain, $category);}}/*** Allows you to override the current domain for a single plural message lookup.* It also allows you to specify a category.* Returns correct plural form of message identified by $singular and $plural for count $count* from domain $domain.** The category argument allows a specific category of the locale settings to be used for fetching a message.* Valid categories are: LC_CTYPE, LC_NUMERIC, LC_TIME, LC_COLLATE, LC_MONETARY, LC_MESSAGES and LC_ALL.** Note that the category must be specified with a numeric value, instead of the constant name. The values are:* LC_CTYPE 0* LC_NUMERIC 1* LC_TIME 2* LC_COLLATE 3* LC_MONETARY 4* LC_MESSAGES 5* LC_ALL 6** @param string $domain Domain* @param string $singular Singular string to translate* @param string $plural Plural* @param integer $count Count* @param integer $category Category* @param boolean $return true to return, false to echo* @return plural form of translated string if $return is false string will be echoed*/function __dcn($domain, $singular, $plural, $count, $category, $return = false) {if (!$singular) {return;}if (!class_exists('I18n')) {App::import('Core', 'i18n');}if ($return === false) {echo I18n::translate($singular, $plural, $domain, $category, $count);} else {return I18n::translate($singular, $plural, $domain, $category, $count);}}/*** The category argument allows a specific category of the locale settings to be used for fetching a message.* Valid categories are: LC_CTYPE, LC_NUMERIC, LC_TIME, LC_COLLATE, LC_MONETARY, LC_MESSAGES and LC_ALL.** Note that the category must be specified with a numeric value, instead of the constant name. The values are:* LC_CTYPE 0* LC_NUMERIC 1* LC_TIME 2* LC_COLLATE 3* LC_MONETARY 4* LC_MESSAGES 5* LC_ALL 6** @param string $msg String to translate* @param integer $category Category* @param string $return true to return, false to echo* @return translated string if $return is false string will be echoed*/function __c($msg, $category, $return = false) {if (!$msg) {return;}if (!class_exists('I18n')) {App::import('Core', 'i18n');}if ($return === false) {echo I18n::translate($msg, null, null, $category);} else {return I18n::translate($msg, null, null, $category);}}/*** Computes the difference of arrays using keys for comparison.** @param array First array* @param array Second array* @return array Array with different keys*/if (!function_exists('array_diff_key')) {function array_diff_key() {$valuesDiff = array();$argc = func_num_args();if ($argc < 2) {return false;}$args = func_get_args();foreach ($args as $param) {if (!is_array($param)) {return false;}}foreach ($args[0] as $valueKey => $valueData) {for ($i = 1; $i < $argc; $i++) {if (isset($args[$i][$valueKey])) {continue 2;}}$valuesDiff[$valueKey] = $valueData;}return $valuesDiff;}}/*** Computes the intersection of arrays using keys for comparison** @param array First array* @param array Second array* @return array Array with interesected keys*/if (!function_exists('array_intersect_key')) {function array_intersect_key($arr1, $arr2) {$res = array();foreach ($arr1 as $key => $value) {if (isset($arr2[$key])) {$res[$key] = $arr1[$key];}}return $res;}}/*** Shortcut to Log::write.** @param string $message Message to write to log*/function LogError($message) {if (!class_exists('CakeLog')) {App::import('Core', 'CakeLog');}$bad = array("\n", "\r", "\t");$good = ' ';CakeLog::write('error', str_replace($bad, $good, $message));}/*** Searches include path for files.** @param string $file File to look for* @return Full path to file if exists, otherwise false* @link http://book.cakephp.org/view/702/fileExistsInPath*/function fileExistsInPath($file) {$paths = explode(PATH_SEPARATOR, ini_get('include_path'));foreach ($paths as $path) {$fullPath = $path . DS . $file;if (file_exists($fullPath)) {return $fullPath;} elseif (file_exists($file)) {return $file;}}return false;}/*** Convert forward slashes to underscores and removes first and last underscores in a string** @param string String to convert* @return string with underscore remove from start and end of string* @link http://book.cakephp.org/view/697/convertSlash*/function convertSlash($string) {$string = trim($string, '/');$string = preg_replace('/\/\//', '/', $string);$string = str_replace('/', '_', $string);return $string;}/*** Implements http_build_query for PHP4.** @param string $data Data to set in query string* @param string $prefix If numeric indices, prepend this to index for elements in base array.* @param string $argSep String used to separate arguments* @param string $baseKey Base key* @return string URL encoded query string* @see http://php.net/http_build_query*/if (!function_exists('http_build_query')) {function http_build_query($data, $prefix = null, $argSep = null, $baseKey = null) {if (empty($argSep)) {$argSep = ini_get('arg_separator.output');}if (is_object($data)) {$data = get_object_vars($data);}$out = array();foreach ((array)$data as $key => $v) {if (is_numeric($key) && !empty($prefix)) {$key = $prefix . $key;}$key = urlencode($key);if (!empty($baseKey)) {$key = $baseKey . '[' . $key . ']';}if (is_array($v) || is_object($v)) {$out[] = http_build_query($v, $prefix, $argSep, $key);} else {$out[] = $key . '=' . urlencode($v);}}return implode($argSep, $out);}}/*** Wraps ternary operations. If $condition is a non-empty value, $val1 is returned, otherwise $val2.* Don't use for isset() conditions, or wrap your variable with @ operator:* Example:* <code>* ife(isset($variable), @$variable, 'default');* </code>** @param mixed $condition Conditional expression* @param mixed $val1 Value to return in case condition matches* @param mixed $val2 Value to return if condition doesn't match* @return mixed $val1 or $val2, depending on whether $condition evaluates to a non-empty expression.* @link http://book.cakephp.org/view/704/ife*/function ife($condition, $val1 = null, $val2 = null) {if (!empty($condition)) {return $val1;}return $val2;}?>