当前位置: 首页 > 知识库问答 >
问题:

我如何让jjs——添加在java9中工作的开放?

何松
2023-03-14

我一直在使用来自https://apimeister.com/2015/06/27/add-jar-to-the-classpath-at-runtime-in-jjs.html在java的nashorn jjs中运行时加载类。

它在java 8中工作,但在java 9中不工作。我知道https://stackoverflow.com/a/41265267/5891192中提到的推荐命令行解决方案

根据https://stackoverflow.com/a/45970885/5891192使用=而不是标志和args之间的空格的替代语法似乎也应该是有效的(需要,因为nashorn方法通过-J--通过jjs传递jvm args...

有什么提示吗?

这很有效。。。(java 8)。。。

$ wget -q http://central.maven.org/maven2/org/apache/poi/poi/4.0.0/poi-4.0.0.jar
$ /usr/lib/jvm/java-1.8.0/bin/jjs -scripting loadit.js -- poi-4.0.0.jar
DONE

这不是...(java 9)...

$ wget -q http://central.maven.org/maven2/org/apache/poi/poi/4.0.0/poi-4.0.0.jar
$ /usr/lib/jvm/java-9/bin/jjs -J--add-opens=java.base/java.net=ALL-UNNAMED -scripting loadit.js -- poi-4.0.0.jar

Exception in thread "main" java.lang.reflect.InaccessibleObjectException: Unable to make protected void java.net.URLClassLoader.addURL(java.net.URL) accessible: module java.base does not "opens java.net" to module jdk.scripting.nashorn.scripts
at java.base/java.lang.reflect.AccessibleObject.checkCanSetAccessible(AccessibleObject.java:337)...

这是它。js。。。

// loadit.js 
function addUrlToClasspath(pth) {
  var s = java.lang.ClassLoader.getSystemClassLoader();
  var C = Java.type("java.lang.Class[]");
  var p = new C(1); p[0]  = java.net.URL.class;
  var m = java.net.URLClassLoader.class.getDeclaredMethod("addURL", p);
  var O = Java.type("java.lang.Object[]"); var a = new O(1); var f = new java.io.File(pth); m.setAccessible(true);
  var u = f.toURL(); a[0] = u; m.invoke(s, a);
}

addUrlToClasspath($ARG[0]);
print("DONE")

编辑:2018年10月23日:更正了“This not(java 9)”示例命令行

共有1个答案

曾晨
2023-03-14

正如我在上面所评论的,实际上有三个问题。

  1. 问的问题-回答:a.没有帮助(请参见下一点)b.系统级的add opens命令行选项没有进入jjs使用的Nashorn引擎)

然而,多亏了艾伦、霍尔格和我的同事菲利普的提示,我得到了我想要的变通方法。

  1. 您可以使用所需的JAR创建自己的URLClassLoader,并创建第二个nashorn引擎来传递这个类加载器(例如jjs的命令行参数)

... 下面是一个完整的例子:

// jjs -scripting ora2csv.js -- "select 'hi' from dual" jdbc:oracle:thin:@host:1521:XE user pass

function newJjsEngineWith (jars) {
  var ua = Java.type("java.net.URL[]"); var urls = new ua(jars.length);
  for(var i=0; i<jars.length; i++) {
    var u=new java.net.URL(new java.io.File(jars[i]).toURL());
    urls[i] = u;
  }
  var loader = new java.net.URLClassLoader(urls);
  java.lang.Thread.currentThread().setContextClassLoader(loader);
  var nsef = Java.type("jdk.nashorn.api.scripting.NashornScriptEngineFactory");
  var sa = Java.type("java.lang.String[]"); var args = new sa(2 + $ARG.length);
  args[0] = "-scripting"; args[1] = "--";
  for(var i=0;i<$ARG.length;i++) { args[i+2] = $ARG[i]; }
  return new nsef().getScriptEngine(args, loader);
}

var jjs = newJjsEngineWith(["ojdbc8.jar"]);

function hereDoc(f) { return f.toString().slice(14,-3); }

