mediact/data-container

此包已废弃,不再维护。未建议替代包。

数据容器库

2.11.3 2022-09-13 02:28 UTC

README

此包已废弃。根据模式选择数据,我们建议使用 JMESPath。要找到匹配模式的路径(glob)并更新这些路径(set),我们没有一个明确的替代方案。

Scrutinizer Code Quality

数据容器

此包提供了一个数据容器。数据容器可以包含任何数据。可以使用点表示法访问数据。

安装

$ composer require mediact/data-container

使用

创建容器

容器可以直接创建或使用工厂创建。

<?php
use Mediact\DataContainer\DataContainer;
use Mediact\DataContainer\DataContainerFactory;

$data = [
    'categories' => [
        'foo' => ['name' => 'Foo'],
        'bar' => ['name' => 'Bar']
    ]
];

// Directly
$container = new DataContainer($data);

// Using a factory
$factory   = new DataContainerFactory();
$container = $factory->create($data);

检查值是否已设置使用 has()

<?php
/** @var Mediact\DataContainer\DataContainer $container */
var_dump($container->has('categories.foo')); // true
var_dump($container->has('categories.qux')); // false

使用 get() 获取值

<?php
/** @var Mediact\DataContainer\DataContainer $container */
var_dump($container->get('categories.foo.name'));            // Foo
var_dump($container->get('categories.qux.name'));            // null
var_dump($container->get('categories.qux.name', 'Default')); // Default

使用 set() 设置值

<?php
/** @var Mediact\DataContainer\DataContainer $container */
$container->set('categories.qux', ['name' => 'Qux']);
var_dump($container->get('categories.qux.name')); // Qux

使用 remove() 删除值

<?php
/** @var Mediact\DataContainer\DataContainer $container */
$container->remove('categories.qux');
var_dump($container->has('categories.qux')); // false

remove 方法也支持通配符,例如 remove('bar.*');

使用 glob() 获取匹配模式的路径

glob 方法返回与给定模式匹配的路径列表。

<?php
/** @var Mediact\DataContainer\DataContainer $container */
var_dump($container->glob('categories.*'));      // ['categories.foo', 'categories.bar']
var_dump($container->glob('categories.ba?'));    // ['categories.bar']
var_dump($container->glob('categories.ba[zr]')); // ['categories.bar']

使用 expand() 获取路径及其替换项

expand 方法返回与给定模式匹配的路径列表,并返回它们的替换项。替换项可以包含变量,类似于 preg_replace。

<?php
/** @var Mediact\DataContainer\DataContainer $container */
var_dump($container->expand('categories.f*', 'cat.f$1'));      // ['categories.foo' => 'cat.foo']
var_dump($container->expand('categories.?a?', 'cat.$1a$2'));   // ['categories.bar' => 'cat.bar']
var_dump($container->expand('categories.ba[zr]', 'cat.ba$2')); // ['categories.bar' => 'cat.bar']

使用 branch() 获取匹配模式的分支

branch 方法返回与模式匹配的路径列表,作为数据容器列表。

<?php
/** @var Mediact\DataContainer\DataContainer $container */
foreach ($container->branch('categories.*') as $category) {
    var_dump($category->get('name')); // Foo, Bar
}

使用 node() 从容器中获取节点

node 方法返回一个包含路径数据的单个容器。

<?php
/** @var Mediact\DataContainer\DataContainer $container */
$foo = $container->node('categories.foo');
var_dump($foo->get('name')); // Foo

使用 copy() 复制数据

<?php
/** @var Mediact\DataContainer\DataContainer $container */
$container->copy('categories.foo', 'categories.qux');
var_dump($container->get('categories.qux')); // ['name' => 'Foo']

copy 方法支持通配符。替换项可以包含变量,类似于 expand()。

<?php
/** @var Mediact\DataContainer\DataContainer $container */
$container->copy('categories.*', 'copied_categories.$1');
var_dump($container->get('copied_categories.foo')); // ['name' => 'Foo']
var_dump($container->get('copied_categories.bar')); // ['name' => 'Bar']

使用 move() 移动数据

<?php
/** @var Mediact\DataContainer\DataContainer $container */
$container->move('categories.foo', 'categories.qux');
var_dump($container->has('categories.foo')); // false
var_dump($container->get('categories.qux')); // ['name' => 'Foo']

move 方法支持通配符。替换项可以包含变量,类似于 expand()。

<?php
/** @var Mediact\DataContainer\DataContainer $container */
$container->move('categories.*', 'moved_categories.$1');
var_dump($container->has('categories.foo'));       // false
var_dump($container->has('categories.bar'));       // false
var_dump($container->get('moved_categories.foo')); // ['name' => 'Foo']
var_dump($container->get('moved_categories.bar')); // ['name' => 'Bar']

创建装饰器

可以使用 DataContainerDecoratorTrait 创建数据容器的装饰器。

<?php
use Mediact\DataContainer\DataContainer;
use Mediact\DataContainer\DataContainerInterface;
use Mediact\DataContainer\DataContainerDecoratorTrait;

class FooDataContainer implements DataContainerInterface
{
    use DataContainerDecoratorTrait;

    public function __construct(array $data = [])
    {
        $this->setData($data);
    }
}

class BarDataContainer implements DataContainerInterface
{
    use DataContainerDecoratorTrait;

    public function __construct(DataContainerInterface $storage = null)
    {
        $this->setStorage($storage ?: new DataContainer());
    }
}

两种实现都包含 DataContainerInterface 的所有方法。

创建一个可遍历装饰器

可以使用 DataContainerIteratorAggregateTrait 创建一个既是装饰器又能遍历的类。

<?php
use Mediact\DataContainer\DataContainerInterface;
use Mediact\DataContainer\DataContainerDecoratorTrait;
use Mediact\DataContainer\DataContainerIteratorAggregateTrait;

class FooTraversableDataContainer implements DataContainerInterface, IteratorAggregate
{
    use DataContainerDecoratorTrait;
    use DataContainerIteratorAggregateTrait;

    public function __construct(array $data = [])
    {
        $this->setData($data);
    }
}

过滤容器

为了过滤容器,需要一个实现 DataContainerFilterInterface 的类。

有一个默认的实现,用于链式操作。

<?php
use Mediact\DataContainer\DataContainerFilterInterface;
use Mediact\DataContainer\DataContainerFilterChain;
use Mediact\DataContainer\DataContainerInterface;

/**
 * @var DataContainerFilterInterface $fooFilter
 * @var DataContainerFilterInterface $barFilter
 * @var DataContainerFilterInterface $bazFilter
 * @var DataContainerInterface       $container
 */

$filter = new DataContainerFilterChain(
    $fooFilter,
    $barFilter,
    $bazFilter
);

if ($filter($container)) {
    // Proceed.
    $container->move('foo', 'bar');
}