Cha*_*ffy 5 clojure classloader
我已经回复了正在运行的服务,并且有一个var指向一个加载了插件的类加载器(my.package已安装).
REPL使用的DynamicClassLoader不包含我希望与之交互的插件; 我希望能够使用从插件加载的类,尽管有这个限制.
以下作品:
=> (.loadClass plugin-classloader "my.package.MyClass")
my.package.MyClass
Run Code Online (Sandbox Code Playgroud)
...而以下不会(显式覆盖线程上下文类加载器):
=> (do
(.setContextClassLoader (Thread/currentThread) plugin-classloader)
(Class/forName "my.package.MyClass"))
ClassNotFoundException my.package.MyClass java.net.URLClassLoader$1.run (URLClassLoader.java:202)
Run Code Online (Sandbox Code Playgroud)
...这两者都没有(显式覆盖线程上下文类加载器和 clojure.lang.Compiler/LOADER引用):
=> (let [dcl (clojure.lang.DynamicClassLoader. plugin-classloader)]
(.setContextClassLoader (Thread/currentThread) dcl)
(with-bindings* {clojure.lang.Compiler/LOADER dcl}
(eval '(pr-str (Class/forName "my.package.MyClass")))))
ClassNotFoundException my.package.MyClass java.net.URLClassLoader$1.run (URLClassLoader.java:202)
Run Code Online (Sandbox Code Playgroud)
......这也不是:
=> my.package.MyClass
CompilerException java.lang.ClassNotFoundException: my.package.MyClass, compiling:(NO_SOURCE_PATH:0)
Run Code Online (Sandbox Code Playgroud)
Class.forName()设置时不应该使用线程上下文类加载器?我正试图调用第三方代码做内省魔术; 即使应该设置线程上下文类加载器,有问题的工具也会因ClassNotFoundExceptions而失败.
在我明确设置上下文类加载器的情况下,堆栈跟踪演示了Clojure的DynamicClassLoader(而不是plugin-classloader var中的BundleClassLoader)正在使用中:
=> (e)
java.lang.ClassNotFoundException: my.package.MyClass
at java.net.URLClassLoader$1.run (URLClassLoader.java:202)
java.security.AccessController.doPrivileged (AccessController.java:-2)
java.net.URLClassLoader.findClass (URLClassLoader.java:190)
clojure.lang.DynamicClassLoader.findClass (DynamicClassLoader.java:61)
java.lang.ClassLoader.loadClass (ClassLoader.java:306)
java.lang.ClassLoader.loadClass (ClassLoader.java:247)
java.lang.Class.forName0 (Class.java:-2)
java.lang.Class.forName (Class.java:169)
Run Code Online (Sandbox Code Playgroud)
clojure.lang.Compiler/eval,由REPL调用clojure.lang.Compiler/LOADER,而不是线程本地类加载器.在eval调用之前,适当的类加载器需要绑定到此var - 因此添加一个包装层可解决此问题:
=> (let [dcl (clojure.lang.DynamicClassLoader. plugin-classloader)]
(with-bindings {clojure.lang.Compiler/LOADER dcl}
(eval '(Class/forName "my.package.MyClass"))))
my.package.MyClass
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
1251 次 |
| 最近记录: |