web-dev-qa-db-fra.com

Ignorer conditionnellement les tests dans JUnit 4

OK, l'annotation @Ignore permet de signaler qu'un scénario de test ne doit pas être exécuté.

Cependant, je souhaite parfois ignorer un test basé sur des informations d'exécution. Un exemple pourrait être si j'ai un test de concurrence d'accès qui doit être exécuté sur une machine avec un certain nombre de cœurs. Si ce test était exécuté sur une machine à un seul processeur, je ne pense pas qu'il serait correct de simplement réussir le test (car il n'a pas été exécuté), et il ne serait certainement pas correct de rater le test et de rompre la construction. .

Je veux donc pouvoir ignorer les tests au moment de l'exécution, car cela semble être le bon résultat (car le cadre de test permettra à la construction de réussir, mais enregistrez que les tests n'ont pas été exécutés). Je suis à peu près sûr que l'annotation ne me donnera pas cette souplesse et je suppose que je devrai créer manuellement la suite de tests pour la classe en question. Cependant, la documentation ne mentionne rien à ce sujet et en regardant à travers API , on ne sait pas non plus comment cela se ferait par programmation (c.-à-d. Comment créer par programme une instance de Test ou similaire équivalent à celui créé par l'annotation @Ignore?).

Si quelqu'un a déjà fait quelque chose de similaire dans le passé ou a une idée brillante de la manière dont je pourrais procéder autrement, je serais heureux de l'entendre.

337
Andrzej Doyle

La méthode JUnit consiste à effectuer cette opération au moment de l'exécution en utilisant org.junit.Assume.

 @Before
 public void beforeMethod() {
     org.junit.Assume.assumeTrue(someCondition());
     // rest of setup.
 }

Vous pouvez le faire dans une méthode @Before ou dans le test lui-même, mais pas dans une méthode @After. Si vous le faites dans le test lui-même, votre méthode @Before sera exécutée. Vous pouvez également le faire dans @BeforeClass pour empêcher l'initialisation de la classe.

n échec de l'hypothèse fait en sorte que le test soit ignoré.

Edit: Pour comparer avec l'annotation @RunIf de junit-ext , leur exemple de code ressemblerait à ceci:

@Test
public void calculateTotalSalary() {
    assumeThat(Database.connect(), is(notNull()));
    //test code below.
}

Sans oublier qu'il est beaucoup plus facile de capturer et d'utiliser la connexion à partir de la méthode Database.connect() de cette façon.

435
Yishai

Vous devriez passer à la caisse Junit-ext projet. Ils ont l'annotation RunIf qui effectue des tests conditionnels, tels que:

_@Test
@RunIf(DatabaseIsConnected.class)
public void calculateTotalSalary() {
    //your code there
}

class DatabaseIsConnected implements Checker {
   public boolean satisify() {
        return Database.connect() != null;
   }
}
_

[Exemple de code tiré de leur tutoriel]

47
notnoop

Dans JUnit 4, vous pouvez également créer une annotation indiquant que le test doit répondre à vos critères personnalisés, puis étendre le coureur par défaut avec le vôtre et, à l'aide de la réflexion, fonder votre décision sur les critères personnalisés. Cela peut ressembler à quelque chose comme ça:

public class CustomRunner extends BlockJUnit4ClassRunner {
    public CTRunner(Class<?> klass) throws initializationError {
        super(klass);
    }

    @Override
    protected boolean isIgnored(FrameworkMethod child) {
        if(shouldIgnore()) {
            return true;
        }
        return super.isIgnored(child);
    }

    private boolean shouldIgnore(class) {
        /* some custom criteria */
    }
}
7
Kyle Shrader