显然是一个 YAML 解析器。

v1.0.8 2024-09-15 01:08 UTC

This package is auto-updated.

Last update: 2024-09-15 01:08:46 UTC


README

from.php to.php

动机

人们似乎不再寻找内容管理系统了。已经有那么多博客服务允许他们只写内容。在大数据时代,个性化和货币化似乎不再是主要关注点。或者,如果货币化是他们唯一的关注点,他们可能会将其留给使用的服务,牺牲选择符合他们个性的网页设计。

实际上,这个项目是我内容管理系统 Mecha 的一个内部功能,但我决定现在将其作为一个独立项目,以便其他人也能使用它。人们似乎更倾向于寻找 PHP YAML 解析器,而不是内容管理系统。因此,这个项目也是我试图将需要 PHP YAML 解析器的人引导到我所自豪的内容管理系统项目中的尝试(显然,这个项目并不非常受欢迎,因为人们似乎更感兴趣的是静态站点生成器)。

为什么你应该选择我的 YAML 解析器而不是其他任何类似的 YAML 解析器?

  • mustangostang/spyc 由一个 PHP 文件组成,大小为 35.1 KB,包含总共 1186 行代码 自编写时起。它已经过时(只支持 YAML 1.0,并且在各种情况下存在错误 在此 此处 此处),并且与我的 YAML 解析器相比,相对较大。
  • symfony/yaml 优先考虑可靠性和稳定性,用于大型应用程序。此库包含许多依赖项,如果您的目标仅仅是将 YAML 语法转换为 PHP 数据,则会导致您的应用程序过度膨胀。
  • yaml 要求您的服务器允许您安装 PHP 扩展。在转换速度方面,它应该更快,因为它使用 C,但并不能保证在您租用的所有 PHP 服务器上都可以使用,考虑到这个 PHP 扩展默认并不捆绑在 PHP 中。

功能

锚点

asdf-1: &asdf 1
asdf-2: *asdf
asdf-3: *asdf
asdf-1: &asdf
  a: asdf
  b: asdf
  c: asdf
asdf-2: *asdf
asdf-3: *asdf

注释

官方 PHP YAML 扩展 不同,此锚点功能仅复制值,并不通过将锚点值链接到它们的别名作为 引用 进行适当的内存管理,以简化 1

数组

列表

- asdf
- asdf
- asdf

[ asdf, asdf, asdf ]

对象

a: asdf
b: asdf
c: asdf

{ a: asdf, b: asdf, c: asdf }

注释

# This is a comment.

标量

布尔值

# Case insensitive
false
# Case insensitive
true

常量

# Case insensitive
.INF
# Case insensitive
.NAN

日期

2023-09-25
2023-09-25 20:22:42
# Case insensitive
2023-09-25T20:22:42.025Z
# Case insensitive
2023-09-25T20:22:42+07:00

数字

浮点数
0.5
.5
指数形式的浮点数
# Case insensitive
1.2e+34
整数
12
十六进制整数
# Case insensitive
0xC
八进制整数
# Case insensitive
0o14
014

空值

# Case insensitive
null
~

字符串

折叠
> # Clip (default)
  asdf asdf asdf asdf
  asdf asdf asdf asdf

  asdf asdf asdf asdf
>4 # Clip and indent with 2 space(s)
      asdf asdf asdf asdf
      asdf asdf asdf asdf

      asdf asdf asdf asdf
>+ # Keep
  asdf asdf asdf asdf
  asdf asdf asdf asdf

  asdf asdf asdf asdf
>+4 # Keep and indent with 2 space(s)
      asdf asdf asdf asdf
      asdf asdf asdf asdf

      asdf asdf asdf asdf
>- # Strip
  asdf asdf asdf asdf
  asdf asdf asdf asdf

  asdf asdf asdf asdf
>-4 # Strip and indent with 2 space(s)
      asdf asdf asdf asdf
      asdf asdf asdf asdf

      asdf asdf asdf asdf
字面量
| # Clip (default)
  asdf asdf asdf asdf
  asdf asdf asdf asdf

  asdf asdf asdf asdf
|4 # Clip and indent with 2 space(s)
      asdf asdf asdf asdf
      asdf asdf asdf asdf

      asdf asdf asdf asdf
|+ # Keep
  asdf asdf asdf asdf
  asdf asdf asdf asdf

  asdf asdf asdf asdf
|+4 # Keep and indent with 2 space(s)
      asdf asdf asdf asdf
      asdf asdf asdf asdf

      asdf asdf asdf asdf
|- # Strip
  asdf asdf asdf asdf
  asdf asdf asdf asdf

  asdf asdf asdf asdf
|-4 # Strip and indent with 2 space(s)
      asdf asdf asdf asdf
      asdf asdf asdf asdf

      asdf asdf asdf asdf

双引号
"asdf asdf \"asdf\" asdf"
单引号
'asdf asdf ''asdf'' asdf'
普通
asdf asdf 'asdf' asdf

标签

支持以下内置标签

  • !!binary
  • !!bool
  • !!float
  • !!int
  • !!map
  • !!null
  • !!seq
  • !!str
  • !!timestamp

想要添加自定义标签的用户可以在from()函数的$lot参数中定义它们,作为一个闭包。注意,这个参数是一个实时引用,因此你不能直接将其中的标签定义数组放入其中。相反,你必须将其放入一个临时变量中。

