如何劫持/拦截来自第三方(EclipseLink)jar 甚至 JDK 的类的方法? [英] How to hijacked/intercept method of a class which from third party(EclipseLink) jar or even JDK?
问题描述
我尝试劫持/拦截 EclipseLink 中某个类的方法.我曾尝试过 Spring AOP 和 AspectJ,但失败了.当 class org.eclipse.persistence.internal.localization.i18n.TraceLocalizationResource
在调用方法 getString(..);
时抛出异常时,我想做一些事情我的实现如下:
I try to hijack/intercept a method of a class in EclipseLink. I had tried Spring AOP and AspectJ and I failed. I want to do something when class org.eclipse.persistence.internal.localization.i18n.TraceLocalizationResource
throw exception while calling method getString(..);
My implementation as below:
@AfterThrowing(pointcut = "execution(* org.eclipse.persistence.internal.localization.i18n.TraceLocalizationResource.getString(..))",throwing="error")
public void logAfterThrowing(JoinPoint joinPoint,Throwable error) {
....
}
并且调用了 calssTraceLocalizationResource
(我调试它).但是没有调用劫持方法.
And calssTraceLocalizationResource
was called (I debug into it). But the hijack method wasn't called.
我的问题:
- 我做错了吗?
- 我们要劫持或拦截的目标类必须是自定义类型吗?
- 如果我想劫持像 java.lang.String 这样的 JDK 类怎么办?
推荐答案
基本上语法看起来不错,但我没有尝试复制此处来自您的代码片段的完整方面.此外,我只使用原生 AspectJ 语法,我不太熟悉基于注释的语法,所以如果有问题,我可能不会看过了.
Basically the syntax looks okay, but I have not tried to replicate a full aspect from your code snippet here. Furthermore, I only use native AspectJ syntax and am not quite familiar with annotation-based syntax, so if there is a problem there I might not have seen it.
不可以,但是如果您想编织主应用程序使用的库(JAR 或解压到文件系统中),您必须确保它位于编织器的路径中.请查阅 AspectJ 文档以了解语法.我今天早些时候在另一个答案中发布了一些有用的链接.
No, but if you want to weave a library (JAR or unpacked into the file system) used by your main application, you must make sure that it is in the in-path for the weaver. Please consult AspectJ documentation for the syntax. I posted some helpful links in another answer earlier today.
默认情况下,包org.aspectj
、java
和javax
被排除在编织之外.对于后两者,有命令行开关来启用编织.但是 LTW 充其量是棘手的,最坏的情况是在 a**(几乎不可能)中痛苦,因为那里有一个鸡蛋和鸡蛋的问题:AspectJ weaver 运行时类需要 JDK,而 JDK 引导发生在任何 Java 之前像织布工一样的代理是附加的.因此,您最好的选择是在编译时编织 JDK 类,然后稍后在您的应用程序中使用编织的 rt.jar.即使使用编译时编织,如果您的建议本身使用 JDK 编织类,您也可能会遇到问题.您要确保避免在那里出现无限递归.但这是可能的.
By default, packages org.aspectj
, java
and javax
are excluded from weaving. For the latter two, there are command line switches to enable weaving. But LTW will be tricky at best and a pain in the a** (next to impossible) at worst because you have a hen-and-egg problem there: The AspectJ weaver runtime classes need the JDK, and JDK bootstrapping happens before any Java agent like the weaver is attached. So your best bet is compile-time weaving for JDK classes and then using the woven rt.jar later in your application. Even with compile-time weaving you might run into issues if your advice use JDK woven classes themselves. You want to make sure to avoid infinite recursions there. But it is possible.
更新: 对于使用 AspectJ 一段时间的人来说,另一个提示有时似乎太简单而无法提及:而不是 execution
切入点,这使得必须编织目标类,您可以只使用 call
切入点,它拦截(顾名思义)对客户端类中任何地方的目标的调用.它可能效率稍低,但可能是您最好和最简单的选择,除非您真的想不厌其烦地编织 JDK.
Update: Another hint which sometimes seems too simple to mention for someone who has used AspectJ for a while: Instead of an execution
pointcut which makes it necessary to weave the target class, you may just use a call
pointcut which intercepts (as the name implies) calls to the target everywhere in your client classes. It might be a little less efficient, but maybe your best and easiest bet unless you really want to take the trouble of weaving the JDK.
这篇关于如何劫持/拦截来自第三方(EclipseLink)jar 甚至 JDK 的类的方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!