更新:@args()
これは、パラメーターの注釈に一致することを意図したものではなく、パラメーター型の注釈に一致することを意図していないことを忘れていました。これは、必要なものではないため、ここでは使用しません。
を介してパラメーターの注釈をバインドすることはできませんargs()
。パラメーター自体のみをバインドします。これは、リフレクションを介してのみパラメーターの注釈にアクセスできることを意味します。メソッドのシグネチャを決定し、Method
そこからオブジェクトを作成してから、メソッド パラメーターの注釈を反復処理する必要があります。完全なコード サンプルは次のとおりです。
package com.mycompany.locking;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface Lock {}
package com.mycompany.locking;
import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;
@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.PARAMETER)
public @interface LockVal {
String value() default "";
}
package com.mycompany;
public class MyBatchObject {}
package com.mycompany;
public interface UpdateManager {
public void processUpdate(MyBatchObject batch);
}
package com.mycompany;
import com.mycompany.locking.Lock;
import com.mycompany.locking.LockVal;
public class UpdateManagerImpl implements UpdateManager {
@Lock
@Override
public void processUpdate(@LockVal("lockValue") MyBatchObject batch) {
System.out.println("Processing update");
}
public static void main(String[] args) {
UpdateManager updateManager = new UpdateManagerImpl();
updateManager.processUpdate(new MyBatchObject());
}
}
package com.mycompany.aop;
import java.lang.annotation.Annotation;
import java.lang.reflect.Method;
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Pointcut;
import org.aspectj.lang.reflect.MethodSignature;
import com.mycompany.MyBatchObject;
import com.mycompany.locking.LockVal;
@Aspect
public class MyAspect {
@Pointcut("execution(@com.mycompany.locking.Lock * *(@com.mycompany.locking.LockVal (*), ..)) && args(batch)")
public void lockedMethod(MyBatchObject batch) {}
@Around("lockedMethod(batch)")
public Object lockAndProceed(ProceedingJoinPoint pjp, MyBatchObject batch) throws Throwable {
System.out.println(pjp);
System.out.println(batch);
MethodSignature methodSignature = (MethodSignature) pjp.getSignature();
Class<?> clazz = methodSignature.getDeclaringType();
Method method = clazz.getDeclaredMethod(methodSignature.getName(), methodSignature.getParameterTypes());
LockVal propertyToLock;
for (Annotation ann : method.getParameterAnnotations()[0]) {
if(LockVal.class.isInstance(ann)) {
propertyToLock = (LockVal) ann;
System.out.println(propertyToLock.value());
}
}
return pjp.proceed();
}
}
を実行するUpdateManagerImpl.main
と、予想どおり、次の出力が表示されます。
execution(void com.mycompany.UpdateManagerImpl.processUpdate(MyBatchObject))
com.mycompany.MyBatchObject@86f241
lockValue
Processing update
免責事項:私はSpringの男ではありません.Spring AOPではなく、プレーンなAspectJでこれをテストしました。