// <https://symfony.com.cn/doc/7.0/reference/formats/yaml.html#symfony-specific-features>
$lot = [
    '!php/const' => static function ($value) {
        if (is_string($value) && defined($value)) {
            return constant($value);
        }
        return null;
    },
    '!php/enum' => static function ($value) {
        if (!is_string($value)) {
            return null;
        }
        [$a, $b] = explode('::', $value, 2);
        if ('->value' === substr($b, -7)) {
            return (new ReflectionEnumBackedCase($a, substr($b, 0, -7)))->getBackingValue();
        }
        return (new ReflectionEnumBackedCase($a, $b))->getValue();
    },
    '!php/object' => static function ($value) {
        return is_string($value) ? unserialize($value) : null;
    }
];

$value = from_yaml($value, false, $lot);

// Here, the `$lot` variable will probably contain anchors as well. Anchor data will have a key started with ‘&’.

var_dump($lot, $value);

用法

此转换器可以使用Composer进行安装,但它不需要其他依赖项,只是使用Composer自动包含文件的能力。如果您不使用Composer,应该能够直接将from.phpto.php文件包含到您的应用程序中而不会出现任何问题。

使用Composer

从命令行界面,导航到您的项目文件夹,然后运行此命令

composer require taufik-nurrohman/y-a-m-l

在您的应用程序中引入生成的自动加载文件

<?php

use function x\y_a_m_l\from as from_yaml;
use function x\y_a_m_l\to as to_yaml;

require 'vendor/autoload.php';

var_export(from_yaml('asdf: asdf')); // Returns `(object) ['asdf' => 'asdf']`

使用文件

在您的应用程序中引入from.phpto.php文件

<?php

use function x\y_a_m_l\from as from_yaml;
use function x\y_a_m_l\to as to_yaml;

require 'from.php';
require 'to.php';

var_export(from_yaml('asdf: asdf')); // Returns `(object) ['asdf' => 'asdf']`

选项

/**
 * Convert YAML string to PHP data.
 *
 * @param null|string $value Your YAML string.
 * @param bool $array If this option is set to `true`, PHP object will becomes associative array.
 * @param array $lot Currently used to store anchor(s) and custom tag(s)
 * @return mixed
 */
from(?string $value, bool $array = false, array &$lot = []): mixed;
/**
 * Convert PHP data to YAML string.
 *
 * @param mixed $value Your PHP data.
 * @param bool|int|string $dent Specify the indent size or character(s).
 * @return null|string
 */
to(mixed $value, bool|int|string $dent = true): ?string;

测试

将此存储库克隆到支持PHP的Web服务器的根目录中,然后您可以使用浏览器打开test/from.phptest/to.php文件,以查看结果和此转换器在各种情况下的性能。

调整

您的YAML内容表示为变量$value。如果在调用from_yaml()函数之前修改内容,则表示在转换之前修改了YAML内容。如果在调用from_yaml()函数之后修改内容,则表示修改了YAML转换的结果。

全局可重用函数

为了使from_yaml()to_yaml()函数可全局重用,请使用此方法

<?php

require 'from.php';
require 'to.php';

// Or, if you are using Composer…
// require 'vendor/autoload.php';

function from_yaml(...$v) {
    return x\y_a_m_l\from(...$v);
}

function to_yaml(...$v) {
    return x\y_a_m_l\to(...$v);
}

文档

此转换器不支持一个YAML文件中的多个文档功能,但可以稍加努力实现支持。

// Ensure line break after `---` and `...`
$value = preg_replace('/^(-{3}|[.]{3})\s+/m', '$1' . "\n", $value);

// Remove `---\n` prefix if any
if (0 === strpos($value, "---\n")) {
    $value = substr($value, 4);
}

$values = [];
foreach (explode("\n---\n", $value . "\n") as $v) {
    // Remove everything after `...`
    $v = explode("\n...\n", $v . "\n", 2)[0];
    $values[] = from_yaml($v);
}

var_dump($values);

变量

在YAML中有几种声明变量的方式,它们都不符合标准。最常见的是类似于{{ var }}格式的变量。为了添加变量功能,需要在解析数据之前将变量转换为YAML值。

$variables = [
    'var_1' => 'asdf',
    'var_2' => true,
    'var_3' => 1,
    'var_4' => 1.5
];

if (false !== strpos($value, '{{')) {
    $value = preg_replace_callback('/"\{\{\s*[a-z]\w*\s*\}\}"|\'\{\{\s*[a-z]\w*\s*\}\}\'|\{\{\s*[a-z]\w*\s*\}\}/', static function ($m) use ($variables) {
        $variable = $m[0];
        // `"{{ var }}"`
        if ('"' === $variable[0] && '"' === substr($variable, -1)) {
            $variable = substr($variable, 1, -1);
        }
        // `'{{ var }}'`
        if ("'" === $variable[0] && "'" === substr($variable, -1)) {
            $variable = substr($variable, 1, -1);
        }
        // Trim variable from `{{` and `}}`
        $variable = trim(substr($variable, 2, -2));
        // Get the variable value if available, default to `null`
        $variable = $variables[$variable] ?? null;
        // Return the variable value as YAML string
        return to_yaml($variable);
    }, $value);
}

$value = from_yaml($value);

var_dump($value);

许可证

此库采用MIT许可证授权。如果您从本库中获得经济利益,请考虑捐赠💰