javax.script,始于JDK1.6,不过现在只有sun实现的javascript的解析器,难道是因为主要用来解析js语法所以归类到JEE的范畴?不过基本足够了,一般的用途主要是能解析通用的表达式就好,比如X >= 1(X作为参数传入)这样的表达式,也能利用js的函数语法,创造一个就像java的函数一样存在于内存中随时可以被调用的函数,更可以将js中的对象直接转换成java对象。
ScriptEngineManager、ScriptEngine、CompiledScript和Bindings 4个类或接口
先来看一段JS
var arrclass = new Array();
arrclass.push(new Class(20000,"计算机-软件开发"));
arrclass.push(new Class(30000,"计算机-网络/通讯"));
arrclass.push(new Class(10000,"计算机-硬件开发"));
arrclass.push(new Class(40000,"计算机-管理"));
arrclass.push(new Class(50000,"计算机-品质管理/技术支持"));
arrclass.push(new Class(320000,"电子/电器/半导体/仪器仪表"));
java代码实现解析
public void parseJS() {
//1、通过Http请求获取js的String数据,格式如上
String jsData = getJsData("url");
//2、观察js结构,自定义Class,push到数组中,java中需要定义跟js中的Class的声明
String clazz = "function Class(classId, className){ this.classId=classId;this.className=className};";
//3、初始化ScriptEngine
ScriptEngine engine = new ScriptEngineManager().getEngineByName("javascript");
//4、js中未定义返回对象,这里需要将Class数据转换成字符串的数组返回,个人觉得很别扭,不知道是理解错误还是确实如此?
//如果不这样做则直接在js后加上arrclass,cScript.evel()则返回NativeObject对象的数组
String fun = "var result = new Array() ;for(var i=0;i ;
Compilable compilable = (Compilable) engine;
//4、使用NativeArray获取数据
CompiledScript cScript;
try {
cScript = compilable.compile(clazz + jsData + fun);
NativeArray na = (NativeArray) cScript.eval();
for (int i = 0; i < na.getLength(); i++) {
NativeArray nv = (NativeArray) na.get(i, null);
System.out.println(nv.get(0, null).toString() + " " + nv.get(1, null).toString());
}
} catch (ScriptException ex) {
ex.printStackTrace();
}
}
java代码中执行js计算
public void js() { // 创建脚本引擎管理器 ScriptEngineManager sem = new ScriptEngineManager(); // 创建一个处理JavaScript的脚本引擎 ScriptEngine engine = sem.getEngineByExtension("js"); try { // 执行js公式 engine.eval("if(6>5){flag=true;}else{flag =false;}"); } catch (ScriptException ex) { ex.printStackTrace(); } //看看我们预期的反馈结果 true System.out.println(engine.get("flag")); }
Rhino是完全用Java编写的JavaScript的开放源代码实现。它通常是嵌入到Java应用程序提供给最终用户的脚本。它被镶嵌在J2SE6作为默认的Java脚本引擎。
使用Rhino来解析,感觉一切都很清晰明朗.
public void parseJS() { //1、通过Http请求获取js的String数据,格式如上 String jsData = getJsData("url"); //2、定义跟js中的Class的声明 String clazz = "function Class(classId, className){ this.classId=classId;this.className=className};"; //3、初始化Context Context cx = Context.enter(); Scriptable scope = cx.initStandardObjects(); Object result = cx.evaluateString(scope, clazz + jsData + ";arrclass", "arrclass", 1, null); System.out.println(NativeJSON.stringify(cx, scope, result, null, null)); Context.exit(); }