15

動的プロキシを使用しようとすると、次の例外が表示されます

 com.intellij.rt.execution.application.AppMain DynamicProxy.DynamicProxy
Exception in thread "main" java.lang.IllegalArgumentException: interface Interfaces.IPerson is not visible from class loader
    at java.lang.reflect.Proxy.getProxyClass(Proxy.java:353)
    at java.lang.reflect.Proxy.newProxyInstance(Proxy.java:581)
    at DynamicProxy.Creator.getProxy(Creator.java:18)
    at DynamicProxy.DynamicProxy.main(DynamicProxy.java:54)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)

それを解決するために私が何をする必要があるかについての考え

4

3 に答える 3

12

これが Web アプリケーションの場合、動的プロキシを作成するときに Web アプリケーション クラスローダーを使用する必要があります。したがって、たとえば次の代わりに:

Proxy.newProxyInstance(
  ClassLoader.getSystemClassLoader(),
  new Class < ? >[] {MyInterface.class},
  new InvocationHandler() {
    // (...)
});

試す:

Proxy.newProxyInstance(
  this.getClass().getClassLoader(), // here is the trick
  new Class < ? >[] {MyInterface.class},
  new InvocationHandler() {
    // (...)
});

たとえば、Tomcat クラス ローダーの階層 (他の Web コンテナーも同様です) は次のとおりです。

      Bootstrap
          |
       System
          |
       Common
       /     \
  Webapp1   Webapp2 ... 

また、Web アプリケーションの /WEB-INF/classes ディレクトリにあるクラスとリソース、および Web アプリケーションの /WEB-INF/lib ディレクトリの下の JAR ファイルにあるクラスとリソースを含む webapp クラスローダーです。

于 2012-11-14T13:31:15.807 に答える
6

結果のインスタンスDynamicProxyを実行しようとすると、プロキシを作成したときに渡したものとは異なります。つまり、同じ名前の 2 つのクラス オブジェクトがあり、プロキシはどちらが正しいかわかりません (同じかどうかは問題ではありません)。Class.forName(youInterfaceClass.getName())java.lang.Class

通常、これは、プロキシしようとしているインターフェイスが、2 つの異なるクラスローダー (つまり、Tomcat の「共通」と「アプリケーション」) を介してロードされたライブラリにある場合に発生します。

これで問題が解決しない場合は、アプリケーションに関する詳細情報を投稿してください。特にアプリケーション サーバー、Spring、OSGi を使用している場合は。

于 2008-10-17T06:31:00.780 に答える