专题导航
一、java调用groovy及groovy中如何使用springBean
二、java运行groovy脚本内存问题及解决
三、java运行groovy脚本并发问题及解决
四、java运行groovy工具类
maven依赖(groovy)
<dependency>
<groupId>org.codehaus.groovy</groupId>
<artifactId>groovy-all</artifactId>
<version>2.4.16</version>
</dependency>
<dependency>
<groupId>org.kohsuke</groupId>
<artifactId>groovy-sandbox</artifactId>
<version>1.7</version>
</dependency>
工具类
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.util.ObjectUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.crypto.digest.DigestUtil;
import groovy.lang.Binding;
import groovy.lang.Script;
import groovy.util.GroovyScriptEngine;
import lombok.Data;
import java.io.File;
import java.io.IOException;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
/**
* java调用groovy工具类(engine方法为执行指定文件)
* @author 非琴不是筝
* @date 2020-09-14
*/
public class GroovyUtil {
private static final Map<String, Md5Script> scriptMap = new ConcurrentHashMap<>();
public static Object engine(String filePath, String fileName, Map<String, Object> variable) {
Binding binding = new Binding();
if (CollectionUtil.isNotEmpty(variable)) {
variable.entrySet().stream().filter(entry -> StrUtil.isNotBlank(entry.getKey()) && ObjectUtil.isNotEmpty(entry.getValue()))
.forEach(entry -> binding.setVariable(entry.getKey(), entry.getValue()));
}
Object result;
Script script = getScriptInstance(filePath, fileName);
//对象锁,因为要赋值,所以一个对象同时只能被一个线程调用
synchronized (script){
script.setBinding(binding);
result = script.run();
}
return result;
}
private static Script getScriptInstance(String filePath, String fileName) {
String fileAbPath = filePath+File.separator+fileName;
File file = new File(fileAbPath);
String md5Hex = DigestUtil.md5Hex(file);
Md5Script md5Script = scriptMap.getOrDefault(fileAbPath,null);
if (md5Script!=null&&md5Hex.equals(md5Script.getMd5())) {
return md5Script.getScript();
} else {
Script script = null;
try {
GroovyScriptEngine engine = new GroovyScriptEngine(filePath);
script = engine.createScript(fileName, new Binding());
} catch (IOException e) {
e.printStackTrace();
throw new RuntimeException("文件不存在");
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException("生成script文件失败");
}
scriptMap.put(fileAbPath, new Md5Script(md5Hex,script));
return script;
}
}
@Data
private static class Md5Script{
private String md5;
private Script script;
public Md5Script(String md5, Script script) {
this.md5 = md5;
this.script = script;
}
}
}
其他工具如hutool,lombok可根据自己需求替换