在项目中需要使用el表达式,对map进行解析后,将这个map作为root对象进行el解析。
条件表达式
模板:参数名称==值
,如果是字符那么值加单引号,譬如:age==88 || city=='福州'
假设有一个Map
Map<String, Object> param = new LinkedHashMap<>();
param.put("city", "福州");
param.put("age", 88);
- 数值是否相等
age == 88
//复杂写法:#root['age']== 88
> 结果:true
- 字符是否相等
city == '北京'
//复杂写法:#root['city']== '福州'
> 结果:true
- 多值比较表达式
age==88 && city=='福州'
//复杂写法:#root['age']== 88 && #root['city']== '福州'
> 结果:true,因age是88
age==888 && city=='福州'
> 结果:false
代码如下
- 解析方式
import org.springframework.context.expression.MapAccessor;
import org.springframework.expression.Expression;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.expression.spel.support.StandardEvaluationContext;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
public class SpelUtil {
/**
* spel解析器
*/
private static final SpelExpressionParser parser = new SpelExpressionParser();
/**
* spel缓存
*/
private static final ConcurrentHashMap<String, Expression> expressionMap = new ConcurrentHashMap<>(256);
/**
* 获取表达式值
*
* @param param
* @param elExpression #root['city']== '福州' || city=='福州'
* @return
*/
public static Object getValue(Map<String, Object> param, String elExpression) {
Expression expression = getExpression(elExpression);
StandardEvaluationContext context = new StandardEvaluationContext(param);
//关键:如果没有配置MapAccessor,那么只能用['c']['a']这种解析方式
context.addPropertyAccessor(new MapAccessor());
Object value = expression.getValue(context);
return value;
}
/**
* 验证SpEL[不符合]
*
* @param param 参数
* @param elExpression 表达式
* @return
*/
public static boolean verifyNotSpEL(Map<String, Object> param, String elExpression) {
return !verifySpEL(param, elExpression);
}
/**
* 验证SpEL[符合]
*
* @param param 参数
* @param elExpression 表达式
* @return
*/
public static boolean verifySpEL(Map<String, Object> param, String elExpression) {
try {
Object value = SpelUtil.getValue(param, elExpression);
if (!(value instanceof Boolean)) {
return false;
}
return true;
} catch (Exception e) {
return false;
}
}
/**
* 从缓存中获取spel编译表达式
*
* @return SpelExpression
*/
private static Expression getExpression(String el) {
Expression expression = expressionMap.get(el);
if (expression != null) {
return expression;
}
return expressionMap.computeIfAbsent(el, k -> parser.parseRaw(el));
}
}
- 单元调试
package com;
import com.istrong.form.common.utils.SpelUtil;
import org.junit.Test;
import java.io.IOException;
import java.util.LinkedHashMap;
import java.util.Map;
public class Spel2UtilTest {
@Test
public void verifyGeoJson() {
Map<String, Object> param = new LinkedHashMap<>();
param.put("city", "");
param.put("age", 88);
String elExpression = "#root['city']== ''";
elExpression = "#root['age']== 88";
System.out.println(SpelUtil.getValue(param, elExpression));
elExpression = "city==''";
System.out.println(SpelUtil.getValue(param, elExpression));
elExpression = "age==88 && city==''";
System.out.println(SpelUtil.getValue(param, elExpression));
elExpression = "#root['age']== 888 && #root['city']== ''";
System.out.println(SpelUtil.getValue(param, elExpression));
}
}