var code = hereDoc(function(){/*
var q = $ARG[0]; // select 'hello' from dual
var c = $ARG[1]; // jdbc:oracle:thin:@host:1521:XW
var u = $ARG[2]; // username
var p = $ARG[3]; // password
var conn = java.sql.DriverManager.getConnection(c, u, p);
var stmt = conn.createStatement(); rset = stmt.executeQuery(q);
var row=0;
while (rset.next()) {
  row++; var rowBuf = new java.lang.StringBuilder();
  var meta = rset.getMetaData();
  for(var col=0; col< meta.getColumnCount(); col++) {
    var cell = rset.getString(col+1);
    if (cell == null) { cell = ""; }
    rowBuf.append(cell.replaceAll(";",","));
    if (col < meta.getColumnCount()-1) { rowBuf.append(";"); }
  }
  print(rowBuf.toString());
}
stmt.close();
*/});

jjs.eval(code);

这适用于Java8到Java11。

$ /usr/lib/jvm/java-1.8.0/bin/jjs -scripting ora2csv.js -- "select 'hi' from dual" jdbc:oracle:thin:@host:1521:XE user pass
hi
$ /usr/lib/jvm/java-9/bin/jjs -scripting ora2csv.js -- "select 'hi' from dual" jdbc:oracle:thin:@host:1521:XE user pass
hi
$ /usr/lib/jvm/java-10/bin/jjs -scripting ora2csv.js -- "select 'hi' from dual" jdbc:oracle:thin:@host:1521:XE user pass
hi
$ /usr/lib/jvm/java-11/bin/jjs -scripting ora2csv.js -- "select 'hi' from dual" jdbc:oracle:thin:@host:1521:XE user pass
Warning: The jjs tool is planned to be removed from a future JDK release
Warning: Nashorn engine is planned to be removed from a future JDK release
hi

我欢迎大家提出建议,让这篇文章更简洁、更简洁

 类似资料:
  • 问题内容: 我已经做了几次尝试,以使包注释@ParametersAreNonnullByDefault在maven项目中为我工作,但没有成功。有人可以共享一个指向最小/示例maven项目的链接吗(或发布了pom.xml和package- info.java和demo类)? 我说的是让findbugs处理器为我实施它。 问题答案: 如何申请 在您的程序包中创建一个文件,以在其中强制执行所需的行为。

  • 我是一个新的android studio和尝试让我的第一个应用程序运行。hello world功能正常工作,但当我在第二个应用程序中按下send按钮时,应用程序就会关闭。 我在此基础上编写的网站教程可以在这里找到:https://developer.android.com/training/basics/firstapp/starting-activity 乔希

  • java.lang.NoClassDeffounderror:org/mockito/internal/creative/cglib/classimposterizer.createProxyClass(classimposterizer.java:95)(classimposterizer.imposterise(classimposterizer.imposterise:57)(classim

  • 我正在尝试在Springmvc中设置OpenSessionInViewInterceptor来修复:org.hibernate.LazyInitializationException:无法初始化代理 - 没有会话。 下面是我已经拥有的代码以及错误的来源。 AppConfig.java featured.jsp ${article.user.isSubscribed()}抛出该错误很可能是因为无法提

  • 这是我正在处理的代码,这是在一个列表中 我希望链接为“mylink/item.id”,但我尝试了以下操作,但没有成功: Create a variable called link and then . 和其他几个,但我得到的只是一个错误“不能将标记与C#代码混合”,所以我完全迷失在这里,有什么帮助吗? 这是一个带有Blazor的Razor页面

  • 问题内容: 我添加了AsyncTask来将网络操作卸载到后台线程。我需要确保UI操作位于UI线程上,因此我想在Activity中使用runOnUiThread()。 谢谢你的帮助 WifiApManager connect.java 编辑 我想在TextView中显示已处理的文本 问题答案: 我添加了AsyncTask来将网络操作卸载到后台线程。我需要确保UI操作位于UI线程上,因此我想在Acti