Многократный макет статического метода с использованием JMockit в тесте JUnit - PullRequest
6 голосов
/ 05 февраля 2011

У меня есть класс со статическими методами, которые я в настоящее время высмеиваю с помощью JMockit.Скажем, это выглядит примерно так:

public class Foo {
    public static FooValue getValue(Object something) {
        ...
    }
    public static enum FooValue { X, Y, Z, ...; }
}

У меня есть другой класс (назовем его MyClass), который вызывает статический метод Foo;Я пытаюсь написать контрольные примеры для этого класса.Мой тест JUnit, использующий JMockit, выглядит примерно так:

public class MyClassTest extends TestCase {
    @NonStrict private final Foo mock = null;

    @Test public void testMyClass() {
        new Expectations() {
            {
                Foo.getValue((Object) any); result = Foo.FooValue.X;
            }
        };
    }

    myClass.doSomething();
}

Это прекрасно работает, и когда тест выполнен, мой экземпляр MyClass правильно получит значение перечисления Foo.FooValue.X, ​​когдаон вызывает Foo.getValue ().

Теперь я пытаюсь перебрать все значений в перечислении и повторно запустить тест.Если я помещу приведенный выше тестовый код в цикл for и попытаюсь установить для результата проверяемого статического метода каждое значение перечисления, это не сработает.Модифицированная версия Foo.getValue () всегда возвращает Foo.FooValue.X, ​​и никогда не использует другие значения, пока я выполняю итерацию в перечислении.

Как я могу выполнить насмешку над статическим методом несколько раз в пределаходиночный тест JUnit?Я хочу сделать что-то вроде этого (но, очевидно, это не работает):

public class MyClassTest extends TestCase {
    @NonStrict private final Foo mock = null;

    @Test public void testMyClass() {

        for (final Foo.FooValue val : Foo.FooValue.values() {

            new Expectations() {
                {
                    // Here, I'm attempting to redefine the mocked method during each iteration
                    // of the loop. Apparently, that doesn't work.
                    Foo.getValue((Object) any); result = val;
                }
            };

            myClass.doSomething();
        }

    }
}

Есть идеи?

1 Ответ

5 голосов
/ 08 февраля 2011

Вместо "насмешки над методом несколько раз", вы должны записать несколько последовательных возвращаемых значений в одну запись:

public class MyClassTest extends TestCase
{
    @Test
    public void testMyClass(@Mocked Foo anyFoo)
    {
        new Expectations() {{
            Foo.getValue(any);
            result = Foo.FooValue.values();
        }};

        for (Foo.FooValue val : Foo.FooValue.values() {
            myClass.doSomething();
        }
    }
}

Это также может быть сделано с Delegate, если требуется большая гибкость.

...