ProceedingJoinPoint에서 메서드의 주석 값을 가져오려면 어떻게 해야 합니까?
아래에 주석이 있습니다.
My Annotation.자바
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface MyAnnotation {
}
SomeAspect.java
public class SomeAspect{
@Around("execution(public * *(..)) && @annotation(com.mycompany.MyAnnotation)")
public Object procede(ProceedingJoinPoint call) throws Throwable {
//Some logic
}
}
SomeOther.java
public class SomeOther{
@MyAnnotation("ABC")
public String someMethod(String name){
}
}
위 수업에서는 @MyAnnotation에서 "ABC"를 전달하고 있습니다.SomeAspect.java 클래스의 프로시저 메서드의 "ABC" 값에 액세스하려면 어떻게 해야 합니까?
감사합니다!
시그니처는 ProceedingJoinPoint에서 얻을 수 있으며 메서드 호출의 경우 MethodSignature로 캐스트하기만 하면 됩니다.
@Around("execution(public * *(..)) && @annotation(com.mycompany.MyAnnotation)")
public Object procede(ProceedingJoinPoint call) throws Throwable {
MethodSignature signature = (MethodSignature) call.getSignature();
Method method = signature.getMethod();
MyAnnotation myAnnotation = method.getAnnotation(MyAnnotation.class);
}
그러나 먼저 주석 속성을 추가해야 합니다.예제 코드에는 이 코드가 없습니다(예:
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface MyAnnotation {
String value();
}
그러면 액세스 할 수 있습니다.
MyAnnotation myAnnotation = method.getAnnotation(MyAnnotation.class);
String value = myAnnotation.value();
편집
클래스 레벨에 @MyAnnotation("ABC")이 있는 경우 값을 얻는 방법
A Class
이기도 합니다.따라서, 에서는, 와 같은 방법으로 취득할 수 있습니다.Method
예: 메서드의 선언 클래스에 대한 주석을 얻을 수 있습니다.
Method method = ...;
Class<?> declaringClass = method.getDeclaringClass();
MyAnnotation myAnnotation = declaringClass.getAnnotation(MyAnnotation.class)
봄을 사용하고 있기 때문에 봄의 것도 사용하는 것이 좋을지도 모릅니다.스프링과 마찬가지로 주석을 검색합니다.예를 들어 슈퍼클래스 및 인터페이스 메서드 등을 검토한다.
MyAnnotation foundAnnotation = AnnotationUtils.findAnnotation(method, MyAnnotation.class);
편집
또한 5.2에서 소개된 봄의 기능에 관심이 있을 수 있습니다.
사실, 난 우리가 이 모든 걸 수중에value
Proceeding Join Point를 사용하는 것이 아니라 다른 방식으로 진행됩니다.reflection
.
주석을 직접 사용하여 다음과 같이 시도합니다.com.mycompany.MyAnnotation yourAnnotation
당신의 안에서advice params
그리고.@annotation(yourAnnotation)
에@Around
.
@Around("execution(public * *(..)) && @annotation(yourAnnotation)")
public Object procede(ProceedingJoinPoint pjp, com.mycompany.MyAnnotation yourAnnotation) {
...
yourAnnotation.value(); // get your annotation value directly;
...
}
com.mycompany.MyAnnotation
어드바이스 패러머에서는 그대로 기능한다.
@Around("execution(public * *(..)) && @annotation(com.mycompany.MyAnnotation)")
yourAnnotation
이후 유효한 변수 이름이 될 수 있습니다.MyAnnotation
params는 이미 어떤 주석이 되어야 하는지를 나타내고 있습니다.여기서yourAnnotation
는 주석 인스턴스만 가져오는 데 사용됩니다.
더 많은 매개 변수를 통과하고 싶다면args()
.
자세한 내용은 공식 문서를 참조하십시오.주석 값의 경우 검색만 하면 됩니다.@Auditable
.
이 작업도 가능합니다.클래스의 리플렉션으로 주석 정보를 취득할 수 있습니다.
Annotation anno = MyClass.class.getAnnotation(MyAnnotation.class);
아니면
Annotation anno = MyClass.class.getDeclaredMethod("somethod").getAnnotation(MyAnnotation.class);
이는 올바르게 선언한 런타임에 주석을 사용할 수 있는 경우에만 작동합니다.
@Retention(RetentionPolicy.RUNTIME)
르네의 예는 나를 멀리 데려가고 있다.ClassLevel Annotations를 얻는 방법에 대해서도 설명합니다.
그러나 이전에 "*@Around("execution (public * (..)" & @annotation (com.mycompany)" 메서드 주석을 사용한 경우에만 ClassLevel Annotations Values를 읽을 수 있습니다.My Annotation)"
어떻게 하면 이 문제를 피할 수 있을까요?메서드 실행을 거치지 않고 클래스 레벨 주석이 설정된 경우 어떻게 애스펙트를 트리거할 수 있습니까?
ClassLevel 주석을 다음과 같이 쓰고 싶다.
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target(value = { ElementType.METHOD, ElementType.TYPE })
@EnableSwagger2
@Import(SwaggerConfiguration.class)
public @interface EnableSwaggerApi {
String controllerPackage() default "foo.bar.ctrl";
}
"controller Package" 값을 받을 "Swagger Configuration"에 대한 구성을 가져옵니다.
@Aspect
public class SwaggerConfiguration {
@Value("${tom.swagger.controller.package:foo.bar.notset}")
private String controllerPackage;
@Value("${tom.swagger.api.version:1.0.0}")
private String apiVersion;
@Value("${spring.application.name:MyApplication}")
private String applicationName;
@Around("execution(public * *(..)) && @annotation(EnableSwaggerApi)")
public void procede(ProceedingJoinPoint call) throws Throwable {
MethodSignature signature = (MethodSignature) call.getSignature();
Method method = signature.getMethod();
Class<?> declaringClass = method.getDeclaringClass();
EnableSwaggerApi myAnnotation = declaringClass.getAnnotation(EnableSwaggerApi.class);
System.err.println("1 -> " + myAnnotation.controllerPackage()); // -> tko.backend.spring.ctrl
myAnnotation = method.getAnnotation(EnableSwaggerApi.class);
System.err.println("2 -> " + myAnnotation.controllerPackage()); // -> tko.backend.spring.SOMEOTHERSTUFF
// THIS WORKS, BUT JUST IF I USE THE @EnableSwaggerApi ON SOME METHOD!
// NOT ON CLASS
}
@Bean
public Docket swaggerApi() {
return new Docket(DocumentationType.SWAGGER_2)
.select()
.apis(RequestHandlerSelectors.basePackage("controllerPackage"))
.paths(PathSelectors.any())
.build()
.apiInfo(new ApiInfoBuilder().version(apiVersion).title(applicationName).description("Documentation " + applicationName + " API v" + apiVersion)
.build());
}
@Bean
public CorsFilter corsFilter() {
final UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource();
final CorsConfiguration config = new CorsConfiguration();
config.setAllowCredentials(true);
config.addAllowedOrigin("*");
config.addAllowedHeader("*");
config.addAllowedMethod("*");
source.registerCorsConfiguration("/v2/api-docs", config);
return new CorsFilter(source);
}
}
@EnableSwaggerApi(controllerPackage="tko.backend.spring.ctrl")
public class Application extends SpringBootServletInitializer {
public static void main(String[] args) {
SpringApplication.run(Application.class, args);
}
@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
return application.sources(Application.class, Initializer.class);
}
@Bean
@EnableSwaggerApi(controllerPackage="tko.backend.spring.SOMEOTHERSTUFF")
public String initSwagger() {
return "some dummy";
}
}
initSwagger()의 주석을 삭제하려면 어떻게 해야 합니까?Application.class는 Swagger Configuration(Swagger Stuff는 별도 lib에 있음)에 인식되지 않기 때문에 다음과 같은 간단한 리플렉션을 사용할 수 없습니다.
Application.class.getAnnotation(EnableSwaggerApi.class)
AspectJ/AOP를 사용하여 메서드 주석 및 클래스 수준 주석을 위한 작업 코드 찾기
@Around("execution(* com.first.test.controller..*(..)))")
public Object profileAllMethods(ProceedingJoinPoint proceedingJoinPoint) throws Throwable
{
MethodSignature methodSignature = (MethodSignature) proceedingJoinPoint.getSignature();
java.lang.reflect.Method method = methodSignature.getMethod();
Annotation []methodAnnotations = method.getDeclaredAnnotations();
System.out.println("==============="+methodAnnotations[0].toString());
Annotation []classAnnotations = proceedingJoinPoint.getTarget().getClass().getAnnotations();
System.out.println("===Class Annotation : "+classAnnotations[1].toString());
Object result = proceedingJoinPoint.proceed();
return result;
}
문서에 설명된 대로 메서드를 바인딩할 수 있습니다.
My Annotation.자바
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface MyAnnotation {
}
SomeAspect.java
public class SomeAspect{
@Around("execution(public * *(..)) && @annotation(myAnnotation)")
public Object procede(ProceedingJoinPoint call, MyAnnotation myAnnotation) throws Throwable {
//Some logic
}
}
언급URL : https://stackoverflow.com/questions/21275819/how-to-get-a-methods-annotation-value-from-a-proceedingjoinpoint
'programing' 카테고리의 다른 글
MySQL 명령줄 클라이언트의 자동 완성 (0) | 2022.09.21 |
---|---|
Python의 해시 맵 (0) | 2022.09.21 |
MariaDB 구문에 대한 SQL 구문 확인 (0) | 2022.09.21 |
상위 폴더에서 모듈 가져오기 (0) | 2022.09.19 |
다른 테이블의 값을 포함하는 mysql update 컬럼 (0) | 2022.09.19 |