本文转载自微信公众号《JAVA架构日记》,作者如盟科技。转载本文请联系JAVA架构日记公众号。1.前言大家好,我是如梦科技(春哥L.cm),大家可能在很多开源项目中见过我。今天就带领大家实践一下spring-native。内容硬核,建议大家坐稳支持(关注,收藏)。我们一直在关注Graalvm和Springnative,发表了多篇公众号文章。对于demo关卡的使用,这里就不做过多介绍了。有兴趣的可以查看之前的文章SpringNative入门。2、springnative2.1graalvm原生镜像配置生成springnative工程(mica-native-test)编译完成后,会生成如下graalvm原生镜像配置。可以配置动态代理、反射、资源文件和序列化。2.2springnativehintsspringnative开放了很多hints,用于配置nativeimage不支持的动态代理、反射、资源文件等。主要提示如下:这些命中会将我们的自定义配置生成为proxy-config.json、reflect-config.json、resource-config.json、serialization-config.json。3、mica的适配本节文章以mica的部分组件为例,介绍springnativehints的使用。3.1mica-ip2regionmica-ip2region涉及一个ip地址信息的ip2region.db文件,所以我们需要自定义资源文件的配置。首先在mica-ip2region中添加spring-native依赖。org.springframework.experimentalspring-native${spring-native.version}提供然后在Ip2regionConfiguration代码中添加NativeHint注解配置ip2region.db资源文件。@Configuration(proxyBeanMethods=false)@EnableConfigurationProperties(Ip2regionProperties.class)@NativeHint(resources=@ResourceHint(patterns="^ip2region/ip2region.db"))publicclassIp2regionConfiguration{@BeanpublicIp2regionSearcherip2regionSearcher(ResourceLoaderresourceLoader,Ip2regionPropertiesLopertiesnewIties){returnSearmpleraderpropertiesnewIties){returnSearmpleraderproperties)公共类Ip2regionConfiguration;}}再次编译springnative项目(mica-native-test),可以看到resource-config.json中增加了ip2region.db文件。最后运行工程:testmica-ip2region(完美):3.2mica-captchamica-captcha主要是几个需要添加的字体文??件,配置如下。具体过程同上,这里不再赘述。@NativeHint(resources=@ResourceHint(patterns="^fonts/.*.ttf"))注:由于验证码涉及字体和awt,所以会涉及到以下两个问题。如果用docker编译运行原生镜像,会遇到字体问题。需要安装字体:yuminstallfontconfig-y&&fc-cache--force详情参见:https://github.com/oracle/graal/issues/817java.lang.UnsatisfiedLinkError:noAwtinjava.library.pathexception在graalvm21.1.0mac上仍然是一个问题。详见:https://github.com/oracle/graal/issues/28423.3mica-caffeine使用了很多caffeine中的unsafe,所以添加mica-caffeine依赖后,mica-native-test可以启动成功。折腾我半天。有各种错误报告,但有提示。我们可以根据提示添加提示,如下图:image.png在下面添加了这么多提示后终于可以启动成功了!!!@NativeHint(types={@TypeHint(types=CaffeineAutoCacheManager.class,access=AccessBits.ALL),@TypeHint(types=CaffeineCacheManager.class,access=AccessBits.ALL),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.UnsafeAccess",fields=@FieldHint(name="UNSAFE",allowUnsafeAccess=true),access=AccessBits.PUBLIC_METHODS),@TypeHint(types=Thread.class,access=AccessBits.DECLARED_FIELDS),@TypeHint(typeNames)="com.github.benmanes.caffeine.cache.PS",fields={@FieldHint(name="key",allowUnsafeAccess=true),@FieldHint(name="value",allowUnsafeAccess=true)},access=AccessBits.DECLARED_CONSTRUCTORS),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.PSA",fields=@FieldHint(name="accessTime",allowUnsafeAccess=true),access=AccessBits.DECLARED_CONSTRUCTORS),@TypeHint(typeNames)="com.github.benmanes.caffeine.cache.PSW",字段=@FieldHint(name="writeTime",allowUnsafeAccess=true),access=AccessBits.DECLARED_CONSTRUCTORS),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.StripedBuffer",字段={@FieldHint(name="tableBusy",allowUnsafeAccess=true)},access=AccessBits.ALL),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.PSWMS",access=AccessBits.DECLARED_CONSTRUCTORS),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.SSA",access=AccessBits.ALL),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.SSLA",access=AccessBits.DECLARED_CONSTRUCTORS),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.SSLMSW",access=AccessBits.DECLARED_CONSTRUCTORS),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.SSMSW",access=AccessBits.DECLARED_CONSTRUCTORS),@TypeHint(类型名称)="com.github.benmanes.caffeine.cache.BoundedBuffer",access=AccessBits.ALL),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.BoundedBuffer$RingBuffer",access=AccessBits.ALL),@TypeHint(typeNames="com.github.benmanes.caffeine.cache.BLCHeader$DrainStatusRef",字段=@FieldHint(name="drainStatus",allowUnsafeAccess=true),access=AccessBits.ALL)})恭喜,没事了???真的吗???Caffeinecache又开始报异常了!!!至此我不想再折腾了4.总结Spring-native目前还在孵化阶段,如果是没有使用第三方组件的简单项目,可以试试,建议大家等待稍大一点的项目,我们也会持续关注和输出相关文章[责任编辑:吴晓燕电话:(010)68476606]