AspectJ:如何在 get() 切入点中获取访问字段的值 [英] AspectJ: How to get accessed field's value in a get() pointcut

查看:20
本文介绍了AspectJ:如何在 get() 切入点中获取访问字段的值的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在编写一个方面记录器,以便在访问给定类中的任何成员变量时写入日志.

I am writing an aspect logger to write a log whenever any member variable in a given class is accessed.

如果我为如下所示的单个变量编写一个特定的切入点,我就可以获得该字段的值.

If I write a specific pointcut for a single variable like below, I am able to get the value of the field.

@Pointcut("get(* abc.ThreadPoolService.drMaxTh)")
public void drFields() {}

@AfterReturning(pointcut="drFields()", returning="drMaxTh")  
public void afterAccessingdrFields(int drMaxTh) {
    LOGGER.info("Accessed the field drMaxTh " + drMaxTh);
}

但是我的班级有十几个变量,我不打算为每个变量编写特定的切入点.所以,我想写一些类似..

But my class has a dozen+ variables, and I don't intend on writing specific pointcuts for each of them. So, I want to write something like..

@Pointcut("get(* abc.ThreadPoolService.*)")
public void drFields() {}

@AfterReturning(pointcut="drFields()", returning= **????** )  
public void afterAccessingdrFields(what should come here???) {
    LOGGER.info("Accessed the field drMaxTh " + <and here???>);
}

但无法理解如何在通配符字段访问说明符的情况下捕获正在访问的字段的名称和值.

But unable to understand how to capture the name and value of the field that is being accessed, in case of a wildcard field access specifier.

感谢任何帮助我解决这个问题的人.

Thanx to anyone helping me out on this.

推荐答案

其实很简单,sheltem 说的对,你可以直接在返回中使用Object类型声明.这里有一个小演示,显示它甚至适用于静态和非静态成员,只要它们没有被声明为 final:

It is actually very simple, and sheltem was right, you can just use Object in the returning type declaration. Here is a little demo showing that it even works for both static and non-static members, as long as they are not declared final:

驱动程序应用:

package de.scrum_master.app;

public class Application {
    public static final double PI = Math.PI;
    static String producer = "Scrum-Master.de";

    private int id = 11;
    private String author = "Alexander Kriegisch";
    private final String COUNTRY = "Germany";

    public static void main(String[] args) {
        Object dummy;
        Application application = new Application();

        // Access static fields
        dummy = PI;
        dummy = producer;
        // Access non-static fields
        dummy = application.author;
        dummy = application.id;
        dummy = application.COUNTRY;
    }
}

方面:

package de.scrum_master.aspect;

import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;

@Aspect
public class FieldAccessLogger {
    @Pointcut("get(* de.scrum_master.app.Application.*)")
    public void fieldAccess() {}

    @AfterReturning(pointcut = "fieldAccess()", returning = "field")
    public void afterFieldAccess(Object field, JoinPoint thisJoinPoint) {
        System.out.println(thisJoinPoint.toLongString());
        System.out.println("  " + thisJoinPoint.getSignature().getName());
        System.out.println("  " + field);
    }
}

控制台输出:

get(static java.lang.String de.scrum_master.app.Application.producer)
  producer
  Scrum-Master.de
get(private java.lang.String de.scrum_master.app.Application.author)
  author
  Alexander Kriegisch
get(private int de.scrum_master.app.Application.id)
  id
  11

如您所见,PICOUNTRY 没有被拦截,因为它们是(最终)常量.

As you can see, PI and COUNTRY are not intercepted because they are (final) constants.

这篇关于AspectJ:如何在 get() 切入点中获取访问字段的值的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