首页 > 编程语言 >一个Bug,让我发现了Java界的.AJ(锥)

一个Bug,让我发现了Java界的.AJ(锥)

时间:2023-07-08 22:31:57浏览次数:34  
标签:aj Java AJ jar IDEA AspectJ 切面 Aspect Bug

目录


  • 一、前言
  • 二、满脑子都是骚操作
  • 1. 遇到问题
  • 2. 发现问题
  • 3. 排查问题
  • 三、如何正确使用 Aspect 的 .aj 类
  • 1. 安装 AspectJ
  • 2. AspectJ 插件
  • 3. 添加依赖 aspectjrt.jar
  • 4. 配置AspectJ编译器
  • 5. 案例测试
  • 四、总结
  • 五、系列推荐


一、前言

话我放这,踩过的坑越多头发越少!

说来也是奇怪,只要是学编程的,从初次接触的 Java 到安装 JDK、IDEA、MYSQL, 再到接触 Spring、MyBatis、RPC、MQ,哪怕有时候再浅的坑也会跳进去尝尝鲜,一遍抓着头发,一手点着鼠标也几乎是你的常态。你的键盘里总是有很多被抓碎的头发!

但,哪怕是抓了这么头发,还是遇到了一个满脑子都是骚操作的小伙。傅哥,我的切面怎么拦截不到?我是照着你的《SpringBoot 中间件设计和开发》专栏写的,你给我看看吧,我都弄了一天了

接下来我带着大家一起看看什么是快乐星球,他是怎么一顿骚操作让切面拦截不到的!

二、满脑子都是骚操作

1. 遇到问题

上周,谢飞机(化名)发过来了自己的手撸的中间件源码,说这代码都没有啥怎么就不能切面呢?

一个Bug,让我发现了Java界的.AJ(锥)_jar

  • 最开始我大意了,让谢飞机发了一些代码截图。
  • 看截图的代码,这完全就和我写的中间件里的代码一毛一样,没啥问题呀,包路径也能扫描到,咋就不能切面了?
  • 我说你打个断点调试下,看看怎么切不到了呢?嘿,调试了,直接通过,就是没切面到。
  • 此时我思考了JDK版本、环境配置、Spring上下文、切面的定义、包的路径以及这小子是否忽悠我?
  • 最后我抱着这小子忽悠我的心里,把源码要过来了。

2. 发现问题

看了几遍源码没发现问题,开始调试,还真它哈拉哨的不进这个切面,接下来;

  • 谢飞机的源码保留,复制出来一份新的。
  • 我的目的要先让他跑起来,再研究。接下来我把自己的工程里的 DoJoinPoint 拷贝过来粘贴进去,噗察一下贴进去了,没提示替换,虽然有报错但两个类能共存,如下:
  • 这就神奇了哈,我当时怀疑是不它那 DoJoinPoint 不是一个正经 Java 类,路径不对?有看不见的特殊字符?
  • 既然发现这个类不对,那行先删掉。让程序先跑起来,确保除了这个类其他的内容没有问题,这样也好排查问题。
  • 还别说,去掉这个错误类,程序可以正常运行,拦截到切面内容了。
  • 既然程序能跑了,我就想着这可以看看问题出在哪了,没想到就只打开个文件夹,就发现了一个神奇的AJ!这货压根就不是 Java 类!

3. 排查问题

要不是IDEA把 .aj 这货显示成 C 类的图标,可能早就发现问题了。紧接着把这错误类的截图发给了谢飞机,问它你是怎么创建的?他说实话了

  • 谢飞机先说自己偷懒了,哈哈哈,让人怪不好意思的!
  • 他说在创建 DoJoinPoint 时,看到一个 Aspect 的选项,以为这个就是创建切面的快捷操作,如图;
  • 创建完成以后发现有点不对,不是 class 类型的,是个 aspect,于是他手动把 aspect 改成了 class,如图;
  • 所以,谢飞机实际创建出来的是一个 aspect 的以 .aj 结尾的类,并不是一个正经的 Java 类,所以切面不到,也根本没有对应的 class 文件。

三、如何正确使用 Aspect 的 .aj 类

AspectJ,简称 AJ 我自己说的

