如何为非法反射访问警告抛出异常?
How can I throw an exception for an illegal reflective access warning?
如何为非法反射访问警告抛出异常?例如,考虑以下代码:
import org.apache.commons.lang3.builder.*;
class Test {
public static void main(String[] args) {
System.out.println(ReflectionToStringBuilder.toString(Boolean.TRUE));
}
}
此代码向 System.err 打印以下警告:
WARNING: An illegal reflective access operation has occurred
WARNING: Illegal reflective access by org.apache.commons.lang3.builder.ReflectionToStringBuilder (file:/Users/brianschack/eclipse-workspace/User%20Libraries/com
mons-lang3-3.7/commons-lang3-3.7.jar) to field java.lang.Boolean.value
WARNING: Please consider reporting this to the maintainers of org.apache.commons.lang3.builder.ReflectionToStringBuilder
WARNING: Use --illegal-access=warn to enable warnings of further illegal reflective access operations
WARNING: All illegal access operations will be denied in a future release
Boolean.TRUE 是一个非常简单的值,我真的不需要 ReflectionToStringBuilder。但更复杂的类型(例如 HashMap)会打印相同的警告。我选择 Boolean.TRUE 是为了简化这个例子。
当我搜索此警告消息时,我找到了将其报告给软件包维护者、避免警告或完全禁用它的建议 (JDK9: An illegal reflective access operation has occurred. org.python.core.PySystemState)。
我想为警告抛出异常,以便获得非法访问发生位置的堆栈跟踪。然后我可以更改代码以避免导致警告的非法访问。我还想做一个单元测试,将来检查警告。
我根据 Whosebug 问题 JUnit test for System.out.println(). This involves setting System.err to a ByteArrayOutputStream and then examining the contents. But unfortunately, according to 尝试测试打印到 System.err,IllegalAccessLogger 在 JVM bootstrap 期间获得对 System.err 的引用,然后我才能改变它。
我也试过关闭 System.err,但打印到关闭的流似乎静默失败而不是抛出异常。请注意,以下代码的输出不包含字符串 "err-2":
代码:
class Test {
public static void main(String[] args) {
System.out.println("Start");
System.err.println("err-1");
System.err.close();
System.err.println("err-2");
System.out.println("End");
}
}
输出:
Start
err-1
End
- 打开Eclipse开发环境
- 选择运行菜单–>运行配置...–>Java应用程序–>(您的配置)–>参数。
- 在 VM 参数文本框中,键入“--illegal-access=deny”[0]。
- 单击“应用”按钮。
- 单击 运行 按钮。
- 非法访问会抛出 java.lang.reflect.InaccessibleObjectException [1].
[0] http://mail.openjdk.java.net/pipermail/jigsaw-dev/2017-May/012673.html
[1] http://docs.oracle.com/javase/9/docs/api/java/lang/reflect/InaccessibleObjectException.html
如何为非法反射访问警告抛出异常?例如,考虑以下代码:
import org.apache.commons.lang3.builder.*;
class Test {
public static void main(String[] args) {
System.out.println(ReflectionToStringBuilder.toString(Boolean.TRUE));
}
}
此代码向 System.err 打印以下警告:
WARNING: An illegal reflective access operation has occurred
WARNING: Illegal reflective access by org.apache.commons.lang3.builder.ReflectionToStringBuilder (file:/Users/brianschack/eclipse-workspace/User%20Libraries/com
mons-lang3-3.7/commons-lang3-3.7.jar) to field java.lang.Boolean.value
WARNING: Please consider reporting this to the maintainers of org.apache.commons.lang3.builder.ReflectionToStringBuilder
WARNING: Use --illegal-access=warn to enable warnings of further illegal reflective access operations
WARNING: All illegal access operations will be denied in a future release
Boolean.TRUE 是一个非常简单的值,我真的不需要 ReflectionToStringBuilder。但更复杂的类型(例如 HashMap)会打印相同的警告。我选择 Boolean.TRUE 是为了简化这个例子。
当我搜索此警告消息时,我找到了将其报告给软件包维护者、避免警告或完全禁用它的建议 (JDK9: An illegal reflective access operation has occurred. org.python.core.PySystemState)。
我想为警告抛出异常,以便获得非法访问发生位置的堆栈跟踪。然后我可以更改代码以避免导致警告的非法访问。我还想做一个单元测试,将来检查警告。
我根据 Whosebug 问题 JUnit test for System.out.println(). This involves setting System.err to a ByteArrayOutputStream and then examining the contents. But unfortunately, according to
我也试过关闭 System.err,但打印到关闭的流似乎静默失败而不是抛出异常。请注意,以下代码的输出不包含字符串 "err-2":
代码:
class Test {
public static void main(String[] args) {
System.out.println("Start");
System.err.println("err-1");
System.err.close();
System.err.println("err-2");
System.out.println("End");
}
}
输出:
Start
err-1
End
- 打开Eclipse开发环境
- 选择运行菜单–>运行配置...–>Java应用程序–>(您的配置)–>参数。
- 在 VM 参数文本框中,键入“--illegal-access=deny”[0]。
- 单击“应用”按钮。
- 单击 运行 按钮。
- 非法访问会抛出 java.lang.reflect.InaccessibleObjectException [1].
[0] http://mail.openjdk.java.net/pipermail/jigsaw-dev/2017-May/012673.html
[1] http://docs.oracle.com/javase/9/docs/api/java/lang/reflect/InaccessibleObjectException.html