diff --git a/framework/YiiBase.php b/framework/YiiBase.php index 62c2fb6..2d08fe4 100644 --- a/framework/YiiBase.php +++ b/framework/YiiBase.php @@ -309,9 +309,6 @@ class YiiBase /** * Creates a new object using the given configuration. * - * The class of the object can be any class. It does not have to - * extend from [[Object]] or [[Component]]. - * * The configuration can be either a string or an array. * If a string, it is treated as the *object type*; if an array, * it must contain a `class` element specifying the *object type*, and @@ -321,17 +318,9 @@ class YiiBase * The object type can be either a class name or the [[getAlias|alias]] of * the class. For example, * - * - `\app\components\GoogleMap`: full qualified namespaced class. + * - `\app\components\GoogleMap`: fully-qualified namespaced class. * - `@app/components/GoogleMap`: an alias * - * This method does the following steps to create an object: - * - * - create the object using the PHP `new` operator; - * - if [[objectConfig]] contains the configuration for the object class, - * it will be merged with the configuration passed to this method; - * - initialize the object properties using the configuration passed to this method; - * - call the `init` method of the object if it implements the [[\yii\base\Initable]] interface. - * * Below are some usage examples: * * ~~~ @@ -342,16 +331,26 @@ class YiiBase * )); * ~~~ * - * Any additional parameters passed to this method will be - * passed to the constructor of the object being created. + * This method can be used to create any object as long as the object's constructor is + * defined like the following: + * + * ~~~ + * public function __construct(..., $config = array()) { + * } + * ~~~ + * + * The method will pass the given configuration as the last parameter of the constructor, + * and any additional parameters to this method will be passed as the rest of the constructor parameters. * - * @param string|array $config the configuration. It can be either a string or an array. + * @param string|array $config the configuration. It can be either a string representing the class name + * or an array representing the object configuration. * @return mixed the created object - * @throws Exception if the configuration is invalid. - * @see \yii\base\Object::newInstance() + * @throws \yii\base\BadConfigException if the configuration is invalid. */ public static function createObject($config) { + static $reflections = array(); + if (is_string($config)) { $class = $config; $config = array(); @@ -359,7 +358,7 @@ class YiiBase $class = $config['class']; unset($config['class']); } else { - throw new Exception('Object configuration must be an array containing a "class" element.'); + throw new \yii\base\BadConfigException('Object configuration must be an array containing a "class" element.'); } if (!class_exists($class, false)) { @@ -367,37 +366,21 @@ class YiiBase } if (($n = func_num_args()) > 1) { - $args = func_get_args(); - if ($n === 2) { - $object = new $class($args[1]); - } elseif ($n === 3) { - $object = new $class($args[1], $args[2]); - } elseif ($n === 4) { - $object = new $class($args[1], $args[2], $args[3]); + /** @var $reflection \ReflectionClass */ + if (isset($reflections[$class])) { + $reflection = $reflections[$class]; } else { - array_shift($args); // remove $config - $r = new \ReflectionClass($class); - $object = $r->newInstanceArgs($args); + $reflection = $reflections[$class] = new \ReflectionClass($class); + } + $args = func_get_args(); + array_shift($args); // remove $config + if ($config !== array()) { + $args[] = $config; } + return $reflection->newInstanceArgs($args); } else { - $object = new $class; + return $config === array() ? new $class : new $class($config); } - - $class = get_class($object); - - if (isset(\Yii::$objectConfig[$class])) { - $config = array_merge(\Yii::$objectConfig[$class], $config); - } - - foreach ($config as $name => $value) { - $object->$name = $value; - } - - if ($object instanceof \yii\base\Initable) { - $object->init(); - } - - return $object; } /** @@ -545,14 +528,22 @@ class YiiBase if (self::$application !== null) { if ($source === null) - $source = $category === 'yii' ? 'coreMessages' : 'messages'; + { + $source = $category === 'yii' ? 'coreMessages' : 'messages'; + } if (($source = self::$application->getComponent($source)) !== null) - $message = $source->translate($category, $message, $language); + { + $message = $source->translate($category, $message, $language); + } } if ($params === array()) - return $message; + { + return $message; + } if (!is_array($params)) - $params = array($params); + { + $params = array($params); + } if (isset($params[0])) // number choice { if (strpos($message, '|') !== false) @@ -563,8 +554,10 @@ class YiiBase $expressions = self::$application->getLocale($language)->getPluralRules(); if ($n = min(count($chunks), count($expressions))) { - for ($i = 0;$i < $n;$i++) - $chunks[$i] = $expressions[$i] . '#' . $chunks[$i]; + for ($i = 0; $i < $n; $i++) + { + $chunks[$i] = $expressions[$i] . '#' . $chunks[$i]; + } $message = implode('|', $chunks); } @@ -572,7 +565,9 @@ class YiiBase $message = CChoiceFormat::format($message, $params[0]); } if (!isset($params['{n}'])) - $params['{n}'] = $params[0]; + { + $params['{n}'] = $params[0]; + } unset($params[0]); } return $params !== array() ? strtr($message, $params) : $message; diff --git a/framework/base/Application.php b/framework/base/Application.php index 5f4971d..4a5c089 100644 --- a/framework/base/Application.php +++ b/framework/base/Application.php @@ -202,14 +202,15 @@ class Application extends Module * @param string $route the route (e.g. `post/create`) * @param array $params the parameters to be passed to the controller action * @return integer the exit status (0 means normal, non-zero values mean abnormal) - * @throws Exception if the route cannot be resolved into a controller + * @throws BadRequestException if the route cannot be resolved into a controller */ public function runController($route, $params = array()) { $result = $this->createController($route); if ($result === false) { - throw new Exception(\Yii::t('yii', 'Unable to resolve the request.')); + throw new BadRequestException(\Yii::t('yii', 'Unable to resolve the request.')); } + /** @var $controller Controller */ list($controller, $action) = $result; $priorController = $this->controller; $this->controller = $controller; @@ -233,13 +234,13 @@ class Application extends Module /** * Sets the directory that stores runtime files. * @param string $path the directory that stores runtime files. - * @throws Exception if the directory does not exist or is not writable + * @throws BadParamException if the directory does not exist or is not writable */ public function setRuntimePath($path) { $p = \Yii::getAlias($path); if ($p === false || !is_dir($p) || !is_writable($path)) { - throw new Exception("Application runtime path \"$path\" is invalid. Please make sure it is a directory writable by the Web server process."); + throw new BadParamException("Application runtime path \"$path\" is invalid. Please make sure it is a directory writable by the Web server process."); } else { $this->_runtimePath = $p; } diff --git a/framework/base/ApplicationComponent.php b/framework/base/ApplicationComponent.php index 6e18e67..c93ff98 100644 --- a/framework/base/ApplicationComponent.php +++ b/framework/base/ApplicationComponent.php @@ -15,7 +15,7 @@ namespace yii\base; * @author Qiang Xue * @since 2.0 */ -abstract class ApplicationComponent extends Component implements Initable +abstract class ApplicationComponent extends Component { /** * Initializes the application component. diff --git a/framework/base/BadConfigException.php b/framework/base/BadConfigException.php new file mode 100644 index 0000000..e0e20f9 --- /dev/null +++ b/framework/base/BadConfigException.php @@ -0,0 +1,21 @@ + + * @since 2.0 + */ +class BadConfigException extends \Exception +{ +} + diff --git a/framework/base/BadMethodException.php b/framework/base/BadMethodException.php new file mode 100644 index 0000000..6ccc10c --- /dev/null +++ b/framework/base/BadMethodException.php @@ -0,0 +1,21 @@ + + * @since 2.0 + */ +class BadMethodException extends \Exception +{ +} + diff --git a/framework/base/BadParamException.php b/framework/base/BadParamException.php new file mode 100644 index 0000000..f250d2b --- /dev/null +++ b/framework/base/BadParamException.php @@ -0,0 +1,21 @@ + + * @since 2.0 + */ +class BadParamException extends \Exception +{ +} + diff --git a/framework/base/BadPropertyException.php b/framework/base/BadPropertyException.php new file mode 100644 index 0000000..7395dc9 --- /dev/null +++ b/framework/base/BadPropertyException.php @@ -0,0 +1,21 @@ + + * @since 2.0 + */ +class BadPropertyException extends \Exception +{ +} + diff --git a/framework/base/BadRequestException.php b/framework/base/BadRequestException.php new file mode 100644 index 0000000..2849a43 --- /dev/null +++ b/framework/base/BadRequestException.php @@ -0,0 +1,21 @@ + + * @since 2.0 + */ +class BadRequestException extends \Exception +{ +} + diff --git a/framework/base/Component.php b/framework/base/Component.php index e8e814b..fb9657a 100644 --- a/framework/base/Component.php +++ b/framework/base/Component.php @@ -40,7 +40,7 @@ class Component extends \yii\base\Object * @param string $name the property name * @return mixed the property value, event handlers attached to the event, * the named behavior, or the value of a behavior's property - * @throws Exception if the property is not defined + * @throws BadPropertyException if the property is not defined * @see __set */ public function __get($name) @@ -58,7 +58,7 @@ class Component extends \yii\base\Object } } } - throw new Exception('Getting unknown property: ' . get_class($this) . '.' . $name); + throw new BadPropertyException('Getting unknown property: ' . get_class($this) . '.' . $name); } /** @@ -74,7 +74,7 @@ class Component extends \yii\base\Object * will be implicitly called when executing `$component->property = $value;`. * @param string $name the property name or the event name * @param mixed $value the property value - * @throws Exception if the property is not defined or read-only. + * @throws BadPropertyException if the property is not defined or read-only. * @see __get */ public function __set($name, $value) @@ -104,9 +104,9 @@ class Component extends \yii\base\Object } } if (method_exists($this, 'get' . $name)) { - throw new Exception('Setting read-only property: ' . get_class($this) . '.' . $name); + throw new BadPropertyException('Setting read-only property: ' . get_class($this) . '.' . $name); } else { - throw new Exception('Setting unknown property: ' . get_class($this) . '.' . $name); + throw new BadPropertyException('Setting unknown property: ' . get_class($this) . '.' . $name); } } @@ -150,7 +150,7 @@ class Component extends \yii\base\Object * Do not call this method directly as it is a PHP magic method that * will be implicitly called when executing `unset($component->property)`. * @param string $name the property name - * @throws Exception if the property is read only. + * @throws BadPropertyException if the property is read only. */ public function __unset($name) { @@ -170,7 +170,7 @@ class Component extends \yii\base\Object } } if (method_exists($this, 'get' . $name)) { - throw new Exception('Unsetting read-only property: ' . get_class($this) . '.' . $name); + throw new BadPropertyException('Unsetting read-only property: ' . get_class($this) . '.' . $name); } } @@ -185,8 +185,8 @@ class Component extends \yii\base\Object * will be implicitly called when an unknown method is being invoked. * @param string $name the method name * @param array $params method parameters - * @throws Exception when calling unknown method * @return mixed the method return value + * @throws BadMethodException when calling unknown method */ public function __call($name, $params) { @@ -204,7 +204,7 @@ class Component extends \yii\base\Object } } - throw new Exception('Calling unknown method: ' . get_class($this) . "::$name()"); + throw new BadMethodException('Calling unknown method: ' . get_class($this) . "::$name()"); } /** diff --git a/framework/base/Controller.php b/framework/base/Controller.php index a93414e..f8da2e0 100644 --- a/framework/base/Controller.php +++ b/framework/base/Controller.php @@ -25,7 +25,7 @@ namespace yii\base; * @author Qiang Xue * @since 2.0 */ -class Controller extends Component implements Initable +class Controller extends Component { /** * @var string ID of this controller @@ -195,11 +195,11 @@ class Controller extends Component implements Initable * This method is invoked when the controller cannot find the requested action. * The default implementation simply throws an exception. * @param string $actionID the missing action name - * @throws Exception whenever this method is invoked + * @throws BadRequestException whenever this method is invoked */ public function missingAction($actionID) { - throw new Exception(\Yii::t('yii', 'The system is unable to find the requested action "{action}".', + throw new BadRequestException(\Yii::t('yii', 'The system is unable to find the requested action "{action}".', array('{action}' => $actionID == '' ? $this->defaultAction : $actionID))); } diff --git a/framework/base/Dictionary.php b/framework/base/Dictionary.php index d94c3cf..4c73463 100644 --- a/framework/base/Dictionary.php +++ b/framework/base/Dictionary.php @@ -182,7 +182,7 @@ class Dictionary extends Object implements \IteratorAggregate, \ArrayAccess, \Co * Copies iterable data into the dictionary. * Note, existing data in the dictionary will be cleared first. * @param mixed $data the data to be copied from, must be an array or an object implementing `Traversable` - * @throws Exception if data is neither an array nor an iterator. + * @throws BadParamException if data is neither an array nor an iterator. */ public function copyFrom($data) { @@ -197,7 +197,7 @@ class Dictionary extends Object implements \IteratorAggregate, \ArrayAccess, \Co $this->add($key, $value); } } else { - throw new Exception('Data must be either an array or an object implementing Traversable.'); + throw new BadParamException('Data must be either an array or an object implementing Traversable.'); } } @@ -214,7 +214,7 @@ class Dictionary extends Object implements \IteratorAggregate, \ArrayAccess, \Co * * @param array|\Traversable $data the data to be merged with. It must be an array or object implementing Traversable * @param boolean $recursive whether the merging should be recursive. - * @throws Exception if data is neither an array nor an object implementing `Traversable`. + * @throws BadParamException if data is neither an array nor an object implementing `Traversable`. */ public function mergeWith($data, $recursive = true) { @@ -238,7 +238,7 @@ class Dictionary extends Object implements \IteratorAggregate, \ArrayAccess, \Co } } } else { - throw new Exception('The data to be merged with must be an array or an object implementing Traversable.'); + throw new BadParamException('The data to be merged with must be an array or an object implementing Traversable.'); } } diff --git a/framework/base/Initable.php b/framework/base/Initable.php deleted file mode 100644 index eb2d3bd..0000000 --- a/framework/base/Initable.php +++ /dev/null @@ -1,32 +0,0 @@ - - * @since 2.0 - */ -interface Initable -{ - /** - * Initializes this component. - * This method is invoked by [[\Yii::createObject]] after its creates the new - * component instance and initializes the component properties. In other words, - * at this stage, the component has been fully configured. - */ - public function init(); -} diff --git a/framework/base/Model.php b/framework/base/Model.php index 4a3ba3b..eee5715 100644 --- a/framework/base/Model.php +++ b/framework/base/Model.php @@ -279,6 +279,7 @@ class Model extends Component implements \IteratorAggregate, \ArrayAccess * Creates validator objects based on the validation rules specified in [[rules()]]. * Unlike [[getValidators()]], each time this method is called, a new list of validators will be returned. * @return Vector validators + * @throws BadConfigException if any validation rule configuration is invalid */ public function createValidators() { @@ -288,7 +289,7 @@ class Model extends Component implements \IteratorAggregate, \ArrayAccess $validator = \yii\validators\Validator::createValidator($rule[1], $this, $rule[0], array_slice($rule, 2)); $validators->add($validator); } else { - throw new Exception('Invalid validation rule: a rule must specify both attribute names and validator type.'); + throw new BadConfigException('Invalid validation rule: a rule must specify both attribute names and validator type.'); } } return $validators; diff --git a/framework/base/Module.php b/framework/base/Module.php index 2d90785..50a12fd 100644 --- a/framework/base/Module.php +++ b/framework/base/Module.php @@ -27,7 +27,7 @@ use yii\util\FileHelper; * @author Qiang Xue * @since 2.0 */ -abstract class Module extends Component implements Initable +abstract class Module extends Component { /** * @var array custom module parameters (name => value). @@ -584,7 +584,7 @@ abstract class Module extends Component implements Initable } if (class_exists($className, false) && is_subclass_of($className, '\yii\base\Controller')) { return array( - $className::newInstance(array(), $id, $this), + new $className($id, $this), $route, ); } diff --git a/framework/base/Object.php b/framework/base/Object.php index 770234a..1811986 100644 --- a/framework/base/Object.php +++ b/framework/base/Object.php @@ -21,8 +21,32 @@ class Object { /** * Constructor. + * The default implementation does two things: + * + * - Initializes the object with the given configuration `$config`. + * - Call [[init()]]. + * + * If this method is overridden in a child class, it is recommended that + * + * - the last parameter of the constructor is a configuration array, like `$config` here. + * - call the parent implementation at the end of the constructor. + * + * @param array $config name-value pairs that will be used to initialize the object properties + */ + public function __construct($config = array()) + { + foreach ($config as $name => $value) { + $this->$name = $value; + } + $this->init(); + } + + /** + * Initializes the object. + * This method is invoked at the end of the constructor after the object is initialized with the + * given configuration. */ - public function __construct() + public function init() { } @@ -34,7 +58,7 @@ class Object * @param string $name the property name * @return mixed the property value, event handlers attached to the event, * the named behavior, or the value of a behavior's property - * @throws Exception if the property is not defined + * @throws BadPropertyException if the property is not defined * @see __set */ public function __get($name) @@ -43,7 +67,7 @@ class Object if (method_exists($this, $getter)) { return $this->$getter(); } else { - throw new Exception('Getting unknown property: ' . get_class($this) . '.' . $name); + throw new BadPropertyException('Getting unknown property: ' . get_class($this) . '.' . $name); } } @@ -54,7 +78,7 @@ class Object * will be implicitly called when executing `$object->property = $value;`. * @param string $name the property name or the event name * @param mixed $value the property value - * @throws Exception if the property is not defined or read-only. + * @throws BadPropertyException if the property is not defined or read-only. * @see __get */ public function __set($name, $value) @@ -63,9 +87,9 @@ class Object if (method_exists($this, $setter)) { $this->$setter($value); } elseif (method_exists($this, 'get' . $name)) { - throw new Exception('Setting read-only property: ' . get_class($this) . '.' . $name); + throw new BadPropertyException('Setting read-only property: ' . get_class($this) . '.' . $name); } else { - throw new Exception('Setting unknown property: ' . get_class($this) . '.' . $name); + throw new BadPropertyException('Setting unknown property: ' . get_class($this) . '.' . $name); } } @@ -99,7 +123,7 @@ class Object * Note that if the property is not defined, this method will do nothing. * If the property is read-only, it will throw an exception. * @param string $name the property name - * @throws Exception if the property is read only. + * @throws BadPropertyException if the property is read only. */ public function __unset($name) { @@ -108,7 +132,7 @@ class Object // write property $this->$setter(null); } elseif (method_exists($this, 'get' . $name)) { - throw new Exception('Unsetting read-only property: ' . get_class($this) . '.' . $name); + throw new BadPropertyException('Unsetting read-only property: ' . get_class($this) . '.' . $name); } } @@ -121,7 +145,7 @@ class Object * will be implicitly called when an unknown method is being invoked. * @param string $name the method name * @param array $params method parameters - * @throws Exception when calling unknown method + * @throws BadMethodException when calling unknown method * @return mixed the method return value */ public function __call($name, $params) @@ -133,7 +157,7 @@ class Object return call_user_func_array($func, $params); } } - throw new Exception('Unknown method: ' . get_class($this) . "::$name()"); + throw new BadMethodException('Unknown method: ' . get_class($this) . "::$name()"); } /** @@ -148,7 +172,7 @@ class Object */ public function hasProperty($name, $checkVar = true) { - return $this->canGetProperty($name, false) || $this->canSetProperty($name, false) || $checkVar && property_exists($this, $name); + return $this->canGetProperty($name, $checkVar) || $this->canSetProperty($name, false); } /** @@ -176,86 +200,6 @@ class Object */ public function canSetProperty($name, $checkVar = true) { - return $checkVar && property_exists($this, $name) || method_exists($this, 'set' . $name); - } - - /** - * Creates a new instance of the calling class. - * - * The newly created object will be initialized with the specified configuration. - * - * Extra parameters passed to this method will be used as the parameters to the object - * constructor. - * - * This method does the following steps to create a object: - * - * - create the object using the PHP `new` operator; - * - if [[Yii::objectConfig]] contains the configuration for the object class, - * it will be merged with the $config parameter; - * - initialize the object properties using the configuration passed to this method; - * - call the `init` method of the object if it implements the [[yii\base\Initable]] interface. - * - * For example, - * - * ~~~ - * class Foo extends \yii\base\Object implements \yii\base\Initable - * { - * public $c; - * public function __construct($a, $b) - * { - * ... - * } - * public function init() - * { - * ... - * } - * } - * - * $model = Foo::newInstance(array('c' => 3), 1, 2); - * // which is equivalent to the following lines: - * $model = new Foo(1, 2); - * $model->c = 3; - * $model->init(); - * ~~~ - * - * @param array $config the object configuration (name-value pairs that will be used to initialize the object) - * @return \yii\base\Object the created object - * @throws Exception if the configuration is invalid. - */ - public static function newInstance($config = array()) - { - $class = get_called_class(); - - if (($n = func_num_args()) > 1) { - $args = func_get_args(); - if ($n === 2) { - $object = new $class($args[1]); - } elseif ($n === 3) { - $object = new $class($args[1], $args[2]); - } elseif ($n === 4) { - $object = new $class($args[1], $args[2], $args[3]); - } else { - // remove $config - array_shift($args); - $r = new \ReflectionClass($class); - $object = $r->newInstanceArgs($args); - } - } else { - $object = new $class; - } - - if (isset(\Yii::$objectConfig[$class])) { - $config = array_merge(\Yii::$objectConfig[$class], $config); - } - - foreach ($config as $name => $value) { - $object->$name = $value; - } - - if ($object instanceof Initable) { - $object->init(); - } - - return $object; + return method_exists($this, 'set' . $name) || $checkVar && property_exists($this, $name); } } diff --git a/framework/base/Request.php b/framework/base/Request.php new file mode 100644 index 0000000..4f3b8b3 --- /dev/null +++ b/framework/base/Request.php @@ -0,0 +1,150 @@ + + * @since 2.0 + */ +class Request extends ApplicationComponent +{ + private $_scriptFile; + + /** + * Initializes the application component. + * This method overrides the parent implementation by preprocessing + * the user request data. + */ + public function init() + { + } + + /** + * Returns the relative URL of the entry script. + * The implementation of this method referenced Zend_Controller_Request_Http in Zend Framework. + * @return string the relative URL of the entry script. + */ + public function getScriptUrl() + { + if($this->_scriptUrl===null) + { + $scriptName=basename($_SERVER['SCRIPT_FILENAME']); + if(basename($_SERVER['SCRIPT_NAME'])===$scriptName) + $this->_scriptUrl=$_SERVER['SCRIPT_NAME']; + else if(basename($_SERVER['PHP_SELF'])===$scriptName) + $this->_scriptUrl=$_SERVER['PHP_SELF']; + else if(isset($_SERVER['ORIG_SCRIPT_NAME']) && basename($_SERVER['ORIG_SCRIPT_NAME'])===$scriptName) + $this->_scriptUrl=$_SERVER['ORIG_SCRIPT_NAME']; + else if(($pos=strpos($_SERVER['PHP_SELF'],'/'.$scriptName))!==false) + $this->_scriptUrl=substr($_SERVER['SCRIPT_NAME'],0,$pos).'/'.$scriptName; + else if(isset($_SERVER['DOCUMENT_ROOT']) && strpos($_SERVER['SCRIPT_FILENAME'],$_SERVER['DOCUMENT_ROOT'])===0) + $this->_scriptUrl=str_replace('\\','/',str_replace($_SERVER['DOCUMENT_ROOT'],'',$_SERVER['SCRIPT_FILENAME'])); + else + throw new Exception(Yii::t('yii','CHttpRequest is unable to determine the entry script URL.')); + } + return $this->_scriptUrl; + } + + /** + * Sets the relative URL for the application entry script. + * This setter is provided in case the entry script URL cannot be determined + * on certain Web servers. + * @param string $value the relative URL for the application entry script. + */ + public function setScriptUrl($value) + { + $this->_scriptUrl='/'.trim($value,'/'); + } + + /** + * Returns whether this is an AJAX (XMLHttpRequest) request. + * @return boolean whether this is an AJAX (XMLHttpRequest) request. + */ + public function getIsAjaxRequest() + { + return isset($_SERVER['HTTP_X_REQUESTED_WITH']) && $_SERVER['HTTP_X_REQUESTED_WITH']==='XMLHttpRequest'; + } + + /** + * Returns whether this is an Adobe Flash or Adobe Flex request. + * @return boolean whether this is an Adobe Flash or Adobe Flex request. + * @since 1.1.11 + */ + public function getIsFlashRequest() + { + return isset($_SERVER['HTTP_USER_AGENT']) && (stripos($_SERVER['HTTP_USER_AGENT'],'Shockwave')!==false || stripos($_SERVER['HTTP_USER_AGENT'],'Flash')!==false); + } + + /** + * Returns the server name. + * @return string server name + */ + public function getServerName() + { + return $_SERVER['SERVER_NAME']; + } + + /** + * Returns the server port number. + * @return integer server port number + */ + public function getServerPort() + { + return $_SERVER['SERVER_PORT']; + } + + /** + * Returns the URL referrer, null if not present + * @return string URL referrer, null if not present + */ + public function getUrlReferrer() + { + return isset($_SERVER['HTTP_REFERER'])?$_SERVER['HTTP_REFERER']:null; + } + + /** + * Returns the user agent, null if not present. + * @return string user agent, null if not present + */ + public function getUserAgent() + { + return isset($_SERVER['HTTP_USER_AGENT'])?$_SERVER['HTTP_USER_AGENT']:null; + } + + /** + * Returns the user IP address. + * @return string user IP address + */ + public function getUserHostAddress() + { + return isset($_SERVER['REMOTE_ADDR'])?$_SERVER['REMOTE_ADDR']:'127.0.0.1'; + } + + /** + * Returns the user host name, null if it cannot be determined. + * @return string user host name, null if cannot be determined + */ + public function getUserHost() + { + return isset($_SERVER['REMOTE_HOST'])?$_SERVER['REMOTE_HOST']:null; + } + + /** + * Returns entry script file path. + * @return string entry script file path (processed w/ realpath()) + */ + public function getScriptFile() + { + if($this->_scriptFile!==null) + return $this->_scriptFile; + else + return $this->_scriptFile=realpath($_SERVER['SCRIPT_FILENAME']); + } +} diff --git a/framework/base/Response.php b/framework/base/Response.php new file mode 100644 index 0000000..c15d108 --- /dev/null +++ b/framework/base/Response.php @@ -0,0 +1,20 @@ + + * @since 2.0 + */ +class Response extends ApplicationComponent +{ +} diff --git a/framework/base/Theme.php b/framework/base/Theme.php index c539a76..464602b 100644 --- a/framework/base/Theme.php +++ b/framework/base/Theme.php @@ -25,12 +25,12 @@ class Theme extends ApplicationComponent if ($this->basePath !== null) { $this->basePath = \Yii::getAlias($this->basePath, true); } else { - throw new Exception("Theme.basePath must be set."); + throw new BadConfigException("Theme.basePath must be set."); } if ($this->baseUrl !== null) { $this->baseUrl = \Yii::getAlias($this->baseUrl, true); } else { - throw new Exception("Theme.baseUrl must be set."); + throw new BadConfigException("Theme.baseUrl must be set."); } } diff --git a/framework/base/Vector.php b/framework/base/Vector.php index 5a685e0..f6c7aca 100644 --- a/framework/base/Vector.php +++ b/framework/base/Vector.php @@ -99,7 +99,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta * Returns the item at the specified index. * @param integer $index the index of the item * @return mixed the item at the index - * @throws Exception if the index is out of range + * @throws BadParamException if the index is out of range */ public function itemAt($index) { @@ -108,7 +108,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta } elseif ($index >= 0 && $index < $this->_c) { // in case the value is null return $this->_d[$index]; } else { - throw new Exception('Index out of range: ' . $index); + throw new BadParamException('Index out of range: ' . $index); } } @@ -130,7 +130,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta * one step towards the end. * @param integer $index the specified position. * @param mixed $item new item to be inserted into the vector - * @throws Exception if the index specified is out of range, or the vector is read-only. + * @throws BadParamException if the index specified is out of range, or the vector is read-only. */ public function insertAt($index, $item) { @@ -140,7 +140,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta array_splice($this->_d, $index, 0, array($item)); $this->_c++; } else { - throw new Exception('Index out of range: ' . $index); + throw new BadParamException('Index out of range: ' . $index); } } @@ -167,7 +167,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta * Removes an item at the specified position. * @param integer $index the index of the item to be removed. * @return mixed the removed item. - * @throws Exception if the index is out of range, or the vector is read only. + * @throws BadParamException if the index is out of range, or the vector is read only. */ public function removeAt($index) { @@ -181,7 +181,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta return $item; } } else { - throw new Exception('Index out of range: ' . $index); + throw new BadParamException('Index out of range: ' . $index); } } @@ -240,7 +240,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta * Copies iterable data into the vector. * Note, existing data in the vector will be cleared first. * @param mixed $data the data to be copied from, must be an array or an object implementing `Traversable` - * @throws Exception if data is neither an array nor an object implementing `Traversable`. + * @throws BadParamException if data is neither an array nor an object implementing `Traversable`. */ public function copyFrom($data) { @@ -255,7 +255,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta $this->add($item); } } else { - throw new Exception('Data must be either an array or an object implementing Traversable.'); + throw new BadParamException('Data must be either an array or an object implementing Traversable.'); } } @@ -263,7 +263,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta * Merges iterable data into the vector. * New items will be appended to the end of the existing items. * @param array|\Traversable $data the data to be merged with. It must be an array or object implementing Traversable - * @throws Exception if data is neither an array nor an object implementing `Traversable`. + * @throws BadParamException if data is neither an array nor an object implementing `Traversable`. */ public function mergeWith($data) { @@ -275,7 +275,7 @@ class Vector extends Object implements \IteratorAggregate, \ArrayAccess, \Counta $this->add($item); } } else { - throw new Exception('The data to be merged with must be an array or an object implementing Traversable.'); + throw new BadParamException('The data to be merged with must be an array or an object implementing Traversable.'); } } diff --git a/framework/base/View.php b/framework/base/View.php index 802855e..f2a06e2 100644 --- a/framework/base/View.php +++ b/framework/base/View.php @@ -103,7 +103,7 @@ class View extends Component * @param array $params the parameters that should be made available in the view. The PHP function `extract()` * will be called on this variable to extract the variables from this parameter. * @return string the rendering result - * @throws Exception if the view file cannot be found + * @throws BadParamException if the view file cannot be found */ public function renderPartial($view, $params = array()) { @@ -111,7 +111,7 @@ class View extends Component if ($file !== false) { return $this->renderFile($file, $params); } else { - throw new Exception("Unable to find the view file for view '$view'."); + throw new BadParamException("Unable to find the view file for view '$view'."); } } @@ -170,6 +170,7 @@ class View extends Component */ public function endWidget() { + /** @var $widget Widget */ if (($widget = array_pop($this->widgetStack)) !== null) { $widget->run(); return $widget; @@ -413,7 +414,7 @@ class View extends Component * The themed layout file will be returned if theme is enabled and the theme contains such a layout file. * * @return string|boolean the layout file path, or false if the context does not need layout. - * @throws Exception if the layout file cannot be found + * @throws BadParamException if the layout file cannot be found */ public function findLayoutFile() { @@ -451,7 +452,7 @@ class View extends Component } } if ($file === false || !is_file($file)) { - throw new Exception("Unable to find the layout file for layout '{$module->layout}' (specified by " . get_class($module) . ")"); + throw new BadParamException("Unable to find the layout file for layout '{$module->layout}' (specified by " . get_class($module) . ")"); } elseif ($this->localizeView) { return FileHelper::localize($file, $this->language, $this->sourceLanguage); } else { diff --git a/framework/base/Widget.php b/framework/base/Widget.php index c95ea7f..23efd37 100644 --- a/framework/base/Widget.php +++ b/framework/base/Widget.php @@ -15,7 +15,7 @@ namespace yii\base; * @author Qiang Xue * @since 2.0 */ -class Widget extends Component implements Initable +class Widget extends Component { /** * @var Widget|Controller the owner/creator of this widget. It could be either a widget or a controller. @@ -62,13 +62,6 @@ class Widget extends Component implements Initable } /** - * Initializes the widget. - */ - public function init() - { - } - - /** * Executes the widget. */ public function run() diff --git a/framework/caching/MemCache.php b/framework/caching/MemCache.php index 5366584..1a19738 100644 --- a/framework/caching/MemCache.php +++ b/framework/caching/MemCache.php @@ -138,7 +138,7 @@ class MemCache extends Cache public function setServers($config) { foreach ($config as $c) { - $this->_servers[] = MemCacheServer::newInstance($c); + $this->_servers[] = new MemCacheServer($c); } } diff --git a/framework/db/ar/ActiveMetaData.php b/framework/db/ar/ActiveMetaData.php index 41391bb..74ce6cb 100644 --- a/framework/db/ar/ActiveMetaData.php +++ b/framework/db/ar/ActiveMetaData.php @@ -89,7 +89,7 @@ class ActiveMetaData if (is_string($config)) { $config = array('on' => $config); } - $relation = ActiveRelation::newInstance($config); + $relation = new ActiveRelation($config); $relation->name = $matches[1]; $modelClass = $matches[2]; if (strpos($modelClass, '\\') !== false) { diff --git a/framework/db/ar/ActiveRecord.php b/framework/db/ar/ActiveRecord.php index bdd8756..544d7a7 100644 --- a/framework/db/ar/ActiveRecord.php +++ b/framework/db/ar/ActiveRecord.php @@ -1034,7 +1034,8 @@ abstract class ActiveRecord extends Model */ public static function instantiate($row) { - return static::newInstance(); + $class = get_called_class(); + return new $class; } /** diff --git a/framework/db/dao/Connection.php b/framework/db/dao/Connection.php index 7b0f5f7..85f29b4 100644 --- a/framework/db/dao/Connection.php +++ b/framework/db/dao/Connection.php @@ -25,10 +25,10 @@ use yii\db\Exception; * the DB connection: * * ~~~ - * $connection = \yii\db\dao\Connection::newInstance(array( - * 'dsn' => $dsn, - * 'username' => $username, - * 'password' => $password, + * $connection = new \yii\db\dao\Connection(array( + * 'dsn' => $dsn, + * 'username' => $username, + * 'password' => $password, * )); * $connection->active = true; // same as: $connection->open(); * ~~~ diff --git a/framework/logging/Target.php b/framework/logging/Target.php index 377528b..1a1979a 100644 --- a/framework/logging/Target.php +++ b/framework/logging/Target.php @@ -23,7 +23,7 @@ namespace yii\logging; * @author Qiang Xue * @since 2.0 */ -abstract class Target extends \yii\base\Component implements \yii\base\Initable +abstract class Target extends \yii\base\Component { /** * @var boolean whether to enable this log target. Defaults to true. @@ -90,15 +90,6 @@ abstract class Target extends \yii\base\Component implements \yii\base\Initable abstract public function exportMessages($final); /** - * Initializes this component. - * This method is invoked after the component is created and its property values are - * initialized. - */ - public function init() - { - } - - /** * Processes the given log messages. * This method will filter the given messages with [[levels]] and [[categories]]. * And if requested, it will also export the filtering result to specific medium (e.g. email). diff --git a/framework/yiic.php b/framework/yiic.php index a1e2a24..a6b205d 100644 --- a/framework/yiic.php +++ b/framework/yiic.php @@ -18,4 +18,5 @@ $config = array( $id = 'yiic'; $basePath = __DIR__ . '/console'; -yii\console\Application::newInstance($config, $id, $basePath)->run(); \ No newline at end of file +$application = new yii\console\Application($id, $basePath, $config); +$application->run();