JDK1.8 nashorn 引擎使用
整理了近期在项目上做的一些技术研究,希望与大家共同探讨交流。
在清算项目的计算模块使用 jdk 1.8 自带的 js 引擎 nashorn 做运算。 使用过程对 nashorn 做了一些简单的测试。
使用 nashorn 编译 js 后 执行 invokeFunction 计算 ,一个简单的逻辑判断 加上一个简单的乘法运算 循环执行100w次总耗时约为600~700ms
使用 mozilla 的 rhino js引擎, 编译 js 后 执行 func.call 计算 ,总耗时约为 1400ms 左右。
nashorn 中 eval 方法编译 js 耗时很大, 实际应用时需要进行缓存处理。
除此之外, 使用 nashorn 过程一直调用不到内部的 js 方法。
这里记录下这次的使用方式
public class LiquidationUtil { private static Logger logger = LoggerFactory.getLogger(LiquidationUtil.class); public static final String _expression = "_expression"; public static final String _conditions = "_conditions"; // 生成清算规则的计算对象 public static Invocable generateLiquidationFuction(String conditions,String expressionMark,String expressionParam) throws ScriptException, NoSuchMethodException {//Liquidation StringBuffer sb = new StringBuffer(128); if(StringUtils.isEmpty(conditions)) conditions = "true"; sb.append("var ").append(_conditions).append(" = function (m,o) {") .append("\nreturn ").append(_conditions).append("(m,o,null);\n") .append("};\n"); sb.append("var ").append(_expression).append(" = function (m,o) {") .append("\nreturn ").append(_expression).append("(m,o,null);\n") .append("};\n"); // 条件 sb.append("var ").append(_conditions).append(" = function (m,o,jh) {") .append("\nreturn ").append(conditions).append(";\n") .append("};\n"); String expressionJs = expressionMap.get(expressionMark); // 计算 sb.append("var ").append(_expression).append(" = function (m,o,jh) {") .append("\nvar result=null;\n") .append("\n var ").append(expressionParam).append(";\n") .append("\n").append(expressionJs).append(";\n") .append("\nreturn result;\n") .append("};"); ScriptEngine engine = new ScriptEngineManager().getEngineByName("nashorn");//nashorn javascript engine.eval(sb.toString()); return (Invocable) engine; } private static final Map<String, String> expressionMap = new HashMap<String, String>(); static { try { String path = Thread.currentThread().getContextClassLoader().getResource("liquidation_script").getFile(); logger.info("加载清算规则js脚本 path:{}", path); File dir = new File(path); for(File script : dir.listFiles()) { String fileName = script.getName(); String filePath = script.getAbsolutePath(); logger.info("加载清算规则脚本 mark:{}\tfilePath:{}",fileName, filePath); expressionMap.put(fileName.substring(0, fileName.length()-3), readFileContent(filePath)); } } catch (IOException e) { logger.error("初始化算费规则脚本出错", e); } } public static String readFileContent(String uri) throws IOException { BufferedReader br = new BufferedReader(new FileReader(uri)); String line = ""; StringBuffer buffer = new StringBuffer(); while ((line = br.readLine()) != null) { buffer.append(line).append("\n"); } String fileContent = buffer.toString(); return fileContent; } } 调用: jsInvocable = (Invocable)LiquidationUtil.generateLiquidationFuction(conditionsJs, expressionMark, expressionParam);// 对 invocable 缓存 result = jsInvocable.invokeFunction(_conditions, mapping, orderInfo);
js 代码的格式为
var func1 = function(param1, param2){ ... } var func2 = function(param1, param2){ ... }
对这段字符串执行 eval, 得到 Invocable ,
然后可以执行 Invocable.invokeFunction("func1", param1, param2) 调用 js 方法。
低调大师中文资讯倾力打造互联网数据资讯、行业资源、电子商务、移动互联网、网络营销平台。
持续更新报道IT业界、互联网、市场资讯、驱动更新,是最及时权威的产业资讯及硬件资讯报道平台。
转载内容版权归作者及来源网站所有,本站原创内容转载请注明来源。
- 上一篇
【从入门到放弃-MySQL】CLion调试MySQL8.0源码
前言 想对的MySQL底层实现做一些了解,奈何没有用过C++不知道怎么调试一个大型项目,一日和大神交流时大神扔给我了一份《XCode调试MySQL8秘籍》。于是在几经波折(主要是因为菜)之后终于打开了MySQL的调试大门。 环境搭建 准备 MacOS: 10.14.5:因为根据大神秘籍,要使用Xcode,但Xcode下载目前只支持10.14.3,因此在10.13.6下强升的系统版本,Xcode下MySQL成功编译运行成功,但是遇到了诡异的调试无法的问题,排查无果最后转用CLionCLion:2019.1.3mysql源码:https://github.com/mysql/mysql-servercmake和boost:brew install cmake boost 编译 MySQL源码目录:/var/workspace/mysql/mysq
- 下一篇
javaWeb初识 Session持久化
Session方法invalidate() 就是从session对象池中删除sessionisNew() boolean; true刚刚创建的Session;false 不是新建的Session session本地持久化 只要正常途径关闭tomcat服务器 就会把session内容存储到本地 注意,如果你在session存放对象,那这个对象想存储在磁盘上必须实现接口 java.io.Serializable import javax.servlet.RequestDispatcher; import javax.servlet.ServletException; import javax.servlet.annotation.WebServlet; import javax.servlet.http.Cookie; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpSession; import javax.servlet.http.HttpServletRequest; import javax....
相关文章
文章评论
共有0条评论来说两句吧...
文章二维码
点击排行
推荐阅读
最新文章
- Windows10,CentOS7,CentOS8安装MongoDB4.0.16
- Red5直播服务器,属于Java语言的直播服务器
- Windows10,CentOS7,CentOS8安装Nodejs环境
- SpringBoot2整合Thymeleaf,官方推荐html解决方案
- Jdk安装(Linux,MacOS,Windows),包含三大操作系统的最全安装
- Eclipse初始化配置,告别卡顿、闪退、编译时间过长
- SpringBoot2编写第一个Controller,响应你的http请求并返回结果
- CentOS7,8上快速安装Gitea,搭建Git服务器
- SpringBoot2更换Tomcat为Jetty,小型站点的福音
- Docker使用Oracle官方镜像安装(12C,18C,19C)