Skip to content

StarPxc/expression

 
 

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

11 Commits
 
 
 
 
 
 

Repository files navigation

expression

之前做过一个数据校验服务,入参是一个文本数据,需要筛选出不符合规则的数据,格式:field1;field2;field3;....
最开始的思路是将每种类型的文件映射为java对象,然后通过hibernate-validate注解对对象属性做一系列的约束,最后校验这些对象是否满足条件约束。
其中比较头疼的一点是,同一行数据的多个字段是有关联性的,比如field1=1时field2可以为空,field1=2时field2不可以为空,虽然可以通过自定义注解,但是实现起来十分麻烦。 并且由于需要把大量的文本转换为java对象导致内存占用率很高且效率十分低下。
最痛苦的是数据规则可能会发生变化,每次都需要修改代码,并重新打包部署上线,非常麻烦。

后来在学习解释器模式时发现可以自定义表达式来解决上述问题。
根据规则预先定义好相关的表达式,然后动态配置表达式与数据字段之间的关联关系,校验时获取字段对应的表达式校验数据是否合法。
使用:

// 可以实现Reader接口自定义数据读取逻辑,可以参考FileReader
List<Map<String, String>> data = new FileReader().read();
for (Map<String, String> datum : data) {
    for (Map.Entry<String, String> entry : datum.entrySet()) {
        // 根据字段名称获取对应的表达式。(可以在数据库中建立映射关系)
        String ruleExpression = Cacheable.fieldExpressionMap.get(entry.getKey());
        if (ruleExpression == null) {
            continue;
        }
        AggregationExpression aggregationExpression = new AggregationExpression(ruleExpression);
        // interpret方法参数格式:key表示字段名,value表示字段值
        boolean interpret = aggregationExpression.interpret(datum);
        System.out.println(entry.getKey() + "=" + entry.getValue() + ": " + interpret);
    }
}
  • 简单表达式(单个字段校验):

    • 格式:filed1 > ? and field2 < ?
    • 例如:
      • (校验name字段不等于zhangsan并且age大于18): name != 'zhangsan' and age > 18
      • (校验name字段等于wangwu或者name字段等于lisi): name = 'wangwu' or name = 'lisi'
  • 数据关联性表达式(多个字段校验):

    • 格式:if[field1 = ?]{field2 = ?}
    • 例如:
      • (state=1时,校验code字段不能为空): if[state = 1]{ code != '' }
      • (state=1并且name不等于空时,校验value字段不能为空): if[state = 1 and name != '']{value != ''}
  • 内置函数:目前只写了lengthpattern这两个函数:length用来校验数据长度,pattern通过正则校验数据

    • 格式:field.函数名 = ?
    • 例如:
      • (校验name字段长度大于5): name.length > 5
      • (校验code字段满足正则): code.pattern = \wd+

About

自定义表达式解析器

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Languages

  • Java 100.0%