当前位置:   article > 正文

Classfinal问题处理及改造升级(一)_classfinal解密

classfinal解密

classfinal介绍

ClassFinal是一款java class文件安全加密工具,支持直接加密jar包或war包,无需修改任何项目代码,兼容spring-framework;可避免源码泄漏或字节码被反编译。

Gitee : ClassFinal: Java字节码加密工具

  • 无需修改原项目代码,只要把编译好的jar/war包用本工具加密即可。
  • 运行加密项目时,无需求修改tomcat,spring等源代码。
  • 支持普通jar包、springboot jar包以及普通java web项目编译的war包。
  • 支持spring framework、swagger等需要在启动过程中扫描注解或生成字节码的框架。
  • 支持maven插件,添加插件后在打包过程中自动加密。
  • 支持加密WEB-INF/lib或BOOT-INF/lib下的依赖jar包。
  • 支持绑定机器,项目加密后只能在特定机器运行。
  • 支持加密springboot的配置文件。

背景

接到一项任务,由于涉及知识产权保护,需要对关键代码片段进行加密处理(核心库)。因此,我选择了ClassFinal工具来实现字节码层面的加密。

使用步骤

  1. 核心库工程引入插件依赖
    1. <plugin>
    2. <!-- https://gitee.com/roseboy/classfinal -->
    3. <groupId>net.roseboy</groupId>
    4. <artifactId>classfinal-maven-plugin</artifactId>
    5. <version>1.2.1</version>
    6. <configuration>
    7. <password>000000</password><!--加密打包之后pom.xml会被删除,不用担心在jar包里找到此密码-->
    8. <packages>com.yourpackage,com.yourpackage2</packages>
    9. </configuration>
    10. <executions>
    11. <execution>
    12. <phase>package</phase>
    13. <goals>
    14. <goal>classFinal</goal>
    15. </goals>
    16. </execution>
    17. </executions>
    18. </plugin>
  2. 运行mvn package时会在target下自动加密生成yourproject-encrypted.jar
  3. 将核心库依赖到spring boot项目中
  4. 配置启动命令
    -javaagent:yourproject-encrypted.jar="-pwd 000000"

问题改造

        IDEA中启动运行一切正常,打包成jar包启动后运行到核心包代码块解密失败,代码无法正常执行?

问题原理

        Spring FatJar使用了LaunchedURLClassLoader去加载FatJar中的class和jar嵌套的jar(即jar in jar),显然按照这个逻辑核心包代码块也交由LaunchedURLClassLoader去加载。但是我们使用了javaagent:yourproject-encrypted.jar去执行字节码解密,而代理包中的class是默认交由AppClassloader去加载的,Classfinal默认生成的代理包又包含了所有的核心包代码块(只需用到Classfinal解密代码),这就导致了问题的出现。因为LaunchedURLClassLoader是AppClassLoader的子类加载器,当核心包里面的类调用到被LaunchedURLClassLoader加载的类时会报ClassNoFound。

举个例子:
一、核心库代码String2DateConvert

  1. public class String2DateConvert implements Converter<String, Date> {
  2. @Override
  3. public Date convert(String s) {
  4. if (StringUtils.isNotBlank(s)) {
  5. DateFormat dtf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
  6. try {
  7. return dtf.parse(s);
  8. } catch (ParseException e) {
  9. log.error("日期格式转换失败; {}", e.getMessage());
  10. }
  11. }
  12. return null;
  13. }
  14. }

二、spring boot项目引用核心包代码

  1. public void test() {
  2. String2DateConvert string2DateConvert = new String2DateConvert();
  3. string2DateConvert.convert("2023-01-01");
  4. }

三、其中核心库引用的StringUtils来自apache.commons.lang3包,该第三方包是交由外部LaunchedURLClassLoader。根据双亲委派机制,是无法从AppClassLoader拿到LaunchedURLClassLoader加载的类,因此会报:org.apache.commons.lang.StringUtils NoClassDefFoundError

解决方式

其实就是将代理包中的非解密代码删除掉

源码修改如下:先打包核心包,再打包代理包

预告:如何支持多重jar包解密,即spring boot包也进行一层加密?Classfinal问题处理及改造升级(二)

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/小舞很执着/article/detail/810151
推荐阅读
相关标签
  

闽ICP备14008679号