J. Brazile:
私はからの反射技術を使用している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代わりに、フラグとその引数の間にスペースを=を使用して、この代替構文は、ためにも経由のJVM引数を渡すnashorn方法の必要(有効でなければなりませんように思えますJJS経由-J--...
任意のヒント?
この作品...(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)...
そして、ここでloadit.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日:「これはしない(javaの9)」例のコマンドラインを修正
J. Brazile:
私は上記のコメント通り、実際に3つの問題があります。
- 尋ねて質問 - 回答:A。B(次のポイントを参照)を助けていません。システムレベルJJSが使用するNashornエンジンにその方法を作るていないコマンドラインオプションを追加し、開きます)
- アペンドツー・システム・クラス・ローダーのアプローチはjava9で始まるとにかく動作しません- Javaの9、ClassLoader.getSystemClassLoaderとの互換性の問題
- Javaの-11で始まる、JJS自体は廃止宣言されています
しかし、からのヒントのおかげで@Alan、@Holgerや同僚@Philippeは、私が回避策で欲しいものです。
- あなたは必要なjarファイルを使用して、独自のURLClassLoaderを作成し、このクラスローダに通過する第2 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);
これはJavaの11を介してJavaの8のために動作します。
$ /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
私はこれより簡潔かつ少ない作るための任意の提案を歓迎pukeyを