目前,JDK两个长期版本是8和11,因为大部分项目使用的仍是8,因此从8升级到11会遇到一些困难。html
本篇文章会基于实践遇到的问题,分类总结可能java
从Java 9开始,因为引入了JPMS(https://openjdk.java.net/projects/jigsaw/spec/),开始更精细化的包管理和模块复用,致使不少JDK默认加载的包被移除了。spring
其中咱们可能会碰到的例如:api
com.x.XMLUtils
:private static void getXmlFromObject(Book book) throws JAXBException { Marshaller marshallerObj = JAXBContext.newInstance(Book.class).createMarshaller(); marshallerObj.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true); StringWriter sw = new StringWriter(); marshallerObj.marshal(book, sw); }
sun.misc.BASE64Encoder
,假设项目中位于com.x.EncodeUtil
:String encodedString = new BASE64Encoder().encode(inputString.getBytes());
经过JAVA 9 之后自带的工具jdeps
,查看解决方法:闭包
jdeps target\APP.jar com.x.ReflectionUtils -> com.sun.crypto.provider JDK internal API (java.base) com.x.XMLUtils -> javax.xml.bind java.xml.bind com.x.EncodeUtil -> sun.misc JDK internal API (JDK removed internal API)
deps --jdk-internals target\pre-jpms.jar ... JDK Internal API Suggested Replacement ---------------- --------------------- sun.misc.BASE64Encoder Use java.util.Base64 @since 1.8 sun.reflect.Reflection Use java.lang.StackWalker @since 9
能够看出,jdeps
这个工具,能够找出过时的APi替换方法,也能够找出缺失的模块。oracle
对于JAXB,经过jdeps
命令咱们能够知道须要添加java.xml.bind
这个模块,经过添加java启动参数--add-modules java.xml.bind
便可解决。maven
可是,这样添加参数,不是长久的办法,仍是添加Maven依赖,比较靠谱:ide
<dependency> <groupId>javax.xml.bind</groupId> <artifactId>jaxb-api</artifactId> <version>2.3.1</version> </dependency>
对于Spring Boot 2.x.x,能够添加依赖:模块化
<dependency> <groupId>org.glassfish.jaxb</groupId> <artifactId>jaxb-runtime</artifactId> </dependency>
对于Spring Cloud体系,须要的全部依赖是:工具
<dependency> <groupId>javax.xml.bind</groupId> <artifactId>jaxb-api</artifactId> <version>${jaxb.version}</version> </dependency> <dependency> <groupId>com.sun.xml.bind</groupId> <artifactId>jaxb-impl</artifactId> <version>${jaxb.version}</version> </dependency> <dependency> <groupId>org.glassfish.jaxb</groupId> <artifactId>jaxb-runtime</artifactId> <version>${jaxb.version}</version> </dependency> <dependency> <groupId>com.sun.xml.bind</groupId> <artifactId>jaxb-xjc</artifactId> <version>${jaxb.version}</version> </dependency> <dependency> <groupId>javax.activation</groupId> <artifactId>activation</artifactId> <version>${activation.version}</version> </dependency>
报错:maven编译报错:java.lang.ExceptionInInitializerError: com.sun.tools.javac.code.TypeTags
这是由于Java 9以后的字节码编译特性变化,须要升级到1.18.+的版本才能够。
JDK 8 到JDK 11有不少参数变化,能够总结为两类参数的变化,一是GC相关的(GC配置调优更加简单),二是日志相关的,日志统一到了一块儿,不像以前那么混乱
具体请参考:
每一个说明参考三部分:
启动的时候可能会报以下异常:
WARNING: An illegal reflective access operation has occurred WARNING: Illegal reflective access by org.springframework.cglib.core.ReflectUtils$1 (file:/D:/Repositories/maven/org/springframework/spring-core/5.0.13.RELEASE/spring-core-5.0.13.RELEASE.jar) to method java.lang.ClassLoader.defineClass(java.lang.String,byte[],int,int,java.security.ProtectionDomain) WARNING: Please consider reporting this to the maintainers of org.springframework.cglib.core.ReflectUtils$1 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
建议启动的时候加上--illegal-access=warn
(其余可选的还有"permit" "warn" "debug" "deny"),这里建议是只报警(WARN),以后留意升级这些相关的依赖,这样避免之后JDK升级禁止这种反射,同时保证目前可用。