使用PowerMock报错java.lang.LinkageError: 装入约束违例

报错信息(限于篇幅有删减):

java.lang.LinkageError: 装入约束违例:装入器“org/powermock/core/classloader/javassist/JavassistMockClassLoader@47ab16ce”先前已启动由装入器“com/ibm/oti/vm/BootstrapClassLoader@ba626924”定义的名为“javax/security/auth/x500/X500Principal”的另一种类型的装入

\tat java.lang.ClassLoader.defineClassImpl(Native Method)
\tat java.lang.ClassLoader.defineClass(ClassLoader.java:346)
\tat org.powermock.core.classloader.javassist.JavassistMockClassLoader.loadUnmockedClass(JavassistMockClassLoader.java:90)
\tat org.powermock.core.classloader.MockClassLoader.loadClassByThisClassLoader(MockClassLoader.java:104)
\tat 、ock.core.MockInvocation.init(MockInvocation.java:31)
\tat org.powermock.core.MockInvocation.<init>(MockInvocation.java:22)
\tat org.powermock.core.MockGateway.doMethodCall(MockGateway.java:155)
\tat org.powermock.core.MockGateway.methodCall(MockGateway.java:138)

分析

    java.Lang.LinkageError 这个异常在使用多ClassLoader的应用程序时常常会遇到。
    这个错误发生的原因是同一个限定名的class类被多个不同的ClassLoader加载后,相互交叉使用导致的类冲突的情况。同一个限定名的class在不同的classLoader中属于不同的 Class实例,而JVM在加载某一个类时,需要加载所有import进入的Class,这种情况下,如果自定义的classLoader中存在与parentClassLoader需要加载相同限定名的Class时,就会抛出java.Lang.LinkageError.
    从报错信息可以看到javax/security/auth/x500/X500Principal类同时被PowerMock自定义的ClassLoader和BootStrapClassLoader加载了。

解决

使用@PowerMockIgnore使JavassistMockClassLoader忽略对javax/security/auth/x500/X500Principal的加载:

@PowerMockIgnore({"javax.security.*"})

延伸

  1. 需要让PowerMock尽量不让加载公共类;

  2. 如果出现java.lang.ClassCastException是同样的问题

Logo

腾讯云面向开发者汇聚海量精品云计算使用和开发经验,营造开放的云计算技术生态圈。

更多推荐