Как издеваться над приватным методом с использованием powermock с одним из параметров в виде массива байтов [duplicate]

У меня есть другая перспектива ответить на это.

При работе на разных уровнях, например, в приложении MVC, контроллеру нужны службы для вызова бизнес-операций. В таких сценариях контейнер инжекции зависимостей может использоваться для инициализации служб, чтобы исключить исключение NullReferenceException. Это означает, что вам не нужно беспокоиться о проверке нулевого значения и просто вызвать службы с контроллера, как будто они всегда будут доступны (и инициализированы) как одиночный или прототип.

public class MyController
{
    private ServiceA serviceA;
    private ServiceB serviceB;

    public MyController(ServiceA serviceA, ServiceB serviceB)
    {
        this.serviceA = serviceA;
        this.serviceB = serviceB;
    }

    public void MyMethod()
    {
        // We don't need to check null because the dependency injection container 
        // injects it, provided you took care of bootstrapping it.
        var someObject = serviceA.DoThis();
    }
}
54
задан ArtB 8 November 2011 в 23:10
поделиться

4 ответа

Я не вижу здесь проблемы. Со следующим кодом, использующим API Mockito, мне удалось сделать именно это:

public class CodeWithPrivateMethod {

    public void meaningfulPublicApi() {
        if (doTheGamble("Whatever", 1 << 3)) {
            throw new RuntimeException("boom");
        }
    }

    private boolean doTheGamble(String whatever, int binary) {
        Random random = new Random(System.nanoTime());
        boolean gamble = random.nextBoolean();
        return gamble;
    }
}

И вот тест JUnit:

import org.junit.Test;
import org.junit.runner.RunWith;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;
import static org.mockito.Matchers.anyInt;
import static org.mockito.Matchers.anyString;
import static org.powermock.api.mockito.PowerMockito.when;
import static org.powermock.api.support.membermodification.MemberMatcher.method;

@RunWith(PowerMockRunner.class)
@PrepareForTest(CodeWithPrivateMethod.class)
public class CodeWithPrivateMethodTest {

    @Test(expected = RuntimeException.class)
    public void when_gambling_is_true_then_always_explode() throws Exception {
        CodeWithPrivateMethod spy = PowerMockito.spy(new CodeWithPrivateMethod());

        when(spy, method(CodeWithPrivateMethod.class, "doTheGamble", String.class, int.class))
                .withArguments(anyString(), anyInt())
                .thenReturn(true);

        spy.meaningfulPublicApi();
    }
}
87
ответ дан Brice 25 August 2018 в 20:26
поделиться

Я знаю способ ny, который вы можете назвать приватной функцией для проверки в mockito

@Test
    public  void  commandEndHandlerTest() throws  Exception
    {
        Method retryClientDetail_privateMethod =yourclass.class.getDeclaredMethod("Your_function_name",null);
        retryClientDetail_privateMethod.setAccessible(true);
        retryClientDetail_privateMethod.invoke(yourclass.class, null);
    }
1
ответ дан Arun Yadav 25 August 2018 в 20:26
поделиться

Общее решение, которое будет работать с любой средой тестирования (, если ваш класс не является final), - это вручную создать свой собственный макет.

  1. Изменить ваш частный метод для защиты.
  2. В вашем тестовом классе расширение класса
  3. переопределяет ранее закрытый метод для возврата любой константы, которую вы хотите

Это не использует фреймворк, поэтому он не такой элегантный, но он всегда будет работать: даже без PowerMock. Кроме того, вы можете использовать Mockito для выполнения шагов №2 и amp; # 3 для вас, если вы уже сделали шаг №1.

Чтобы издеваться над частным методом напрямую, вам нужно использовать PowerMock, как показано в другом ответе .

19
ответ дан Community 25 August 2018 в 20:26
поделиться

По какой-то причине ответ Брайса не работает для меня. Я смог немного манипулировать им, чтобы заставить его работать. Это может быть просто из-за того, что у меня новая версия PowerMock. Я использую 1.6.5.

import java.util.Random;

public class CodeWithPrivateMethod {

    public void meaningfulPublicApi() {
        if (doTheGamble("Whatever", 1 << 3)) {
            throw new RuntimeException("boom");
        }
    }

    private boolean doTheGamble(String whatever, int binary) {
        Random random = new Random(System.nanoTime());
        boolean gamble = random.nextBoolean();
        return gamble;
    }
}

Класс тестирования выглядит следующим образом:

import org.junit.Test;
import org.junit.runner.RunWith;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;

import static org.mockito.Matchers.anyInt;
import static org.mockito.Matchers.anyString;
import static org.powermock.api.mockito.PowerMockito.doReturn;

@RunWith(PowerMockRunner.class)
@PrepareForTest(CodeWithPrivateMethod.class)
public class CodeWithPrivateMethodTest {
    private CodeWithPrivateMethod classToTest;

    @Test(expected = RuntimeException.class)
    public void when_gambling_is_true_then_always_explode() throws Exception {
        classToTest = PowerMockito.spy(classToTest);

        doReturn(true).when(classToTest, "doTheGamble", anyString(), anyInt());

        classToTest.meaningfulPublicApi();
    }
}
1
ответ дан gaoagong 25 August 2018 в 20:26
поделиться
Другие вопросы по тегам:

Похожие вопросы: