如何为 class 初始化定义切入点
How to define pointcut for class initialization
我是 AspectJ 的新手,正在尝试了解连接点模型
现在我有 class 这样的
public class Account {
private static Map<String, PaymentMethod> supportedPayments = new HashMap<>();
static {
supportedPayments.add("COD", new CodPaymentMethod());
supportedPayments.add("ATM", new ATMPaymentMethod());
}
}
正如我从 AspectJ In Action 中读到的那样,有一种方法可以在初始化 class 时定义切入点,但我找不到语法。
有人帮帮我吗?
这个不行:
@Pointcut("initialization(com.jas.aop.bean.Payment"))
它说
ERROR] Syntax error on token "initialization(com.jas.aop.bean.Payment)", "name pattern" expected
/Users/admin/eclipse-workspace/aop/src/main/java/com/jas/aop/aspect/ClassInitializationAspect.java:9
@Pointcut("initialization(com.jas.aop.bean.Payment)")
你的切入点有几个问题:
- 缺少右括号
)
。
initialization
拦截构造函数(即对象初始化)而不是静态 class 初始化,这不是您想要的,并且还需要构造函数模式,而不是 class 名称模式.
- 如果您的方面恰好不在与目标 class 完全相同的包中,您必须使用完全限定的 class 名称,例如
my.package.Account
,以便切入点匹配。
顺便说一下,您的代码片段只是伪代码,因为哈希映射没有 add
方法,而是 put
方法。示例 class 甚至无法编译。在这里发布问题时不要只是发明代码。让试图帮助您的人的生活更轻松。
现在这里有一个 MCVE,我总是建议您在问题中具体说明,以帮助人们重现您的情况。这次是我为你做的,这是你的免费机会。下次请自己动手
主要class使用的依赖class:
package de.scrum_master.app;
public interface PaymentMethod {}
package de.scrum_master.app;
public class ATMPaymentMethod implements PaymentMethod {}
package de.scrum_master.app;
public class CodPaymentMethod implements PaymentMethod {}
目标 class 驱动程序应用程序:
package de.scrum_master.app;
import java.util.HashMap;
import java.util.Map;
public class Account {
private static Map<String, PaymentMethod> supportedPayments = new HashMap<>();
static {
System.out.println("Static initialiser block");
supportedPayments.put("COD", new CodPaymentMethod());
supportedPayments.put("ATM", new ATMPaymentMethod());
}
public Account() {
System.out.println("Creating account");
}
public void doSomething() {
System.out.println("Doing something");
}
public static void main(String[] args) {
new Account().doSomething();
}
}
看点:
方面同时显示 initialization
和 staticinitialization
以显示语法和功能上的差异。您可以在 AspectJ 手册中找到所有这些解释的示例,我强烈建议您阅读。
package de.scrum_master.aspect;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
@Aspect
public class AccountAspect {
@Before("initialization(de.scrum_master.app.Account.new(..))")
public void interceptObjectInitialisation(JoinPoint joinPoint) {
System.out.println(joinPoint);
}
@Before("staticinitialization(de.scrum_master.app.Account)")
public void interceptClassInitialisation(JoinPoint joinPoint) {
System.out.println(joinPoint);
}
}
控制台日志:
staticinitialization(de.scrum_master.app.Account.<clinit>)
Static initialiser block
initialization(de.scrum_master.app.Account())
Creating account
Doing something
我是 AspectJ 的新手,正在尝试了解连接点模型 现在我有 class 这样的
public class Account {
private static Map<String, PaymentMethod> supportedPayments = new HashMap<>();
static {
supportedPayments.add("COD", new CodPaymentMethod());
supportedPayments.add("ATM", new ATMPaymentMethod());
}
}
正如我从 AspectJ In Action 中读到的那样,有一种方法可以在初始化 class 时定义切入点,但我找不到语法。 有人帮帮我吗?
这个不行:
@Pointcut("initialization(com.jas.aop.bean.Payment"))
它说
ERROR] Syntax error on token "initialization(com.jas.aop.bean.Payment)", "name pattern" expected
/Users/admin/eclipse-workspace/aop/src/main/java/com/jas/aop/aspect/ClassInitializationAspect.java:9
@Pointcut("initialization(com.jas.aop.bean.Payment)")
你的切入点有几个问题:
- 缺少右括号
)
。 initialization
拦截构造函数(即对象初始化)而不是静态 class 初始化,这不是您想要的,并且还需要构造函数模式,而不是 class 名称模式.- 如果您的方面恰好不在与目标 class 完全相同的包中,您必须使用完全限定的 class 名称,例如
my.package.Account
,以便切入点匹配。
顺便说一下,您的代码片段只是伪代码,因为哈希映射没有 add
方法,而是 put
方法。示例 class 甚至无法编译。在这里发布问题时不要只是发明代码。让试图帮助您的人的生活更轻松。
现在这里有一个 MCVE,我总是建议您在问题中具体说明,以帮助人们重现您的情况。这次是我为你做的,这是你的免费机会。下次请自己动手
主要class使用的依赖class:
package de.scrum_master.app;
public interface PaymentMethod {}
package de.scrum_master.app;
public class ATMPaymentMethod implements PaymentMethod {}
package de.scrum_master.app;
public class CodPaymentMethod implements PaymentMethod {}
目标 class 驱动程序应用程序:
package de.scrum_master.app;
import java.util.HashMap;
import java.util.Map;
public class Account {
private static Map<String, PaymentMethod> supportedPayments = new HashMap<>();
static {
System.out.println("Static initialiser block");
supportedPayments.put("COD", new CodPaymentMethod());
supportedPayments.put("ATM", new ATMPaymentMethod());
}
public Account() {
System.out.println("Creating account");
}
public void doSomething() {
System.out.println("Doing something");
}
public static void main(String[] args) {
new Account().doSomething();
}
}
看点:
方面同时显示 initialization
和 staticinitialization
以显示语法和功能上的差异。您可以在 AspectJ 手册中找到所有这些解释的示例,我强烈建议您阅读。
package de.scrum_master.aspect;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
@Aspect
public class AccountAspect {
@Before("initialization(de.scrum_master.app.Account.new(..))")
public void interceptObjectInitialisation(JoinPoint joinPoint) {
System.out.println(joinPoint);
}
@Before("staticinitialization(de.scrum_master.app.Account)")
public void interceptClassInitialisation(JoinPoint joinPoint) {
System.out.println(joinPoint);
}
}
控制台日志:
staticinitialization(de.scrum_master.app.Account.<clinit>)
Static initialiser block
initialization(de.scrum_master.app.Account())
Creating account
Doing something