【发布时间】:2020-03-23 18:08:40
【问题描述】:
我一直在使用 Nashorn 进行类似 awk 的批量数据处理。这个想法是,有很多传入的数据,一行一行地,一个接一个。每一行都由命名字段组成。这些数据由存储在外部某处且可由用户编辑的用户定义脚本处理。脚本很简单,例如 if( c>10) a=b+3,其中 a、b 和 c 是传入数据行中的字段。数据量真的很大。代码是这样的(展示用例的例子):
ScriptEngine engine = new NashornScriptEngineFactory().getScriptEngine(
new String[]{"-strict", "--no-java", "--no-syntax-extensions", "--optimistic-types=true"},
null,
scr -> false);
CompiledScript cs;
Invocable inv=(Invocable) engine;
Bindings bd=engine.getBindings(ScriptContext.ENGINE_SCOPE);
bd.remove("load");
bd.remove("loadWithNewGlobal");
bd.remove("exit");
bd.remove("eval");
bd.remove("quit");
String scriptText=readScriptText();
cs = ((Compilable) engine).compile("function foo() {\n"+scriptText+"\n}");
cs.eval();
Map params=readIncomingData();
while(params!=null)
{
Map<String, Object> res = (Map) inv.invokeFunction("foo", params);
writeProcessedData(res);
params=readIncomingData();
}
现在 nashorn 已经过时了,我正在寻找替代品。谷歌搜索了几天,但没有找到完全符合我的需求。要求是:
- 速度。有很多数据,所以它应该非常快。所以我也认为,预编译是必须的
- 应在 linux/openJDK 下工作
- 至少在数据访问/代码执行方面支持沙盒
很高兴拥有:
- 简单的类 c 语法(不是 lua;)
- 支持沙盒处理 CPU 使用率
到目前为止,我发现 Rhino 仍然存在(最后一次发布日期为 2020 年 1 月 13 日),但我不确定它是否仍然受支持以及它有多快 - 我记得,Java 切换到 Nashorn 的原因之一是速度。就我而言,速度非常重要。还找到了 J2V8,但不支持 linux。 GraalVM 看起来有点矫枉过正,还没有得到如何使用它来完成这样的任务 - 如果它适合的话,可能需要进一步探索,但看起来它是完整的 jvm 替代品,不能用作库。
不是必须是javascript,也许还有其他选择。 谢谢。
【问题讨论】:
-
GraalVM 的 JavaScript 可以用作库:graalvm.org/docs/reference-manual/languages/JavaScript/user/… 您可以限制脚本应该可以访问的内容,例如 Java 类、创建线程等。也比 Nashorn 更快:medium.com/graalvm/…
-
@OlegŠelajev 给你这么多,你帮了我很多!真的,刚刚试过,真的很快!您能否指出我在哪里可以阅读有关沙盒的信息?
-
我将所有这些信息添加到不阅读 cmets 的人的答案中
-
@OlegŠelajev 好主意
标签: java performance sandbox embedding