aop的实现原理_非Spring管理Bean如何添加AOP呢?

前几天有个朋友问了一个问题,觉得可以给大家分享一下。

问题如下图

b5e3b696d0b292f366451b54dd7d4e74.png

归其根本这是个历史项目,里面有很多的类并没有交给spring管理,但现在需要统一添加日志。

面对这样的问题,其实只要了解AOP的原理,就会有多种方法。AOP都是基于动态代理来实现,而动态代理常见的就是cglib和java动态代理,不了解的可以看下之前干货君写的文章

java动态代理为什么需要基于接口

cglib动态代理对类没有任何限制吗?

但此两种方法似乎在这样的场景不好实现,需要修改大量的代码,那么有没有什么好的方案呢?

答案当然是有。

首先要清楚的是AOP的底层实现原理就是字节码,我们只需要从字节码层面,就一定可以解决这样的问题。因此可以利用编译期增强和运行期增强,常见的方案有两种,一种Java Agent技术,另一种 AspectJ方案。

Java Agent

Java Agent中文名字叫做java 探针,可以在运行java时指定探针程序,对原程序无侵入,常见的一些APM工具都会这样,如skywalking,后续有机会给大家介绍下。如下图

37c23d8140f96a8b3dfa56ae3d1fe648.png

java agent的主要原理就是利用JVMTI(JVM Tool Interface),JVM用来暴露一些供用户扩展的接口集合,因此可以在此处做一些运行期字节码增强。

Java Agent内容比较多,有很多大家熟悉的工具都是基于它去做的,例如阿里的arthas。本文就不介绍了,后期会给大家详细介绍下Java Agent。

AspectJ方案

可以利用aspectj + javac来编译织入代码,也可以利用maven插件aspectj-maven-plugin,下面利用AspectJ注解 + aspectj-maven-plugin来实战一下。

aspectj-maven-plugin官网 http://www.mojohaus.org/aspectj-maven-plugin/usage.html

引入依赖

编译增强,依赖此jar

import org.aspectj.lang.annotation.Aspect;

import org.aspectj.lang.annotation.Before;

import org.aspectj.lang.annotation.Pointcut;

@Aspect

public class Aop {

@Pointcut("execution(* com.ganhuojun.gracefulshutdown.controller..*.*(..))")

public void pointcut1(){

}

@Before("pointcut1()")

public void before(){

System.out.println("controller before");

}

}

定义注解

注意:该注解不要交给spring管理

org.codehaus.mojo

aspectj-maven-plugin

1.11

1.8

1.8

UTF-8

src/main/java

**/ServiceAop.java

compile

配置maven插件

org.codehaus.mojo

aspectj-maven-plugin

1.11

1.8

1.8

UTF-8

src/main/java

**/ServiceAop.java

compile

排除spring的aop

如果对spring aop比较熟悉的都知道,spring的aop也是基于AspectJ的,因此需要exclude的,已经配置到mavn的地方了。

编译&运行&测试

编译后class文件已经被织入了相关代码,如下图

70f6af8f696eead36e3ac74fdcd2237b.png

运行相关日志输出如下

f2ea07516f0d2898b04714fc3f6e0119.png

说明功能已经实现。

如果还有其他比较好的方法,欢迎大家留言,谢谢

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/550693.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

什么从什么写短句_2020抖音文案短句:爱情、励志、伤感合集,值得收藏!

视频火不火,一半看文案!想知道爆款视频的文案都是什么吗?想知道爆款文案的套路吗?今天,我就给大家整理了近期抖音爆款短视频的文案——爱情、励志、伤感短句,句句深入人心,赶紧来看看吧&#xf…

插入数据的时候出现错误:Error during job, obtaining debugging information…

插入数据的时候出现错误:Error during job, obtaining debugging information… 原因: Javaf堆内存不足 解决办法 修改为本地模式 set hive.exec.mode.local.autotrue;

::在sql语句中是什么写法_不懂就问:SQL 语句中 where 条件后 写上1=1 是什么意思...

程序员在编程过程中,经常会在代码中使用到“where 11”,这是为什么呢?SQL注入初次看到这种写法的同学肯定很纳闷,加不加where 11,查询不都一样吗?例如:select * from customers; 与 select * fr…

django 集成个推_持续集成CircleCI vs Travis CI vs Jenkins

Continuous Integration. CircleCI vs Travis CI vs Jenkins​hackernoon.com持续集成(CI)的定义及其主要目标持续集成(CI)是一种软件开发实践,它基于将代码频繁集成到共享代码仓中。 然后通过自动构建(automated build)验证每个签入(Check-In)。持续集成(CI)的主要…

战双帕弥什自抽号怎么使用_战双帕弥什新S冰露怎么玩《战双帕弥什》新S冰露玩法技巧...

战双帕弥什新S冰露怎么玩呢,新的S构造体更新之后正式登场,不少玩家都对他不太了解,接下来就让小编给大家带来《战双帕弥什》新S冰露玩法技巧介绍。《战双帕弥什》新S冰露玩法技巧介绍 冰露技能分为两种形式,一种是极寒形态&#x…

log4j:WARN No appenders could be found for logger (org.apache.ibatis.logging.LogFactory). log4j:WARN

1. 警告信息 log4j:WARN No appenders could be found for logger (org.apache.ibatis.logging.LogFactory). log4j:WARN Please initialize the log4j system properly. log4j:WARN See http://logging.apache.org/log4j/1.2/faq.html#noconfig for more info. 2. 解决方法 在…