AspectJ 其实也是 AOP 的一种实现技术,功能类似于拦截器,在集成在 IntelliJ IDEA 开发工具里。在使用 IntelliJ IDEA 编写 AspectJ 代码之前需要本机先安装 AspectJ 工具包。否则你的 .aj 类不能运行,同时IDEA类显示出来的 .aj 类,也是C的标识

接下来我们就来聊聊关于这个东西怎么使用,别再被 .aj 骗了。

1. 安装 AspectJ

在使用 AspectJ 之前,需要去官网下载一个安装包,地址:https://www.eclipse.org/aspectj/downloads.php 如果官网下载得很慢,可以从我提供的源码中获取,也可以从其他途径搜索下载 aspectj-1.9.4.jar

下载完成安装;

  • 双击安装
  • 命令安装 java -jar aspectj-1.9.4.jar
  • 配置说明:没有配置,傻瓜式下一步就可以了

一个Bug,让我发现了Java界的.AJ(锥)_Java_02

  • 默认配置安装完成以后会在C盘创建出一个文件夹 C:\aspectj1.9,包括:bin、doc、lib等,后面我们就会使用到这些内容。

2. AspectJ 插件

在专业版 IDEA 中开发 AspectJ,需要安装以下两个插件:

  • Spring AOP/@AspectJ
  • AspectJ Support

一个Bug,让我发现了Java界的.AJ(锥)_jar_03

3. 添加依赖 aspectjrt.jar

开始之前需要在项目中添加 aspectjrt.jar 依赖,aspectjrt.jar 即 AspectJ 安装目录中lib目录下的jar包。你可以复制到工程中引入,也可以直接引入

一个Bug,让我发现了Java界的.AJ(锥)_jar_04

  1. 在工程上鼠标右键,点击 Open Module Setting 打开 Project Structure
  2. 点击 Libraries 选项卡,和上面的 + 号,创建 New Project Library
  3. 选择 C:\aspectj1.9\lib\aspectjrt.jar 路径,点击即可配置完成

4. 配置AspectJ编译器

IDEA 默认使用 javac 编译器,这里需要配置 AspectJ 的编译器 ajc,在 IDEA 中做相应配置。

一个Bug,让我发现了Java界的.AJ(锥)_System_05

  1. 打开 IDEA -> File -> Settings 对话
  2. 选择 Build,Execution,Deployment -> Compiler -> Java Compiler
  3. Use complier:选择 Ajc
  4. 在 Path to aspectjtools.jar 里配置路径 C:\aspectj1.9\lib\aspectjtools.jar

5. 案例测试

创建 Aspect 类

public aspect DoAspect {

    pointcut logPointcut():call(* ApiTest.hi(..));

    void around():call(void ApiTest.hi(..)){
        System.out.println("call 开始...");
        proceed();
        System.out.println("call 结束...");
    }

    before(): logPointcut(){
        System.out.println("方法执行 before");
    }

    after(): logPointcut(){
        System.out.println("方法执行 after");
    }

}

测试类

public class ApiTest {

    public void hi(){
        System.out.println("Hi Aspect");
    }

    public static void main(String[] args) {
        ApiTest apiTest = new ApiTest();
        apiTest.hi();
    }

}

测试结果

call 开始...
方法执行 before
Hi Aspect
call 结束...
方法执行 after

Process finished with exit code 0
  • 到这,才是一个关于 Aspect 类的正确打开方式,关于 Aspect 的使用也可以尝试搞搞,此篇还只是关于此类切面写法的一个入门。

四、总结

  • 你的代码越粗犷、越豪放、越骚气,几乎你遇到的问题也是越多的,可能就是因为没有遵守一定的研发执行规范,所以遇到的这些有点傻的问题,几乎会浪费掉你一个上午或者一天。
  • 但有些时候如果你能认真对待你弄出来的bug,深入分析下它是如何产生的,并把它复现出来一点点深入研究下,可能也会得到意想不到的收获,也说不定。所以凡是认真,凡事没有坏事。
  • 关于切面、关于源码、关于开发,可能并不应该只注重于功能实现,甚至有时候要想办法逃离日复一日没有成长的工作内容。多在那些有价值的技术上下功夫,那你的收获也是最多的。

