无法使用Nashorn在Java List上调用hasOwnProperty

时间:2014-11-12 20:07:08

标签: java java-8 nashorn

我有一个执行很多javascript服务器端的应用程序,我正在尝试从Rhino转换为Nashorn但是我的脚本遇到了麻烦。使用Rhino我总是会将函数的任何参数转换为JSON字符串,但这确实很慢。使用Nashorn我试图将参数作为Java对象传递,但它们似乎并不从Javascript的Object类型继承函数。这是一个示例方法,它说明了我的问题,其中hasOwnProperty在我的数组上不可用:

public String printArrayValues() throws ScriptException, NoSuchMethodException {

  String script =
      "function printArrayValues(objArray) {\n" +
      "  var result = '';\n" +
      "  for(var obj in objArray) {\n" +
      "    if(objArray.hasOwnProperty(obj)) {\n" +
      "      result = result + ' ' + objArray[obj];\n" +
      "    }\n" +
      "  }\n" +
      "  return result;\n" +
      "}";

  List<String> data = Arrays.asList(new String[]{ "one", "two", "three"});

  ScriptEngine scriptEngine = new NashornScriptEngineFactory().getScriptEngine();
  scriptEngine.eval(script);
  String result = (String) ((Invocable) scriptEngine).invokeFunction("printArrayValues", data);
}

这里对invokeFunction的调用抛出异常:

javax.script.ScriptException: TypeError: [one, two, three] has no such function "hasOwnProperty" in <eval> at line number 4

如果我在浏览器中调用相同的函数,我会得到我期望的结果:

> printArrayValues(["one", "two", "three"]);
> " one two three"

我是否有某种方法可以实现这一点,所以我真的可以使用这些Java对象而不将它们转换为JSON字符串,然后将其评估为Javascript对象?

2 个答案:

答案 0 :(得分:2)

您无法以这种方式使用Java数组。 Java数组是&#34;硬连线&#34;对象。与普通对象不同,它们没有方法,它们支持[]运算符,而对象无法运行。

Article about Nashorn at Oracle说明您需要在javascript中使用Java.toJava.from方法才能将Java数组更改为Javascript数组。

答案 1 :(得分:2)

使用Java.from()将Java List转换为Javascript Array,然后对其进行操作。

  String script =
  "function printArrayValues(objArray) {\n" +
  "  var result = '';\n var temp = Java.from(objArray);" +
  "  for(var obj in temp ) {\n" +
  "    if(temp .hasOwnProperty(obj)) {\n" +
  "      result = result + ' ' + temp [obj];\n" +
  "    }\n" +
  "  }\n" +
  "  return result;\n" +
  "}";