npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

object-expression-parser

v0.4.0

Published

javascript object expression parser.

Readme

ObjectExpressionParser

一个支持自定义操作符的 javascript 对象表达式转换器,可根据自定义的操作符生成不同语法。

let e = {
    'name': 'yichen',
    age: { '$gt': 18, '$lt': 30 },
    '||': { 'level': [1, 2], 'age': { '$in': [3, 4] } }
};

let { segment, values } = expressionParser.parse(e);


console.log(segment);
// (name = ?) and ((age > ?) and (age < ?)) and ((level in (?)) or (age in (?)))

console.log(values);
// [ 'yichen', 18, 30, [ 1, 2 ], [ 3, 4 ] ]

Install

$ npm install object-expression-parser

Usage

配置比较操作符

  • 配置支持 >、<、=、in 的比较操作符。
let c = {
    '$gt': {          
        through: false,
        // more attribute..        
        parse: function (prop, value, originalOperator, level, context) {
            return { segment: `${prop} > ?`, values: [value] };
        }
    },
    '$lt': function (prop, value, originalOperator, level, context) {
        return { segment: `${prop} < ?`, values: [value] };
    },
    '$eq': function (prop, value, originalOperator, level, context) {
        return { segment: `${prop} = ?`, values: [value] };
    },
    '$in': function (prop, value, originalOperator, level, context) {
        return { segment: `${prop} in (?)`, values: [value] };
    }
};

配置逻辑操作符

  • 配置支持 and、or 的逻辑操作符。
let l = {
    '&&': function (expr, segments, originalOperator, level, context) {
        if (segments.length == 1) return segments[0];
        return `(${segments.join(`) and (`)})`;
    },   
    '||': function (expr, segments, originalOperator, level, context) {
        if (segments.length == 1) return segments[0];
        return `(${segments.join(`) or (`)})`;
    }
};

配置一元操作符

  • 配置支持 not 的一元操作符。
let u = {
    '$not': function (expr, segment, originalOperator, level, context) {            
        return `not(${segment})`;
    }
    
};

其它配置

// 当未指明比较操作符时视为使用 $eq 处理
let defaultOperator = '$eq';

// 当未指明逻辑操作符时视为使用 && 处理
let defaultLogicalOperator = '&&';

// 当未指明比较操作符且值为数组时使用 $in 处理
let arrayValueOperator = '$in';

// 设置操作符忽略大小写
let operatorIgnorecase = true;

构建 ObjectExpressionParser 实例

  • 使用配置参数构建 ObjectExpressionParser 实例
let expressionParser = new ObjectExpressionParser(c, l, 
                    defaultOperator, defaultLogicalOperator, 
                    arrayValueOperator, operatorIgnorecase, u);

转换表达式

let e = {
    'name': 'yichen',
    age: { '$gt': 18, '$lt': 30 },
    '||': { 'level': [1, 2], 'age': { '$in': [3, 4] } }
};

let { segment, values } = expressionParser.parse(e);


console.log(segment);
// (name = ?) and ((age > ?) and (age < ?)) and ((level in (?)) or (age in (?)))

console.log(values);
// [ 'yichen', 18, 30, [ 1, 2 ], [ 3, 4 ] ]

Operator attributes

| attribute | type | required | default | desc | |:--- | :--- | :--- | :--- | :--- | | parse | Function | yes | | 表达式核心转换方法,用于将对象(表达式)转换成字符串 | through | Boolean | | False | 设置操作符不解析子对象(表达式),而是将子对象(表达式)直接传递给parse方法 | priority | Int | | | 操作符优先级(同级多个操作符解析时,此数值小的优先解析) | single | Boolean | | False | 限定操作符仅可在被解析对象(表达式)中出现一次 | level | Int, [Int] | | | 限定操作符在对象(表达式)中的层级 | children | Object | | - parseBehavior | ParseBehavior | | Default | 设置子级对象(表达式)转换行为 | | ParseBehavior.OperatorOnly | | | 只转换操作符对象(表达式) | | ParseBehavior.PropertyOnly | | | 只转换常规属性对象(表达式) | | ParseBehavior.OperatorFirst | | | 优先转换操作符对象(表达式) | | ParseBehavior.PropertyFirst | | | 优先转换常规属性对象(表达式) | | ParseBehavior.Default | | | 按定义顺序转换(未设置此项时使用该行为) | - required | String, [String] | | | 限定子级对象(表达式)中必须包括此列表中指定的操作符 | - optional | String, Object, [String], [Object] | | | 限定子级对象(表达式)中除required列表中指定的操作符之外,只可使用此列表中指定的操作符 | -- name | String | yes | | 操作符名称 | -- autoParse| Boolean | | False | 指定当对象(表达式)中未包含name中指定的操作符时,是否自动执行此操作符的转换操作 | -- defaultTo| Any | | | 指定当autoParsetrue时,执行转换操作传递给parse的对象(表达式)或值 | siblings | String, [String] | | | 限定同级对象(表达式)中必须包括此列表中指定的操作符 | parents | String, [String] | | | 限定父级操作符必须为parents列表中的一个 | runtimeValidate | Function | | | 自定义运行时对象(表达式)或值的验证方法