标签:aj,Java,AJ,jar,IDEA,AspectJ,切面,Aspect,Bug
From: https://blog.51cto.com/u_16173732/6663839

相关文章

  • Java中AQS的原理与实现
    目录1:什么是AQS?2:AQS都有那些用途?3:我们如何使用AQS4:AQS的实现原理5:对AQS的设计与实现的一些思考1:什么是AQS​ 随着计算机的算力越来越强大,各种各样的并行编程模型也随即踊跃而来,但当我们要在并行计算中使用共享资源的时候,就需要利用一种手段控制对共享资源的访问和修改来......
  • 2012 javascript
    javascript  学习列表   BodyButtonCanvasEvent                                                                 02/07FormFrameFramesetIFrameImage                     ......
  • 已经配置了`JAVA_HOME`环境变量,但Tomcat仍然提示未配置该变量
    检查JAVA_HOME变量的正确性:确保JAVA_HOME的值指向JavaJDK的安装路径,而不是JRE的路径。例如,JAVA_HOME应该是类似于C:\ProgramFiles\Java\jdk1.8.0_XXX的路径,而不是C:\ProgramFiles\Java\jre1.8.0_XXX。检查环境变量配置位置:确保将JAVA_HOME变量添加到系统环境变量中,而不仅......
  • java通过注解和反射优雅的实现数据脱敏
     数据脱敏是对分为数据库数据脱敏与接口脱敏。其中数据库入库数据脱敏方式我们一般采用对称加密来实现数据脱敏,接口脱敏我们一般用遮罩方式实现数据脱敏比如用“*”占位。本文章主要介绍接口脱敏方式。 1.定义一个自定义注解类importjava.lang.annotation.*;@Target(Elem......
  • java入门概念个人理解之package与import浅析
    java入门概念个人理解之package与import浅析由于近来学习java,遇到了一些在c++上没有的概念,将它记http://录下,以自己复习使用,如有不理解妥之处,望大家批评指导。资料均由网上经过自己整合理解而来,如有侵权请通知我将起删除即可。我就以package与import开始吧。package的作用其实就是......
  • 一次简单的Java服务性能优化,实现压测 QPS 翻倍
    背景前段时间我们的服务遇到了性能瓶颈,由于前期需求太急没有注意这方面的优化,到了要还技术债的时候就非常痛苦了。在很低的QPS压力下服务器load就能达到10-20,CPU使用率60%以上,而且在每次流量峰值时接口都会大量报错,虽然使用了服务熔断框架Hystrix,但熔断后服务却迟迟不......
  • Java学习
    JDBC核心api使用步骤:1注册驱动,依赖的jar包,进行安装2.建立连接connection3.创建发送SQL语句对象4.statement对象(小汽车),发送SQL语句到数据库并且返回获取结果5.解析结果集6.销毁(释放)资源:释放connection 释放statement 释放resultset......
  • Java字符串比较 == 和 equals方法的区别
    今天在排除一个bug的时候出现了一个很低级但是也很容易被忽视的错误,在此写了一个小例子做记录。首先我先说一下错误的场景,我读取了一段json数据,并使用JSONObject的实例对象的getString方法去拿到了一个value数据,由于我忽视了getString方法的返回值是一个String对象,所以我在后面......
  • java Swing和AWT是什么关系?
    1)AWT是基于本地方法的C/C++程序,其运行速度比较快;Swing是基于AWT的Java程序,其运行速度比较慢。2)AWT的控件在不同的平台可能表现不同,而Swing在所有平台表现一致。参考:https://www.cnblogs.com/RUI2022/p/16975881.html参考2:https://www.cnblogs.com/2008nmj/p/16257373.html(ge......
  • 如何实现Java转账借口的具体操作步骤
    Java转账接口实现指南引言作为一名经验丰富的开发者,我将向你介绍如何实现Java转账接口。在本文中,我将为你展示整个流程,并提供逐步指导,帮助你理解每一步需要做什么。让我们开始吧!流程概述下表展示了实现Java转账接口的步骤:步骤描述1创建一个Java类2添加转账方法......