macfja/value-provider

通过getter/setter/属性/元数据获取/设置对象值

v0.3.1 2016-02-19 20:46 UTC

This package is auto-updated.

Last update: 2024-09-17 00:56:31 UTC


README

ValueProvider 允许您访问对象的属性值,而无需了解对象如何定义访问方式。属性、getter/setter?让我们让 GuessProvider 来处理这个问题。

特性

可以访问对象的属性值

  • 通过直接属性访问(例如 $myObject->myProperty
    • 与魔法 __get__set(见下文示例和限制)一起工作
    • protectedprivate 属性(见下文示例和限制)一起工作
  • 通过修改器(getter/setter)(例如 $myObject->getMyProperty()$myObject->setMyProperty('new value')
    • 与魔法 __call(见下文示例和限制)一起工作
  • doctrine Metadata(见下文示例)一起工作

安装

Composer

composer require macfja/value-provider

示例

属性访问

Person 类

class Person {
    public $firstName = '';
    public $lastName = '';
}

在您的代码中的某处

$jdoe = new Person();
$provider = new PropertyProvider();

// ...

$provider->setValue($jdoe, 'firstName', 'John');
$provider->setValue($jdoe, 'lastName', 'Doe');

// ...

echo 'Hello ' . $provider->getValue($jdoe, 'firstName') . ' ' . $provider->getValue($jdoe, 'lastName');
//Output : "Hello John Doe"

注意

属性必须是公共的才能被访问。(对于受保护的和私有的属性,请参阅 ReflectorProvider)

魔法 __get__set 属性访问

Person 类

class Person {
    private $_firstName = 'John';
    private $_lastName = 'Doe';

    function __get($name) {
        if (in_array($name, array('firstName', 'lastName')) {
            $propertyName = '_' . $name;
            return $this->$propertyName;
        }

        throw new \BadFunctionCallException;
    }

    function __set($name, $value) {
        if (in_array($name, array('firstName', 'lastName')) {
            $propertyName = '_' . $name;
            $this->$propertyName = $value;
            return;
        }

        throw new \BadFunctionCallException;
    }

    function __isset($name) {
        return in_array($name, array('firstName', 'lastName');
    }
}

在您的代码中的某处

$jdoe = new Person();
$provider = new PropertyProvider();

// ...

$provider->setValue($jdoe, 'firstName', 'John');
$provider->setValue($jdoe, 'lastName', 'Doe');

// ...

echo 'Hello ' . $provider->getValue($jdoe, 'firstName') . ' ' . $provider->getValue($jdoe, 'lastName');
//Output : "Hello John Doe"

注意

该类依赖于 __isset 函数来知道属性是否可以用 __get__set 使用

修改器访问(getter/setter)

Person 类

class Person {
    private $_firstName = '';
    private $_lastName = '';
    private $_known = true;

    public function getFirstName() {
        return $this->_firstName;
    }
    public function setFirstName($value) {
        $this->_firstName = $value;
    }
    public function getLastName() {
        return $this->_lastName;
    }
    public function setLastName($value) {
        $this->_firstName = $value;
    }
    public function isKnown() {
        return $this->_known;
    }
    public function setKnown($flag) {
        $this->_known = $flag;
    }
}

在您的代码中的某处

$jdoe = new Person();
$provider = new MutatorProvider();

// ...

$provider->setValue($jdoe, 'firstName', 'John');
$provider->setValue($jdoe, 'lastName', 'Doe');
$provider->setValue($jdoe, 'known', false);

// ...

echo 'Hello ' . $provider->getValue($jdoe, 'firstName') . ' ' . $provider->getValue($jdoe, 'lastName');
echo ', you are ' . ($provider->getValue($jdoe, 'known') ? '' : 'un') . 'known';
//Output : "Hello John Doe, you are unknown"

注意

修改器必须是公共的才能被访问。getter 将按此顺序搜索

  • getMyProperty
  • isMyProperty

魔法 __call 修改器访问

Person 类

class Person {
    private $_firstName = 'John';
    private $_lastName = 'Doe';
    private $_known = true;

    function __call($name, $arguments) {
        switch ($name) {
            case 'getFirstName':
                return $this->_firstName;
            case 'getLastName':
                return $this->_lastName;
            case 'isKnown':
                return $this->_known;
            case 'setFirstName':
                $this->_firstName = $argument[0];
                return;
            case 'setLastName':
                $this->_lastName = $argument[0];
                return;
            case 'setKnown':
                $this->_known = $argument[0];
                return;
        }

        throw new \BadFunctionCallException;
    }
}

在您的代码中的某处

$jdoe = new Person();
$provider = new MutatorProvider();

// ...

$provider->setValue($jdoe, 'firstName', 'John');
$provider->setValue($jdoe, 'lastName', 'Doe');
$provider->setValue($jdoe, 'known', false);

// ...

echo 'Hello ' . $provider->getValue($jdoe, 'firstName') . ' ' . $provider->getValue($jdoe, 'lastName');
echo ', you are ' . ($provider->getValue($jdoe, 'known') ? '' : 'un') . 'known';
//Output : "Hello John Doe, you are unknown"

注意

该类依赖于 __call 函数的实现:如果getter/setter不存在,该函数必须抛出 \BadFunctionCallException\InvalidArgumentException

Doctrine Metadata

在您的代码中的某处

/** @type EntityManager $entityManager */
$class = 'MyClass';
$id = 1234;

$provider = new MetadataProvider();
MetadataProvider::setEntityManager($entityManager);

jdoe = $entityManager->find($class, $id);

// ...

$provider->setValue($jdoe, 'firstName', 'John');
$provider->setValue($jdoe, 'lastName', 'Doe');
$provider->setValue($jdoe, 'known', false);

// ...

echo 'Hello ' . $provider->getValue($jdoe, 'firstName') . ' ' . $provider->getValue($jdoe, 'lastName');
echo ', you are ' . ($provider->getValue($jdoe, 'known') ? '' : 'un') . 'known';
//Output : "Hello John Doe, you are unknown"

注意

您必须将 Doctrine EntityManager 设置到 MetadataProvider

ReflectorProvider

Person 类

class Person {
    public $firstName = 'John';
    protected $lastName = 'Doe';
    private $known = true;
}

在您的代码中的某处

$jdoe = new Person();
$provider = new ReflectorProvider();

// ...

$provider->setValue($jdoe, 'firstName', 'John');
$provider->setValue($jdoe, 'lastName', 'Doe');
$provider->setValue($jdoe, 'known', false);

// ...

echo 'Hello ' . $provider->getValue($jdoe, 'firstName') . ' ' . $provider->getValue($jdoe, 'lastName');
echo ', you are ' . ($provider->getValue($jdoe, 'known') ? '' : 'un') . 'known';
//Output : "Hello John Doe, you are unknown"

注意

如果您的PHP版本是5.3或更高,则该类可以访问私有/受保护的属性

GuessProvider

此类尝试通过修改器或属性或反射来访问值。它首先尝试修改器,如果失败,则尝试属性,最后尝试通过反射器。

ChainProvider

此类允许您尝试多个提供程序。例如,GuessProvider 基于该 ChainProvider

信息

此库遵循 PSR-1、PSR-2、PSR-4。每个提供程序都有 PHPUnit 测试。