Kann ich automatisch aktiviert JUnit Testfälle einmal mit allen Protokollierung ausführen und einmal mit allen Anmeldung deaktiviert?

StackOverflow https://stackoverflow.com/questions/945659

Frage

Ich habe eine Lösung gefunden, unter meine eigene Antwort sehen. Hat jemand eine elegantere eine hat?

Ich möchte, dies zu tun Code-Abdeckung zu erhöhen und finden subtile Bugs.

Nehmen wir die folgende Klasse getestet werden:

public class Foo {
    private final Logger logger = LoggerFactory.getLogger(Foo.class);
    public void bar() {
        String param=[..];
        if(logger.isInfoEnabled()) logger.info("A message with parameter {}", param);

        if(logger.isDebugEnabled()) {
            // some complicated preparation for the debug message
            logger.debug([the debug message]);
        }
    }
}

und die folgende Test-Klasse:

public class FooTest {
    @Test
    public void bar() {
        Foo foo=new Foo();
        foo.bar();
    }
}

Ein Code-Coverage-Tool wie z.B. Cobertura korrekt berichten, dass nur ein Teil der bedingten Verzweigungen überprüft wurden.

info und debug sind entweder aktiviert oder für den Logger deaktiviert.

Neben der Suche schlecht in Ihrer Berichterstattung Punktzahl, dies stellt eine echte Gefahr.

Was, wenn es einige Nebenwirkung von Code verursacht innerhalb if (logger.isDebugEnabled ())? Was passiert, wenn Ihr Code nur funktioniert, wenn DEBUG aktiviert ist und scheitert kläglich, wenn die Protokollebene INFO eingestellt ist? (Dies ist eigentlich in einem unserer Projekte geschehen: p)

So ist meine Schlussfolgerung, dass Code-Logger-Anweisungen enthält immer einmal getestet werden sollte, mit allen Protokollierung aktiviert und einmal mit allen Anmeldung deaktiviert ...

Gibt es eine Möglichkeit etwas wie die mit JUnit zu tun? Ich weiß, wie ermöglichen global oder all meine Protokollierung in Logback deaktivieren, damit das Problem ist: Wie kann ich die Prüfungen zweimal ausführen, einmal mit Protokollierung aktiviert, einmal mit deaktiviert Protokollierung

.

P. S. Ich bin mir dessen bewusst diese Frage aber ich glaube nicht, das ist ein Duplikat. Ich bin weniger besorgt über den absoluten Deckungswert, sondern um subtile, schwer zu findende Fehlern, die innerhalb eines enthalten sein könnten, wenn (logger.isDebugEnabled ()).

War es hilfreich?

Lösung

Ich habe dieses Problem gelöst, indem eine Basisklasse, die Testklassen Umsetzung sollte verlängern, wenn eine solche Funktionalität gewünscht wird.

Der Artikel einen parametrisierte JUnit-Test Schreiben enthielt die Lösung.

Siehe LoggingTestBase für die Logging-Basisklasse und LoggingTestBaseExampleTest für ein einfaches Beispiel, das es verwendet wird.

Jede enthaltene Testverfahren wird dreimal ausgeführt:

1. Es ausgeführt ist die Protokollierung unter Verwendung des in logback-test.xml wie üblich definiert. Dies soll helfen, beim Schreiben / die Tests debuggen.

2. Es ist mit allen Protokollierung ausgeführt aktiviert und in eine Datei geschrieben. Diese Datei wird nach dem Test gelöscht.

3. Es ist ausgeführt mit allen Anmeldung deaktiviert.

Ja, LoggingTestBase muss Dokumentation;)

Andere Tipps

Haben Sie versucht einfach beibehalten zwei separate Protokollkonfigurationsdateien? Jeder auf verschiedenen Ebenen vom Root-Logger log würde.

Alle Anmeldung deaktiviert :

...
<root>
    <priority value="OFF"/>
    <appender-ref ref="LOCAL_CONSOLE"/>
</root>
...

Alle Protokollierung aktiviert :

...
<root>
    <priority value="ALL"/>
    <appender-ref ref="LOCAL_CONSOLE"/>
</root>
...

Ausführung unterschiedliche Konfigurationen auf dem Classpath über einen Systemparameter angeben würde:

-Dlog4j.configuration=path/to/logging-off.xml
-Dlog4j.configuration=path/to/logging-on.xml

Ich würde empfehlen, von JUnit zu TestNG wechseln. TestNG hat viele erweiterte Funktionen über JUnit. Es ermöglicht Ihnen, Ihre Tests mehrmals mit verschiedenen Konfiguration laufen und ich denke, das ist, was Sie brauchen

eqbridges Vorschlag einfach die Tests zweimal mit unterschiedlichen Protokollierungs Kontexten läuft die einfachste zu sein scheint. Sie müssen sich nicht erinnern, die Logik in jedem gesegneten Test zu codieren, für einen großen Vorteil. Die andere ist, dass Sie die Protokollierungsebene sehen kann, ist sehr leicht schuld.

aber sagen, dass es ein paar Strategien, wenn Sie nur diese laufen in einem Test zu tun hatte.

Für 3.8 würde ich alles in Suiten setzen, und mache zwei Suiten, einen für jede Protokollebene, die die Protokollierungsebene setzt vor der Testausführung. Dies ist funktionell das gleiche wie die gesamte Testsuite zweimal mit unterschiedlichen Kommandozeilenparameter ausgeführt, mit der Ausnahme, dass Sie es mit einem Lauf zu bekommen.

In JUnit 4.x ein paar zusätzliche Optionen in den Sinn kommen:

Eine davon ist ein Brauch Läufer. Obwohl ich nicht aus der Hand an alles denken kann, würde man diese Arbeit machen zu tun hat, aber ein Läufer, die den Test zweimal tatsächlich läuft und mit Anmerkungen versehen Sie den Test mit @RunWith Ihren benutzerdefinierten Läufer arbeiten könnten.

Die andere ist parametriert Tests. Obwohl Sie eigentlich jeden Test einrichten müssten Parameter übernehmen (dies einen Konstruktor erfordert, die die Argumente übernimmt) und dann nach den Log-Level auf den Parameter.

EDIT: Als Antwort auf Ihre Anfrage für ein How-to auf den paramterized Tests, hier ist ein praktischer Leitfaden.

Wenn Sie Sie zu viel Protokollierung fühlen, wenn Sie alles einschalten, vielleicht könnten Sie versuchen, die Menge der Protokollierung zu reduzieren. Es ist nicht sehr nützlich, wenn es zu viel für den Computer einen Menschen procude nie zu lesen, etwas dagegen.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top