ppt讲解中的过渡_PPT黑科技,只用一张图做出3D动画

我一直在探索PPT中平滑切换的应用。这篇文章感觉算是探索到头了。之前的文章中,曾经提到过平滑切换可以让3D模型动起来。但是在实际应用中,能够供PPT使用的3D素材数量有限,难以准确契合我们的需求。后来我发现,只需要1张普通图片&…

的好处_女性做下蹲运动有什么好处 原来有这些好处

我们在小时候如果犯了错,那么很可能会被老师或者家长罚着做下蹲。因为下蹲非常的累,其实下蹲累的原因就是它的锻炼效果非常的明显。那么你知道女人做下蹲运动的好处是什么呢?下面我们一起去健身知识那里看看吧!女人做下蹲运动的好…

阿里云使用idea通过hdfs api来上传文件时出现could only be written to 0 of the 1 minReplication nodes.错误

问题描述: 使用阿里云服务器,在本地windows电脑上使用idea进行hdfs api操作来上传文件时出现错误如下: org.apache.hadoop.ipc.RemoteException(java.io.IOException): File /a.xlsx could only be written to 0 of the 1 minReplication nod…

birt什么意思中文翻译_ECTN是什么意思

ECTN是什么意思?ECTN是英语ELECTRONIC CARGO TRACKING NOTE的简称,中文翻译为电子货物跟踪单。从9月1日起,贝宁ECTN号码必须显示在提单上,根据BENIN贝宁法令,所有发货至贝宁科托努(COTONOU)港或经由此港转往尼日尔、布…

dockerfile如何运行镜像内的脚本_第七章 Dockerfile文件解析(一)

七 Dockerfile文件解析-17.1 定义:Dockerfile是用来构建Docker镜像的文件,是由一系列命令和参数构成的脚本7.2 Dockerfile内容基础知识:1.每条保留字指令字母必须为大写,并且后面必须跟随参数2.指令从上到下,依次执行3.#为注释内容4.每条指令都会创建一个新的镜像层,并对镜像层…

dfs.client.block.write.replace-datanode-on-failure

问题描述 在使用hdfs api追加内容操作,从windows电脑上的idea对aliyun服务器上的hdfs中的文件追加内容时,出现错误,如下: java.io.IOException: Failed to replace a bad datanode on the existing pipeline due to no more good …

开机显示输入最佳预设值_开机黑屏,有招了(收藏篇)

我的本本有时候就和女朋友一样昨天还好好的,今天就生气了真的啥也没干, 到底因为啥呢?真的想不起来你都干了啥?当然小编想着黑屏问题好像也同样困扰着小伙伴们;所以下次电脑再黑屏,先不要冲动,小…

小样本点云深度学习库_论文 | 小样本学习综述

转自:专知【https://www.zhuanzhi.ai/】【导读】现有的机器学习方法在很多场景下需要依赖大量的训练样本。但机器学习方法是否可以模仿人类,基于先验知识等,只基于少量的样本就可以进行学习。本文介绍41页小样本学习综述《Few-shot Learning:…

uniapp 可视化开发_uniapp的简单安装流程使用教程

由于本人开发的小程序大部分都是通过uniapp开发的,但是又有部分对uniapp的整理安装流程不大熟悉,所以这次给大家写一个简单完整的使用教程。下载uniapp专用开发工具uniapp是由DCloud公司推出的一款前端应用的框架,所以需要专属的开发工具来开…

Exception in thread “main“ org.apache.hadoop.hbase.client.RetriesExhaustedException: Can‘t get the l

问题描述 今天在windows电脑上使用java api进行hbase的操作时,报了如下错误 Exception in thread "main" org.apache.hadoop.hbase.client.RetriesExhaustedException: Cant get the locations问题原因 conf.set(“hbase.zookeeper.quorum”,“hadoop002,…

dataframe 空值替换为0_dataframe取元素方法总结

dataframe是pandas包的重要对象,熟练掌握dataframe的基本操作是很有必要的。下面就总结一下dataframe取行列元素的基本操作。一. DataFrame的基本结构可以理解为一个矩阵,所有的行名保存在index, 列名保存在columns(注意:一个是单…

bool python 运算_python中的布尔操作

点击以下链接可以快速访问全部我发表的Python相关文章:Nick WU:Nick WU的python文章目录(持续更新中...)​zhuanlan.zhihu.com1. Python中的布尔值Python中任何对象都有一个固定的布尔值,即非零、非空的对象为真&#…

软件工程环形复杂度计算方法有哪些_软件工程复习6165组考题

黑色字体为原本答案,蓝色字体修改补充了复习题组「61-65/61-65/13/13」一、名词解释61.确认测试检查已实现的软件是否满足了需求规格说明中所确定的各种需求,以及软件配置是否完全、正确。(过程:功能性测试---软件配置复查---验收测试----α测…

多线程导出excel高并发_大牛带你深入java多线程与高并发:JMH与Disruptor,确定能学会?...

前言今天我们讲两个内容,第一个是JMH,第二个是Disruptor。这两个内容是给大家做更进一步的这种多线程和高并发的一些专业上的处理。生产环境之中我们很可能不自己定义消息队列,而是使用Disruptor。我们生产环境做测试的时候也不是像我说的那样…