68 votes

EasyMock: Méthodes Void

J'ai une méthode qui retourne void dans une classe qui est une dépendance de la classe que je veux tester.

Cette classe est énorme et je suis seulement en utilisant cette méthode unique. J'ai besoin de remplacer la mise en œuvre de cette méthode pour le test que je voulais faire quelque chose de différent et j'ai besoin d'être en mesure d'accéder aux paramètres de cette méthode reçoit.

Je ne peux pas trouver un moyen de le faire dans EasyMock. Je pense que je sais comment le faire avec Mockito en utilisant doAnswer mais je ne veux pas ajouter une autre bibliothèque, sauf si absolument nécessaire.

91voto

matt b Points 73770

Si je comprends ce que vous voulez le faire correctement, vous devriez être en mesure d'utiliser andAnswer():

mockObject.someMethod(eq(param1), eq(param2));
expectLastCall().andAnswer(new IAnswer() {
    public Object answer() {
        //supply your mock implementation here...
        SomeClass arg1 = (SomeClass) getCurrentArguments()[0];
        AnotherClass arg2 = (AnotherClass) getCurrentArguments()[1];
        arg1.doSomething(blah);
        //return the value to be returned by the method (null for void)
        return null;
    }
});

Javadoc sur IAnswer

22voto

eqbridges Points 2143

Si vous appelez la méthode void pour chaque temps vous vous attendez à être invoquée, puis invoque EasyMock.expectLastCall() avant d'appeler la fonction replay(), Easymock "mémoriser" chaque invocation.

Donc, je ne pense pas que vous avez besoin d'appeler explicitement "expect()" (autres que lastCall) puisque vous n'êtes pas attendre quoi que ce soit à partir d'un "vide" de la méthode, à l'exception de son invocation.

Merci Chris!

Voici un bon blog qui fournit plus de détails: http://burtbeckwith.com/blog/?p=43

5voto

piepera Points 780

Si vous voulez seulement l'accès aux paramètres pour plus tard, vous pourriez également apprécier la Capture de la classe qui est nouveau pour EasyMock 2.4.

Vous pouvez utiliser une instance de la "Capture" de la classe à la place d'un comparateur. Lorsque votre moqué méthode est appelée, l'instance de Capture enregistrer le paramètre, il a été invoqué.

Capture<ChartPanel> captured = new Capture<ChartPanel>();
// setChartPanel is going to be called during execution;
// we want to verify some things about the ChartPanel
// instance it's invoked with
chartMock.setChartPanel(capture(captured));
replay(chartMock);

ufdm.setChartAnnotater(chartMock);
// afterPropertiesSet triggers the setChartPanel call...
ufdm.afterPropertiesSet();
verify(chartMock);

// verify some things about the ChartPanel parameter our
// mock object was invoked with
assertSame(plot, captured.getValue().getChart().getPlot());

1voto

Joseph Lust Points 4961

Vous pourriez vouloir vérifier PowerMock. EasyMock est basé sur le proxy API reflection sens tout ce qui est un proxy et que vous ne pouvez tester les interfaces, et donc non seulement de finale de méthodes et de classes. Cela peut fonctionner pour certains, mais si vous testez le monde tel que construit, vous aurez besoin de plus de puissance.

Avec PowerMock Java 5 instrumentation API supprime les limitations. Pas besoin d'écrire de l'objet fantaisie implémentations de l'objet à tester (juste laid de l'OMI). Couple PowerMock avec Mockito et vous allez vraiment être hors de la course.

Bien sûr, il y a l'autre direction de la réécriture de votre code sera plus facile à tester, ce qui est généralement une bonne idée aussi, si possible.

-1voto

Marc W Points 13166

Dans de telles situations, j'ai trouvé que la réalisation d'une classe imbriquée dans mon unité de la classe de test et surchargeant les méthodes en fonction des besoins particuliers de cette manière est la meilleure route. Donc, si vous faites des tests ClassA qui a qui est de la méthode avec les paramètres dont vous avez besoin accès, vous feriez quelque chose comme:

class MockClassA extends ClassA {
    @Override
    void specialMethod(String param1, String param2) {
        // do logging or manipulation of some sort
        super.specialMethod(param1,param2); // if you need to
    }
}

Dans mon unité de test de code, j'ai ensuite il suffit d'utiliser cette instance à la place. Juste le traiter comme s'il s'agissait de tout autre objet fantaisie. Beaucoup plus facile que de mélanger des bibliothèques, ce qui j'en conviens n'est probablement pas une bonne idée.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X