261 lines
7.5 KiB
PHP
261 lines
7.5 KiB
PHP
<?php
|
|
|
|
#namespace Doctrine\Common;
|
|
|
|
#use \ArrayAccess;
|
|
|
|
/**
|
|
* Base class for classes that use the virtual property system.
|
|
*
|
|
* @author robo
|
|
*/
|
|
class Doctrine_Common_VirtualPropertyObject implements ArrayAccess
|
|
{
|
|
protected $_data = array();
|
|
protected $_entityName;
|
|
|
|
/**
|
|
* Initializes a new instance of a class derived from VirtualPropertyObject.
|
|
*/
|
|
public function __construct()
|
|
{
|
|
$this->_entityName = get_class($this);
|
|
if ( ! Doctrine_Common_VirtualPropertySystem::isInitialized($this->_entityName)) {
|
|
Doctrine_Common_VirtualPropertySystem::initialize($this->_entityName);
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Generic getter for virtual properties.
|
|
*
|
|
* @param string $fieldName Name of the field.
|
|
* @return mixed
|
|
*/
|
|
final public function get($fieldName)
|
|
{
|
|
if ( ! Doctrine_Common_VirtualPropertySystem::hasProperty($this->_entityName, $fieldName)) {
|
|
throw new Doctrine_Exception("Access of undefined property '$fieldName'.");
|
|
}
|
|
$getter = $this->_getCustomAccessor($fieldName);
|
|
if ($getter) {
|
|
return $this->$getter();
|
|
}
|
|
return $this->_get($fieldName);
|
|
}
|
|
|
|
/**
|
|
* Generic setter for virtual properties.
|
|
*
|
|
* @param string $name The name of the field to set.
|
|
* @param mixed $value The value of the field.
|
|
*/
|
|
final public function set($fieldName, $value)
|
|
{
|
|
if ( ! Doctrine_Common_VirtualPropertySystem::hasProperty($this->_entityName, $fieldName)) {
|
|
throw new Doctrine_Exception("Access of undefined property '$fieldName'.");
|
|
}
|
|
if (Doctrine_Common_VirtualPropertySystem::isTypeCheckEnabled()) {
|
|
$this->_checkType($fieldName, $value);
|
|
}
|
|
$setter = $this->_getCustomMutator($fieldName);
|
|
if ($setter) {
|
|
return $this->$setter($value);
|
|
}
|
|
$this->_set($fieldName, $value);
|
|
}
|
|
|
|
/**
|
|
* Checks the type of a virtual property.
|
|
*
|
|
* @param <type> $fieldName
|
|
* @param <type> $value
|
|
*/
|
|
protected function _checkType($fieldName, $value)
|
|
{
|
|
$type = Doctrine_Common_VirtualPropertySystem::getType($this->_entityName, $fieldName);
|
|
if (Doctrine_Common_VirtualPropertySystem::isSimplePHPType($type)) {
|
|
$is_type = "is_$type";
|
|
if ( ! $is_type($value)) {
|
|
throw new Doctrine_Exception("'$value' is of an invalid type. Expected: $type.");
|
|
}
|
|
} else if ($type == 'array') {
|
|
if ( ! is_array($value)) {
|
|
throw new Doctrine_Exception("'$value' is of an invalid type. Expected: array.");
|
|
}
|
|
} else {
|
|
if ( ! $value instanceof $type) {
|
|
throw new Doctrine_Exception("'$value' is of an invalid type. Expected: $type.");
|
|
}
|
|
}
|
|
}
|
|
|
|
protected function _get($fieldName)
|
|
{
|
|
return isset($this->_data[$fieldName]) ? $this->_data[$fieldName] : null;
|
|
}
|
|
|
|
protected function _set($fieldName, $value)
|
|
{
|
|
$this->_data[$fieldName] = $value;
|
|
}
|
|
|
|
/**
|
|
* Gets the custom mutator method for a virtual property, if it exists.
|
|
*
|
|
* @param string $fieldName The field name.
|
|
* @return mixed The name of the custom mutator or FALSE, if the field does
|
|
* not have a custom mutator.
|
|
*/
|
|
private function _getCustomMutator($fieldName)
|
|
{
|
|
if (Doctrine_Common_VirtualPropertySystem::getMutator($this->_entityName, $fieldName) === null) {
|
|
if (Doctrine_Common_VirtualPropertySystem::isAutoAccessorOverride()) {
|
|
$setterMethod = 'set' . Doctrine::classify($fieldName);
|
|
if ( ! method_exists($this, $setterMethod)) {
|
|
$setterMethod = false;
|
|
}
|
|
Doctrine_Common_VirtualPropertySystem::setMutator(
|
|
$this->_entityName, $fieldName, $setterMethod);
|
|
} else {
|
|
Doctrine_Common_VirtualPropertySystem::setMutator(
|
|
$this->_entityName, $fieldName, false);
|
|
}
|
|
}
|
|
return Doctrine_Common_VirtualPropertySystem::getMutator($this->_entityName, $fieldName);
|
|
}
|
|
|
|
/**
|
|
* Gets the custom accessor method of a virtual property, if it exists.
|
|
*
|
|
* @param string $fieldName The field name.
|
|
* @return mixed The name of the custom accessor method, or FALSE if the
|
|
* field does not have a custom accessor.
|
|
*/
|
|
private function _getCustomAccessor($fieldName)
|
|
{
|
|
if (Doctrine_Common_VirtualPropertySystem::getAccessor($this->_entityName, $fieldName) === null) {
|
|
if (Doctrine_Common_VirtualPropertySystem::isAutoAccessorOverride()) {
|
|
$getterMethod = 'get' . Doctrine::classify($fieldName);
|
|
if ( ! method_exists($this, $getterMethod)) {
|
|
$getterMethod = false;
|
|
}
|
|
Doctrine_Common_VirtualPropertySystem::setAccessor(
|
|
$this->_entityName, $fieldName, $getterMethod);
|
|
} else {
|
|
Doctrine_Common_VirtualPropertySystem::setAccessor(
|
|
$this->_entityName, $fieldName, false);
|
|
}
|
|
}
|
|
|
|
return Doctrine_Common_VirtualPropertySystem::getAccessor($this->_entityName, $fieldName);
|
|
}
|
|
|
|
protected function _contains($fieldName)
|
|
{
|
|
return isset($this->_data[$fieldName]);
|
|
}
|
|
|
|
protected function _unset($fieldName)
|
|
{
|
|
unset($this->_data[$fieldName]);
|
|
}
|
|
|
|
/**
|
|
* Intercepts mutating calls for virtual properties.
|
|
*
|
|
* @see set, offsetSet
|
|
* @param $name
|
|
* @param $value
|
|
* @since 1.0
|
|
* @return void
|
|
*/
|
|
public function __set($name, $value)
|
|
{
|
|
$this->set($name, $value);
|
|
}
|
|
|
|
/**
|
|
* Intercepts accessing calls for virtual properties.
|
|
*
|
|
* @see get, offsetGet
|
|
* @param mixed $name
|
|
* @return mixed
|
|
*/
|
|
public function __get($name)
|
|
{
|
|
return $this->get($name);
|
|
}
|
|
|
|
/**
|
|
* Intercepts isset() calls for virtual properties.
|
|
*
|
|
* @param string $name
|
|
* @return boolean whether or not this object contains $name
|
|
*/
|
|
public function __isset($name)
|
|
{
|
|
return $this->_contains($name);
|
|
}
|
|
|
|
/**
|
|
* Intercepts unset() calls for virtual properties.
|
|
*
|
|
* @param string $name
|
|
* @return void
|
|
*/
|
|
public function __unset($name)
|
|
{
|
|
return $this->_unset($name);
|
|
}
|
|
|
|
/* ArrayAccess implementation */
|
|
|
|
/**
|
|
* Check if an offsetExists.
|
|
*
|
|
* @param mixed $offset
|
|
* @return boolean whether or not this object contains $offset
|
|
*/
|
|
public function offsetExists($offset)
|
|
{
|
|
return $this->_contains($offset);
|
|
}
|
|
|
|
/**
|
|
* offsetGet an alias of get()
|
|
*
|
|
* @see get, __get
|
|
* @param mixed $offset
|
|
* @return mixed
|
|
*/
|
|
public function offsetGet($offset)
|
|
{
|
|
return $this->get($offset);
|
|
}
|
|
|
|
/**
|
|
* sets $offset to $value
|
|
* @see set, __set
|
|
* @param mixed $offset
|
|
* @param mixed $value
|
|
* @return void
|
|
*/
|
|
public function offsetSet($offset, $value)
|
|
{
|
|
return $this->set($offset, $value);
|
|
}
|
|
|
|
/**
|
|
* unset a given offset
|
|
* @see set, offsetSet, __set
|
|
* @param mixed $offset
|
|
*/
|
|
public function offsetUnset($offset)
|
|
{
|
|
return $this->_unset($offset);
|
|
}
|
|
|
|
/* END of ArrayAccess implementation */
|
|
}
|
|
?>
|