Java8 Nashorn实现Java调用javascript代码

最近项目需要,利用java执行动态语言,首先想到的是支持js。

1.从打印Hello World开始

Java8 引入Nashorn实现javascript调用,比如使用java运行一段js实现“Hello World”打印:

package com.iflytek.research.jsdemo;

import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import javax.script.ScriptException;

public class NashornTest {

    public static void main(String[] args) {
        // 加载nashorn执行引擎
        ScriptEngine engine = new ScriptEngineManager().getEngineByName("nashorn");
        try {
            engine.eval("var str = ‘Hello World‘;"
                    + "print(str);");
        } catch (ScriptException e) {
            e.printStackTrace();
        }
    }

}

上述代码成功打印了“Hello World”, 现实场景中,script代码大多来自文件,编辑test.js

var str = ‘Hello World‘;
print(str);

将java读取方式改为从文件加载

// 加载nashorn执行引擎
        ScriptEngine engine = new ScriptEngineManager().getEngineByName("nashorn");
        try {
            FileReader scriptFile = new FileReader("test.js");
            engine.eval(scriptFile);
        } catch (ScriptException e) {
            e.printStackTrace();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }

运行后,仍然能正常打印

2.传递参数给javascript代码

可以使用SimpleBindings类来实现参数传递,改写test.js

var str = ‘Hello ‘;
print(str + name);

上述代码name变量就可以使用SimpleBindings来传递,具体实现

// 加载nashorn执行引擎
        ScriptEngine engine = new ScriptEngineManager().getEngineByName("nashorn");
        try {
            FileReader scriptFile = new FileReader("test.js");
            SimpleBindings simpleBindings = new SimpleBindings();
            simpleBindings.put("name", "Nashorn");
            engine.eval(scriptFile, simpleBindings);
        } catch (ScriptException e) {
            e.printStackTrace();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        }

再次运行代码 打印

Hello Nashorn

这个参数在js中是全局可见的,比如将它放到函数作用域中也可以正常读取到

var good = function() {
    return name + ‘ is Good‘;
}
print(good());

打印结果

Nashorn is Good

3.指定调用的函数

在加载js文件后,可以使用Invocable接口的invokeFunction方法, 修改js文件

var good = function(name) {
    print(name + ‘ is Good‘);
}

在给函数传参直接在invokeFunction方法添加参数即可,不再需要使用SimpleBindings

public static void main(String[] args) {
        // 加载nashorn执行引擎
        ScriptEngine engine = new ScriptEngineManager().getEngineByName("nashorn");
        try {
            FileReader scriptFile = new FileReader("test.js");
            engine.eval(scriptFile);
            Invocable in = (Invocable) engine;
             in.invokeFunction("good","Nashorn");
        } catch (ScriptException e) {
            e.printStackTrace();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            e.printStackTrace();
        }
    }

如果要传递对象也是妥妥的

var good = function(person) {
    print( ‘name: ‘ + person.name);
}
Map<String,Object> person = new HashMap<>();
            person.put("name", "nashorn");
             in.invokeFunction("good",person);

4.获取js返回值

同样调用invokeFunction

test.js

var getPerson = function() {
    var person = {
            name : "Zhan San",
            age: 18
    }
    return person;
}
public static void main(String[] args) {
        // 加载nashorn执行引擎
        ScriptEngine engine = new ScriptEngineManager().getEngineByName("nashorn");
        try {
            FileReader scriptFile = new FileReader("test.js");
            engine.eval(scriptFile);
            Invocable in = (Invocable) engine;
            JSONObject personJson =(JSONObject)JSONObject.toJSON(in.invokeFunction("getPerson"));
            System.out.println(personJson.toJSONString());
        } catch (ScriptException e) {
            e.printStackTrace();
        } catch (FileNotFoundException e) {
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            e.printStackTrace();
        }
    }

这里json引用了fastjson包,执行之后获得结果

{"name":"Zhan San","age":18}

原文地址:https://www.cnblogs.com/ljgeng/p/10179766.html

时间: 2024-11-01 17:20:42

Java8 Nashorn实现Java调用javascript代码的相关文章

java调用javascript :js引擎rhino

