nicoswd/php-rule-parser

规则引擎 - 规则解析器 & 评估器

0.7.1 2021-02-05 22:06 UTC

README

Latest Stable Version Build status Code Quality StyleCI

Total Downloads Latest Stable Version

您正在查看一个独立的PHP库,用于使用类似JavaScript的语法解析和评估基于文本的规则。这个项目源于评估数百条规则的需求,这些规则最初是用JavaScript编写和评估的,现在需要在服务器端使用PHP进行评估。

这个库最初被用于更改和配置内网应用中某些“工作流”的行为(而不改变实际代码),但它可能适用于其他用途。

在Twitter上找到我:@nicoSWD

(如果您使用的是PHP 5,您可能想看看版本0.4.0

SensioLabsInsight

安装

通过Composer

$ composer require nicoswd/php-rule-parser

捆绑包

此库与以下任何一个捆绑包配合使用效果最佳,但不是必需的

使用示例

测试一个值是否在给定的数组中

$variables = ['foo' => 6];

$rule = new Rule('foo in [4, 6, 7]', $variables);
var_dump($rule->isTrue()); // bool(true)

简单的数组操作

$rule = new Rule('[1, 4, 3].join(".") === "1.4.3"');
var_dump($rule->isTrue()); // bool(true)

测试一个值是否在给定的范围内

$variables = ['threshold' => 80];

$rule = new Rule('threshold >= 50 && threshold <= 100', $variables);
var_dump($rule->isTrue()); // bool(true)

在规则内部调用对象的方法

class User
{
    // ...

    public function points(): int
    {
        return 1337;    
    }
}

$variables = [
    'user' => new User(),
];

$rule = new Rule('user.points() > 300', $variables);
var_dump($rule->isTrue()); // bool(true)

出于安全原因,PHP的魔法方法如__construct__destruct不能在规则内部调用。但是,如果可用,将自动调用__call,除非定义了被调用的方法。

内置方法

内置函数

支持的运算符

错误处理

两者$rule->isTrue()$rule->isFalse()如果语法无效,都将抛出异常。这些调用可以放在try / catch块中,或者可以使用$rule->isValid()预先检查。

$ruleStr = '
    (2 == 2) && (
        1 < 3 && 3 == 2 ( // Missing and/or before parentheses
            1 == 1
        )
    )';

$rule = new Rule($ruleStr);

try {
    $rule->isTrue();
} catch (\Exception $e) {
    echo $e->getMessage();
}

或者

if (!$rule->isValid()) {
    echo $rule->getError();
}

两者都将输出:在行3位置25出现意外的令牌 "("

语法高亮显示

还提供了一个自定义语法高亮器。

use nicoSWD\Rule;

$ruleStr = '
    // This is true
    2 < 3 && (
        // This is false
        foo in [4, 6, 7] ||
        // True
        [1, 4, 3].join("") === "143"
    ) && (
        // True
        "foo|bar|baz".split("|" /* uh oh */) === ["foo", /* what */ "bar", "baz"] &&
        // True
        bar > 6
    )';

$highlighter = new Rule\Highlighter\Highlighter(new Rule\Tokenizer());

// Optional custom styles
$highlighter->setStyle(
    Rule\Constants::GROUP_VARIABLE,
    'color: #007694; font-weight: 900;'
);

echo $highlighter->highlightString($ruleStr);

输出

Syntax preview

注意

  • 括号可以嵌套,并且将按从右到左的顺序进行评估。
  • 仅支持值/变量比较表达式,带有可选的逻辑ANDs/ORs。

安全

如果您发现任何与安全相关的问题,请通过security@nic0.me而不是使用问题跟踪器发送电子邮件。

测试

$ composer test

贡献

欢迎Pull请求!如果它们包括测试,那就更好了。此项目遵循PSR-2编码标准,请确保您的Pull请求也这样做。

待办事项

  • 支持对象属性(foo.length)
  • 支持返回实际结果,而不仅仅是true或false
  • 支持数组/字符串解引用:"foo"[1]
  • 对于已经是布尔值的令牌,不要强制进行布尔比较。`my_func() && 2 > 1`应该工作
  • 更改方法调用的正则表达式和实现。".split("不应该是一个令牌
  • 添加/实现缺失的方法
  • 添加"typeof"结构
  • 做数学(?)
  • 允许使用"+"进行字符串连接
  • 无效的正则表达式修饰符不应导致未知令牌
  • 重复的正则表达式修饰符应抛出错误
  • 支持函数调用
  • 支持正则表达式
  • 修复PHP 7/Nightly的构建问题
  • 允许数组中存在变量
  • 验证函数和方法名称的拼写(.tOuPpErCAse()当前是有效的)
  • ...

许可

License