Attribute 'parse' method

  • 表达式核心转换方法

ComparisonOperator

function(prop, value, originalOperator, level, context) { 
  // segment, values 
  return { segment: '', values: [] };
}

| argument | type | desc | |:--- | :--- | :--- | | prop | String | 要转换的属性名称 | value | Any | 要转换的属性值 | originalOperator | String | 原始操作符 | level | Int | 要转换的属性在对象(表达式)中所处的层级 | context | Any | 惯穿全局的上下文对象(由ObjectExpressionParser.parse方法传入)

LogicalOperator

function(expr, segments, originalOperator, level, context) { 
  // segment, values 
  return { segment: '', values: [] };
}

| argument | type | desc | |:--- | :--- | :--- | | expr | Any | 原始的对象(表达式) | segments | [String]| 转换后的子级对象(表达式)片段, 当操作符属性(attribute)throughTrue时,此参数值为undefined | originalOperator | String | 原始操作符 | level | Int | 要转换的属性在对象(表达式)中所处的层级 | context | Any | 惯穿全局的上下文对象(由 ObjectExpressionParser.parse方法传入)

UnaryOperator

function(expr, segment, originalOperator, level, context) { 
  // segment, values 
  return { segment: '', values: [] };
}

| argument | type | desc | |:--- | :--- | :--- | | expr | Any | 原始的对象(表达式) | segment | String | 转换后的子级对象(表达式)片段, 当操作符属性(attribute)throughTrue时,此参数值为undefined | originalOperator | String | 原始操作符 | level | Int | 要转换的属性在对象(表达式)中所处的层级 | context | Any | 惯穿全局的上下文对象(由 ObjectExpressionParser.parse方法传入)

ObjectExpressionParser 构造

/**
* 
* @param {Object} comparisonOperators 
* 配置比较操作符及对应处理方法
* @param {Object} logicalOperators 
* 配置逻辑操作符及对应处理方法
* @param {String} defaultOperator 
* 指定当未指明比较操作符时所使用的操作符, 此操作符必须存在于配置(comparisonOperators)中。
* 对应表达式如 { prop: 10 } 
* @param {String} defaultLogicalOperator 
* 指定当未指明逻辑操作符时所使用的操作符, 此操作符必须存在于配置(logicalOperators)中。
* 对应表达式如 { prop: { '>': 1, '<': 10 } } 
* @param {String} arrayValueOperator 
* 指定当值为数组时所使用的操作符, 此操作符必须存在于配置(comparisonOperators)中。
* 对应表达式如 { prop: [1, 2, 4, 8] } 
* @param {Boolean} operatorIgnorecase
* 操作符是否忽略大小写, 默认true
* @param {Object} unaryOperators
* 配置一元操作符及对应处理方法
*/
constructor (comparisonOperators, logicalOperators, defaultOperator,
        defaultLogicalOperator, arrayValueOperator, operatorIgnorecase = true, unaryOperators = undefined) {

}

ObjectExpressionParser.parse 方法

/**
* 
* @param {Object} expr
* 要转换的对象
*
* @param {Object} context 
* 上下文对象, 此对象将被传递至操作符处理方法中
*
* @returns {Object}
* { segment: '...', values: [] }
*/
parse(expr, context = undefined) {
    //...
}
let { segment, values } = expressionParser.parse({ 'name': 'a' });

License

MIT