runz0rd/mapper-php

模型映射、取消映射和验证

v2.2.16 2017-03-17 14:04 UTC

README

功能列表

  • 从json、xml、数组和其他对象映射PHP类属性。
  • 从模型到json、xml、数组和stdClass取消映射
  • 支持嵌套模型
  • 注释为模型属性提供自定义命名、类型和规则
  • 正确注释并映射的模型可以针对不同类型和规则进行验证

安装

composer require runz0rd/mapper-php

工作原理

映射器会遍历您的模型的所有属性名称(使用 @name 可以更改属性名称映射),如果源(json/xml/array/stdClass)中有相同名称的属性,则将其映射。映射的模型可以直接使用,但建议在映射后对其进行验证。必须设置所需属性(@required),并且必须为适当的类型(如果使用 @var 或 @rule 设置)。非必需属性可以不设置(null),但如果设置,则必须与定义的类型或规则(如果使用 @var 或 @rule 设置)匹配才能通过验证。因此,如果您有

{
  "name": "Jack",
  "type": "human",
  "age": 35,
  "isEmployed": true,
  "custom-desc": "lazy"
}

您可以创建如下模型

class SomeGuy {

    /**
     * @required
     * @var string
     */
    public $name;    

    /**
     * @required createSomeGuy
     * @var string
     */
    public $type;    

    /**
     * @rule limit(1,150)
     * @var integer
     */
    public $age;    

    /**
     * @var boolean
     */
    public $isEmployed;    
    
    /**
     * @name custom-desc
     * @var string
     */
    public $description
}

如果以下情况,验证会 失败

  • 您使用 createSomeGuy 动作,而没有(null) $type(仅在 createSomeGuy 动作中必需)
  • 没有(null) $name(总是必需)
  • 您使用 createSomething 动作,并且 $type 不是一个字符串
  • $name 不是一个字符串
  • $age 已设置(非 null),但不是一个整数,或者不在 1 到 150 之间(规则)
  • $isEmployed 已设置(非 null),但不是一个布尔值

请注意,$description 将被映射,因为它具有 @name 注释,并且源中存在具有该名称的属性(custom-desc)。

注释

以下是我们可以用在模型中的注释列表

@var 注释类型列表

用法

映射

在您的模型中使用 MappableTrait 来调用模型本身的方法

$model->mapFromArray($myArray);
$model->mapFromJson($myJson);
$model->mapFromXml($myXml);
$model->mapFromObject($myObject);

或者通过使用 ModelMapper 类,向其提供您想要映射的模型实例和源对象

$model = new Model();
$mapper = new ModelMapper();
$mapper->map($sourceObject, $model);

取消映射

在您的模型中使用 ConvertibleTrait 来调用模型本身的方法

$myArray = $model->toArray();
$myJson = $model->toJson();
$myXml = $model->toXml();
$myObject = $model->toObject();

或者通过使用 ModelMapper 类,向其提供映射的模型(转换为 stdClass)

$mapper = new ModelMapper();
$myObject = $mapper->unmap($myModel);

验证

验证将检查您的映射模型的属性类型、自定义规则以及属性是否必需。

使用 ValidatableTrait 验证您的映射模型,通过提供所需的验证操作

$model->validate('createAction');

或者如果只想验证始终必需的属性

$model->validate();

您也可以直接使用验证器

$model = new Model();
$validator = new ModelValidator();
$validator->validate($model, 'myAction');

规则

规则用于自定义验证映射属性的值。

/**
 * @rule email
 */
public $email;

这将检查属性值是否包含有效的电子邮件字符串。

您可以为规则传递额外的参数。

/**
 * @rule limit(0,99)
 */
public $value;

如果正确设置,此自定义规则将检查属性值是否介于 0 和 99 之间。

规则设置

让我们使用上面的 limit 规则示例来创建一个新的自定义规则

use Common\ModelReflection\ModelProperty;
use Validator\IRule;
use Validator\ModelValidatorException;

class LimitRule implements IRule {

    function getNames() {
        return ['limit'];
    }

    function validate(ModelProperty $property, array $params = []) {
        if($property->getPropertyValue() < $params[0] || $property->getPropertyValue() > $params[1]) {
            throw new ModelValidatorException('Value is not between '.$params[0].' and '.$params[1]);
        }
    }
}

在上面的示例中,我们可以通过以下方式配置一个新的规则

  • 定义一个名称(别名)数组,该名称作为注释中的规则名称(getNames)
  • 提供验证定义,如果它未通过则抛出异常(validate)
  • 规则参数(0,99)通过 $params 数组传入,按照它们提供的顺序

如需更多信息,请查看预定义的规则类和IRule接口。

加载您的规则

$model = new Model();
$myCustomRule = new MyCustomRule();
$validator = new ModelValidator();
$validator->useRule($myCustomRule);
$validator->loadRules('/path/to/rules/');
$validator->validate($model, 'myAction');

在上面的示例中,我们可以通过逐个提供给验证器(useRule)或提供包含规则的目录路径(loadRules)来使用自定义规则。

代码示例

请参阅其中使用的测试和模型。

启发我的东西

cweiske/jsonmapper