java调用javascript :js引擎rhino JavaJavaScriptEclipse脚本SQL 前段时间,在浏览javaeye论坛,看见有人征集如何在java中运行数学表达式.结果方案五花八门:1.jakarta commons JEXL. 2.Beanshell3.Java Math Expression Parser jep 4.parse combinator jparsec 5.jdk 6.0的 script6.利用SQL 7.自己写语法分析如果自己写语法分析,没有个200

在HTML标签&lt;a/&gt;中调用javascript代码

<a/>标签的“href”属性可以是一个有效的URL,表示跳转的目的地,除此之外,href还可以是一段javascript代码.当为“href”设置javascript代码时,格式如下:<a href=”javascript:……;” />.当点击这种形式的超链接时,浏览器将执行“href”中设置的javascript代码.需要注意的是,如果代码执行之后的返回值是一个有效值(除“undefined”之外的值)的话,当前页面的内容将会被返回值替换! W3C标准不推荐使用这种方法来调用

Selenium3 + Python3自动化测试系列十——调用JavaScript代码

调用JavaScript代码 一.调用JavaScript代码方法 Selenium在对浏览器操作时会有自动化代码中不稳定的部分,经常出错的部分,可以将这部分对网页元素进行操作的代码换成对应的JavaScript脚本,由于浏览器原生的支持JavaScript,JavaScript代码直接在浏览器内核中执行,就不会出现元素不在所点击的位置等错误,可以大大提高自动化用例执行的稳定性和执行效率. 调用JavaScript方法有两种: 1.execute_script():此是同步方法,用它执行js代码

如何使用网页开发自己的app,在网页中的按钮与自己的java代码绑定来实现打电话即javascript代码调用java代码,和java代码来调用javascript代码

1首先是如何在自己的app里用网页显示,这样可以较快的更新界面而不需要让客户端升级,方法如下: xml文件: <WebView android:layout_width="fill_parent" android:layout_height="fill_parent" android:id="@+id/web_v" /> 2在activity里绑定网页: public class MainActivity extends Action

Java 调用 Javascript 函数的范例

在Java 7 以后,可以在Java代码中调用javascript中的函数,请看下面的例子: package com.lee; import java.io.FileNotFoundException; import java.io.FileReader; import java.util.Scanner; import javax.script.Bindings; import javax.script.Invocable; import javax.script.ScriptContext;

01_JNI是什么,为什么使用,怎么用JNI,Cygwin环境变量配置,NDK案例(使用Java调用C代码)

1 什么是JNI JNI Java本地开发接口 JNI是一个协议,这个协议用来沟通java代码和外部的本地代码(C/C++) 通过这个协议,java代码就可以调用外部的C/C++代码,外部的C/C++代码也可以调用Java代码. 2 为什么用JNI 1  JNI扩展了java虚拟机的能力,驱动开发(wifi-hotspot)2.3无线热点共享 2  Native code效率高,数学运算,实时渲染的游戏上,音视频处理(极品飞车),opengl,ffmpeg 3  复用代码(文件压缩,人脸识别)

使用JNA,让java调用原生代码

JNA定义: JNA:java Native Access,是SUN公司开发的基于JNI的框架.JNI使得Java可以调用原生的c或者c++代码. JNA与JNI(Java Native Interface)的差别: 性能:JNA在性能上不如JNI.由于JNA是在JNI的基础上封装了一层. 移植性:JNA的可移植性要好于JNI,由于开发人员不须要再编写作为代理的动态链接库. 使用:JNI使用native关键字,使用一个个java方法映射原生方法,利用System.loadLibrary:JNA使

JDK8中Java调用Javascript脚本引擎动态定义与执行代码

import java.lang.*; import java.util.Arrays; import java.util.List; import javax.script.Invocable; import javax.script.ScriptEngine; import javax.script.ScriptEngineManager; public class ScriptEngineTest { public static void main(String[] args) throw

JNI Java调用C代码 示例

Activity public class MainActivity extends ListActivity {     static {         System.loadLibrary("hello");// 在java代码中引入libs目录下的库函数,文件名为[libhello.so].注意,引入时的文件名要去掉前面的lib和后面的.so                 System.loadLibrary("hellocpp");     }