Javassist 修改 jar 包里的 class 文件

前言

Javassist 是一个用于处理 Java 字节码的类库,可以用以修改 class 文件或 jar 包里的 class 文件。

简单来说我们用Java编写的代码是放在 java 格式的代码文件里,在编译的时候会编译为 class 格式的字节码文件,然后一般所有 class 文件会打成一个 jar 包对外提供服务,

如果我们没有源码但是想修改 class 文件或 jar 包里的文件是很不方便的,而 Javassist 类库就可以很方便的修改 class 和 jar 包。

Javassist 官网
Javassist Github地址

一、Maven依赖

xml 复制代码
        <dependency>
            <groupId>org.javassist</groupId>
            <artifactId>javassist</artifactId>
            <version>3.28.0-GA</version>
        </dependency>

二、假设jar包中的 Student.class 类如下

假设 tempTest-1.0-SNAPSHOT.jar 包里有 Student.class 如下:

java 复制代码
package com.haitang.test.service;

public class Student {
    public Student() {
    }

    public String name() {
        return "张三";
    }

    public boolean isStudent(int id, String name) {
        return id > 0 && id < 10 && name != null;
    }

    public void printName(int id, String name, int age) {
        System.out.println("学生姓名是:" + name);
    }
}

三、修改class文件

修改上面的 Student.class 里的 isStudent 方法 使其方法里返回 true

java 复制代码
import javassist.CannotCompileException;
import javassist.ClassPool;
import javassist.CtClass;
import javassist.CtMethod;
import javassist.NotFoundException;


import java.io.IOException;

public class MainServer {
    public static void main(String[] args) throws NotFoundException, CannotCompileException, IOException {
	    //获取 jar 包里的要修改的 class 文件,这里获取 com.haitang.test.service 下的 Student.class
	    ClassPool pool = ClassPool.getDefault();
        pool.insertClassPath("C:\\myCode\\mavenTest\\lib\\tempTest-1.0-SNAPSHOT.jar");
        CtClass cc = pool.get("com.haitang.test.service.Student");

		//获取该类里的所有方法
        CtMethod[] methodA = cc.getDeclaredMethods();
		//遍历所有方法
        for (CtMethod ctMethod : methodA) {
            //获取方法的参数信息
            CtClass[] ps = ctMethod.getParameterTypes();
			//如果该方法有两个参数,第一个是int 类型,第二个是String类型,并且方法名是 isStudent ,那么就将方法体修改为 return true;
            if (ps.length == 2 && "int".equals(ps[0].getName()) && "java.lang.String".equals(ps[1].getName()) && "isStudent".equals(ctMethod.getName())) {
                ctMethod.setBody("{return true;}");
            }
        }
		//将修改后的 clsss 文件保存到下面的路径
        cc.writeFile("C:\\myCode\\mavenTest\\lib\\");
    }
}

将修改后的 clsss 文件进行复制,使用 Bandzip 这样的解压缩软件对 tempTest-1.0-SNAPSHOT.jar 进行压缩文件预览,找到 Student.class 所在的位置,把修改后的 Student.class 粘贴覆盖原来的 Student.class

这样 tempTest-1.0-SNAPSHOT.jar 包里 Student 类的 isStudent 方法就被修改为用于返回 true 了。


其他操作可参考:
Java字节码操作神器:Javassist入门指南
javassist使用指南

Javassist官方文档翻译

相关推荐
mldong3 小时前
引擎从不发一条消息:jeeflow 的两类扩展点与消息模块的分工
java·架构
君顾14 小时前
智慧零售实战指南:从技术架构到落地方案全解析
java·开发语言·零售
zhanghe6874 小时前
es的密码带有特殊字符,导出
java
pnoker5 小时前
IoT DC3 概念解读:把设备抽象成一套语义模板——位号、指令、事件与面向智能体的设备建模
java·人工智能·物联网·iot·dc3
my_realmy5 小时前
Java SE 基础学习笔记(一):面向对象、继承多态、抽象接口与异常(JDK 8)
java·多线程·并发··生产者消费者模式
天远数科5 小时前
风险治理实战:基于天远车信盟出险构建自动化理赔核保流水线
java·网络·人工智能·自动化
骇客野人6 小时前
SpringBoot电商系统用户注册、登录、留存及数据埋点设计与落地实施方案
java·spring boot·后端
qiuhaipeng16 小时前
Claude code 升级后上下文长度变短问题
java·前端·数据库
wxwx_bscxy3227 小时前
基于Python新冠疫情可视化分析系统的设计与实现
java·数据库·spring boot·python·微信小程序·sqlite
evans在进步8 小时前
Tomcat NIO 工作原理详解:从 Acceptor、Poller 到容器处理链
java·tomcat·nio