使用 PEG 解析 JavaScript 的表达式

Parse expression with JavaScript using PEG

我已经编写了解析以下表达式的代码

!=10 AND <=99

{
    operator: 'AND',
    values: [
        {
            op: '!=',
            value: '10',
        },
        {
            op: '<=',
            value: '99',
        },
    ],
}

使用 PEG.js。请检查代码沙箱。

但是当我解析以下表达式时,我没有得到预期的输出。

=10 AND <=99 OR =1000

我想要以下输出

{
    operator: 'or',
    values: [
        {
            operator: 'and',
            values: [
                {
                    op: '=',
                    value: '10',
                },
                {
                    op: '<=',
                    value: '99',
                },
            ],
        },
        {
            op: '=',
            value: '1000',
        },
    ],
}

代码沙箱:https://codesandbox.io/s/javascript-testing-sandbox-forked-h5xh5?file=/src/index.js

不要使用字符串函数来解析比较运算符,让它们成为你语法的一部分。对于像 'AND' 这样的链式操作,使用这样的规则:

operation = head:argument tail:(ws AND ws argument)* 

并在代码块中相应地处理 headtail

完整示例:

expression = and

and = head:or tail:(ws "OR" ws or)* { 
    return tail.length ? {op: 'or', values: [head].concat(tail.map(r => r.pop()))} : head
} 

or = head:not tail:(ws "AND" ws not)* { 
    return tail.length ? {op: 'and', values: [head].concat(tail.map(r => r.pop()))} : head
}

not 
    = "NOT" ws right:not { return {op: 'not', right} }
    / factor

factor
    = op:operator value:primary { return {op, value} }
    / value:primary { return {value} }

operator = '!=' / '<=' / '>=' / '<' / '>' / '='  

primary = name / number / '(' expression ')'

name = a:[A-Za-z_] b:[0-9a-zA-Z_]* { return a + b.join("") }

number = a:[0-9]+ { return a.join("") }

ws = [ \t]+