Byte Buddy 是一个代码生成和操作库,用于在 JAVA 应用程序运行时创建和修改 Java 类,而无需编译器的帮助 。除了 Java 类库附带的代码生成实用程序外,Byte Buddy 还允许创建任意类,并且不限于实现用于创建运行时代理的接口 。一、前言相对于小傅哥之前编写的字节码编程; ASM、Javassist 系列,Byte Buddy 玩法上更加高级,你可以完全不需要了解一个类和方法块是如何通过 指令码 LDC、LOAD、STORE、IRETURN... 生成出来的 。就像它的官网介绍;
Byte Buddy 是一个代码生成和操作库,用于在 Java 应用程序运行时创建和修改 Java 类,而无需编译器的帮助 。除了 Java 类库附带的代码生成实用程序外,Byte Buddy 还允许创建任意类,并且不限于实现用于创建运行时代理的接口 。此外,Byte Buddy 提供了一种方便的 API,可以使用 Java 代理或在构建过程中手动更改类 。
- 无需理解字节码指令,即可使用简单的 API 就能很容易操作字节码,控制类和方法 。
- 已支持Java 11,库轻量,仅取决于Java字节代码解析器库ASM的访问者API,它本身不需要任何其他依赖项 。
- 比起JDK动态代理、cglib、Javassist,Byte Buddy在性能上具有一定的优势 。
除了这些简单的介绍外,还可以通过官网:https://bytebuddy.NET,去了解更多关于 Byte Buddy 的内容 。
【一个更简单的字节码增强框架,谁看了案例都会使用!】好!那么接下来,我们开始从 HelloWorld 开始 。深入了解一个技能前,先多多运行,这样总归能让找到学习的快乐 。
二、开发环境
- JDK 1.8.0
- byte-buddy 1.10.9
- byte-buddy-agent 1.10.9
- 本章涉及源码在:itstack-demo-bytecode-2-01,可以关注公众号:bugstack虫洞栈,回复源码下载获取 。你会获得一个下载链接列表,打开后里面的第17个「因为我有好多开源代码」,记得给个Star!
public class Hi {public static void main(String[] args) {System.out.println("Byte-buddy Hi HelloWorld By 小傅哥(bugstack.cn)");}}
那么我们接下来就通过使用动态字节码生成的方式,来创建出可以输出 HelloWorld 的程序 。新知识点的学习不要慌,最主要是找到一个可以入手的点,通过这样的一个点去慢慢解开整个程序的面纱 。
四、技术实现1. 官网经典例子在我们看官网文档中,从它的介绍了就已经提供了一个非常简单的例子,用于输出 HelloWorld,我们在这展示并讲解下 。
案例代码:
String helloWorld = new ByteBuddy().subclass(Object.class).method(named("toString")).intercept(FixedValue.value("Hello World!")).make().load(getClass().getClassLoader()).getLoaded().newInstance().toString();System.out.println(helloWorld);// Hello World!
他的运行结果就是一行,Hello World!,整个代码块核心功能就是通过 method(named("toString")),找到 toString 方法,再通过拦截 intercept,设定此方法的返回值 。FixedValue.value("Hello World!") 。到这里其实一个基本的方法就通过 Byte-buddy ,改造完成 。接下来的这一段主要是用于加载生成后的 Class 和执行,以及调用方法 toString() 。也就是最终我们输出了想要的结果 。那么,如果你不能看到这样一段方法块,把我们的代码改造后的样子,心里还是有点虚 。那么,我们通过字节码输出到文件,看下具体被改造后的样子,如下;
编译后的Class文件,ByteBuddyHelloWorld.class
public class HelloWorld {public String toString() {return "Hello World!";}public HelloWorld() {}}
在官网来看,这是一个非常简单并且能体现 Byte buddy 的例子 。但是与我们平时想创建出来的 main 方法相比,还是有些差异 。那么接下来,我们尝试使用字节码编程技术创建出这样一个方法 。
推荐阅读
- 边缘计算的未来:五个值得关注的趋势
- 2023年的五大网络安全趋势
- 新时代的 SSR 框架破局者:qwik
- 解决冗余代码的三种方法,让你的代码更上一层楼
- 介绍一种可以让Linux中存储具有弹性容量的方法
- 如何编写高效的CSS代码?这五个技巧一定要知道!
- 一文讲解MySQL的主从复制
- 一个超适合初学者的轻量级Java开发工具!
- 你会让ChatGPT控制你的智能家居吗?
- 5G将如何影响AR和VR?