jjs.exe 和服务加载器
jjs.exe and ServiceLoader
jjs.exe 的 运行 脚本是否应该能够像任何 Java 程序一样使用 ServiceLoader
定位服务?
我已将案例简化为以下脚本:
function dump (stream)
{
(new BufferedReader(new InputStreamReader(stream))).lines().forEach(function (x) { print(x); });
}
var BufferedReader = Java.type("java.io.BufferedReader");
var InputStreamReader = Java.type("java.io.InputStreamReader");
var ServiceLoader = Java.type("java.util.ServiceLoader");
var Sts = Java.type("prodist.sts.Sts");
print(Sts);
// A
var stsConfigStream = Sts.class.getResourceAsStream("/META-INF/services/prodist.sts.Sts");
dump(stsConfigStream);
// B
var StsImpl = Java.type("prodist.sts.internal.StsImpl");
print(new StsImpl());
// C
var stsLoader = ServiceLoader.load(Sts.class);
var stsIterator = stsLoader.iterator();
stsIterator.next();
// D
我调用 jjs.exe
在命令行上设置 Class-Path。我的脚本正确地找到并打印了 A 点的接口名称。它定位了服务描述资源;当我转储资源的内容时,我在 B 点看到了预期的内容。我确保预期的实现 class 在 C 点可用。
在 D 点,程序抛出 NoSuchElementException
,我将其解释为 ServiceLoader 未找到接口的任何服务描述资源。
这应该有效吗?
我错过了什么吗?
您需要设置线程上下文class加载程序。从您的 jjs class 路径引用任何 class,获取它的 Class 对象,然后获取它的 class 加载器。然后将该加载程序设置为线程上下文 class 加载程序。这应该在您使用服务加载器 API:
之前完成
var StsClass = Java.type("prodist.sts.Sts").class;
java.lang.Thread.currentThread().contextClassLoader = StsClass.classLoader;
jjs.exe 的 运行 脚本是否应该能够像任何 Java 程序一样使用 ServiceLoader
定位服务?
我已将案例简化为以下脚本:
function dump (stream)
{
(new BufferedReader(new InputStreamReader(stream))).lines().forEach(function (x) { print(x); });
}
var BufferedReader = Java.type("java.io.BufferedReader");
var InputStreamReader = Java.type("java.io.InputStreamReader");
var ServiceLoader = Java.type("java.util.ServiceLoader");
var Sts = Java.type("prodist.sts.Sts");
print(Sts);
// A
var stsConfigStream = Sts.class.getResourceAsStream("/META-INF/services/prodist.sts.Sts");
dump(stsConfigStream);
// B
var StsImpl = Java.type("prodist.sts.internal.StsImpl");
print(new StsImpl());
// C
var stsLoader = ServiceLoader.load(Sts.class);
var stsIterator = stsLoader.iterator();
stsIterator.next();
// D
我调用 jjs.exe
在命令行上设置 Class-Path。我的脚本正确地找到并打印了 A 点的接口名称。它定位了服务描述资源;当我转储资源的内容时,我在 B 点看到了预期的内容。我确保预期的实现 class 在 C 点可用。
在 D 点,程序抛出 NoSuchElementException
,我将其解释为 ServiceLoader 未找到接口的任何服务描述资源。
这应该有效吗? 我错过了什么吗?
您需要设置线程上下文class加载程序。从您的 jjs class 路径引用任何 class,获取它的 Class 对象,然后获取它的 class 加载器。然后将该加载程序设置为线程上下文 class 加载程序。这应该在您使用服务加载器 API:
之前完成var StsClass = Java.type("prodist.sts.Sts").class;
java.lang.Thread.currentThread().contextClassLoader = StsClass.classLoader;