2016-11-09 4 views
0

클래스의 메소드를 찾기 위해 리플렉션을 사용하고 있으며 작업 유형 (CREATE, DELETE, ...)을 설명하는 주석 "PermessiNecessari"를 가져옵니다. 메소드가 구현됩니다.자바 리플렉션 : 주석이 존재하지 않아도 찾을 수 없습니다.

이것은 피벗 링크 클래스 PathAuthorizer을 구현하는 권한 검사입니다. 나는 호출 된 url을 얻었고, 나는 그것을 나눠서 URL로부터 웹 서비스를 구현하는 클래스를 찾는다. 그런 다음 호출 될 메소드를 검색하고 사용되는 조작 유형을 읽습니다.

public interface VlpgmoduliManagerFacadeRemote 
    extends InterfacciaFacadeRemote<Vlpgmoduli>{ 

    @POST 
    @javax.ws.rs.Path("getpermessimoduligruppo") 
    @Consumes(MediaType.APPLICATION_FORM_URLENCODED) 
    @Produces({MediaType.APPLICATION_JSON, MediaType.TEXT_PLAIN}) 
    @PermessiNecessari(operation = STANDARD_OP.READ) 
    public GridResponse<Vlpgmoduli> getPermessiModuliGruppo(MultivaluedMap<String, String> formParams, 
     String callback) 
     throws BadRequestException; 
... 

있어서 @ javax.ws.rs.Path 통해 발견된다

istance 들어
Class facadeinterface = Class.forName(pm); // get the interface 
Method metodo = getMetodoClasse(facadeinterface, metodoRest); // find method with @Path annotation 
if(metodo != null){ 
    PermessiNecessari rp = metodo.getAnnotation(PermessiNecessari.class); 

    if(rp != null){ // caso metodo con permessi 
     return checkPermessiModulo(m, rp); 
    } 

    if(metodo.isAnnotationPresent(NonProtetto.class)){ 
     return true; 
    } 
    LOG.log(Level.WARNING, "Metodo trovato : {0}/{1}, ma non annotato!", new Object[]{metodoRest,metodo}); 

, 이것은 확인 된 클래스 :

는 검색 메소드의 조각 주석을 추가 할 수 있지만 "PermessiNecessari"주석을 가져 오려면이 주석을 찾을 수 없습니다!

추신 : 다른 시스템에서는이 시스템이 정상적으로 작동합니다. 상위 인터페이스의 메소드도 찾을 수 없습니다! 동일한 인터페이스와 모든 메소드 (상속 된 인터페이스)를 확장하는 다른 인터페이스로 시도합니다.

private Method getMetodoClasse(Class facade, String metodo){ 
    for(Method method : facade.getMethods()){ 
     Path p = method.getAnnotation(Path.class); 
     if(p != null && (p.value().equals(metodo) || p.value().equals("/"+metodo))){ 
      return method; 
     } 
    } 
    for (Class c : facade.getInterfaces()) { 
     for (Method method : c.getDeclaredMethods()) { 
      Path p = method.getAnnotation(Path.class); 
      if(p != null && (p.value().equals(metodo) || p.value().equals("/"+metodo))){ 
       return method; 
      } 
     } 
    } 
    return null; 
} 

편집 : 그것은 주석의 문제가 아니에요

@Retention(RetentionPolicy.RUNTIME) 
@Target(ElementType.METHOD) 
public @interface PermessiNecessari {  
    Class resourceClass() default void.class; 
    String operation() default ""; 
    String modulo() default ""; 
} 

이 웹 서비스를 구현하는 방법을 검색하는 방법입니다 :

이 내 주석이다. 나는이 검사와 tryed :.

public boolean haAnnotazione(Method method, Class annotationType){ 
    Annotation annotazioni[] = method.getAnnotations(); 
    for(Annotation a : annotazioni){ 
     if(a.annotationType().getName().equals(annotationType.getName())){ 
      return true; 
     } 
    } 
    return false; 
} 

내가 사용하는 경우 a.annotationType() 등호 (annotationType) 그들이 같은 경우에도 false를 돌려; 수업의 이름을 사용하면 효과가 있습니다!

아마도 클래스 로더 문제일까요? 이 소프트웨어는 Wildfly에서 실행됩니다.

+0

가능한 복제 [다른 보존 정책을 내 주석에 영향을 어떻게해야합니까?] (http : // stackoverflow.com/questions/3107970/how-do-different-retention-policies-affect-my-annotations) – Dariusz

+0

@Daniele은 편집 내용을 설명해 주시겠습니까? – Antoniossss

+0

@Antoniossss 질문을 변경했습니다. 지금은 더 명확 해졌습니다. –

답변

1

해결!

종속성 오류입니다. 프로젝트에는 2 가지 다른 종속성 버전이 있으므로로드 된 주석은 실제로 두 개의 다른 클래스였습니다.

다음 번에는 캐스트 예외가 있거나 두 개의 동일한 클래스가 같지 않은 경우 pom.xml에서 다른 종속성을 확인하십시오.

... 정말 해결되지,이 EAR/lib 디렉토리 및 WAR/lib 디렉토리에서 클래스 사이의 클래스 로더 문제는, 그러나 이것은 또 다른 질문입니다

+0

업데이트 해 주셔서 감사합니다. 전체 경로 작성으로 문제가 해결되었습니다. / – Tasgall

0

@PermessiNecessari은 보유가 다를 경우 컴파일러가 해당 주석에 대한 정보를 바이트 코드에 포함시키지 않기 때문에 제거해야합니다 (Runtime retention).

따라서 런타임에 주석을 찾을 수없는 이유가 여기에 있습니다.

+0

PermessiNecessari에 @ Retention (RetentionPolicy.RUNTIME) :( 주석이 다른 클래스에서 발견되었습니다. –