2016-04-05 4 views
0

Ich schreibe Tests für einige Sftp-Validierungen und ich starte einen eingebetteten Sftp-Server.Einschränken einer Java-Methode zum Aufrufen von Methoden mit bestimmten Annotation

so habe ich eine Klasse wie:

public class SftpServer { 

    //method to initialize server 
    public void init(){}; 

    //method to stop server 
    public void stop(){}; 

    } 

nun als meine Tests in Multithreaded-Umgebung ausführen mag ich den Server gestartet nur einmal werden oder gestoppt wird, ich TestNG als Unit Testing Framework verwenden.

so mag ich die init und die stop Methoden nur mit Methoden annotated mit @BeforeSuite oder @AfterSuite Anmerkungen genannt werden, ich weiß, dass Java-docs vielleicht eine Möglichkeit, diese Art und Weise getan vorschlagen bekommen, aber ich mag Erzwingen es, Ist es in Java möglich, diese Beschränkung in irgendeiner Weise durchzusetzen?

+0

Nein, Anmerkungen enthalten nur Metainformationen für den Compiler und können den Zugriff auf Methoden nicht einschränken. –

+0

Wie ist es, den Annotationsklassennamen der aufrufenden Methode zu finden und eine Ausnahme auszulösen, wenn es nicht die richtige Annotation ist? – Anirudh

+0

finden Sie die aufrufende Methode und verwenden Sie Reflektion, um seine Anmerkungen zu lösen :) –

Antwort

0

Dies kann nicht die beste Option sein, zu tun, was Sie wollen, aber Sie werden es erreichen trotzdem in der Lage:

public void test() { 
    StackTraceElement element = getElement(); 
    try { 
     Method m = Class.forName(element.getClassName()).getDeclaredMethod(element.getMethodName()); 
     Annotation[] annotations = m.getAnnotations(); 
     // do your thing 
    } catch (NoSuchMethodException e) { 
     e.printStackTrace(); 
    } catch (ClassNotFoundException e) { 
     e.printStackTrace(); 
    } 

} 

private static StackTraceElement getElement() { 
    StackTraceElement[] elements = Thread.currentThread().getStackTrace(); 
    for (int i = 1; i < elements.length; i++) { 
     StackTraceElement stackTraceElement = elements[i]; 
     if (!stackTraceElement.getClassName().equals(Bar.class.getName()) 
       && !stackTraceElement.getMethodName().equals("getElement()") 
       && stackTraceElement.getClassName().indexOf("java.lang.Thread") != 0) { 
      return stackTraceElement; 
     } 
    } 
    return null; 
} 

Mit der Anmerkungsliste zur Hand für den Anrufer Methode sucht, nur für die eine Du willst und tust was immer du willst.

Beachten Sie, dass die Aufrufmethode aus einer anderen Klasse stammt, passen Sie sie also an Ihre Anforderungen an.

0

Es gibt zwei allgemeine Möglichkeiten, dies zu erzwingen.

Eine ist für die Methoden init und stop, Laufzeitprüfung durchzuführen. Wenn sie aufgerufen werden, untersuchen sie den Stack, bestimmen ihren Aufrufer, bestimmen reflektiv die Annotation für ihren Aufrufer und lösen eine Ausnahme aus, wenn der Aufrufer nicht mit @BeforeSuite oder @AfterSuite annotiert ist. Das hindert Sie nicht daran, falsche Anrufe zu schreiben, es stürzt nur Ihre Testsuite ab, wenn Sie die falschen Anrufe geschrieben haben.

Der andere Ansatz ist statische Überprüfung. Beim Kompilieren einer Methode, die init oder stop aufruft, würde der Compiler einen Fehler ausgeben, wenn die Methode nicht mit @BeforeSuite oder @AfterSuite annotiert ist. Dies gibt Ihnen eine frühere Benachrichtigung über Fehler zum Zeitpunkt der Kompilierung und verhindert so, dass Sie jemals falschen Code ausführen. Um dies zu implementieren, würden Sie einen Annotationsprozessor mit einem Tool wie dem Checker Framework oder einem Plugin zu einem Tool wie error-prone schreiben.

Verwandte Themen