Mockito:有没有办法用假数据调用/运行真正的方法。

时间:2017-07-18 10:51:02

标签: android unit-testing junit mockito

尝试使用一些假数据(测试数据)调用方法。我知道返回值可以覆盖doReturn(),thenReturn(),但这里的场景是覆盖将要传递的参数而不是方法的返回值或行为。和实际的服务类,

的DataService

public class DataService extends IntentService {

@Override
protected void onHandleIntent(@Nullable Intent intent) {
       DataAcquirer.getInstance()
                    .subscribe(DataService.this,dataCallback);
}

DataAcquirer.DataCallback dataCallback = new DataAcquirer.DataCallback() {
        @Override
        public void onResult(Data data) {
         //some process here
        }  
      };
}

然后问题是如何在测试类中运行onResult(Data data)方法并传递测试数据(硬编码数据)。

DataServiceTest

@MediumTest
@RunWith(AndroidJUnit4.class)
@FixMethodOrder(MethodSorters.NAME_ASCENDING)
public class DataServiceTest {

@Rule
public ServiceTestRule mServiceTestRule =  new ServiceTestRule();

    @Mock
    DataService mockDataService;

    @Mock
    Data data;

    @Mock
    DataCallback callback;

    @Mock
    DataAcquirer mockDA;

    @Before
    public void setup(){
        MockitoAnnotations.initMocks(this);
    }

    @Test
    public void testDataProcessing() throws InterruptedException {
        Intent intent = new Intent(context, DataFetchService.class);
        intent.putExtra(res.getString(R.string.type), "options_one");
        mServiceTestRule.startService(intent);


        data.temp =(float) -15.37;
        //This should run actual work in DataService with the data provided here 
        mockDataService.callback.onResult(data);
    }
}

2 个答案:

答案 0 :(得分:1)

你正在以一种错误的方式“嘲笑”。

这个想法是:您为测试类所依赖的内容创建@Mock(模拟)对象。

从这个意义上说:你可以简单地做到

@Mock
Intent mockedIntent;

然后传递在调用时模拟对象。

答案 1 :(得分:0)

如何将测试数据传递给DataCallback?我会说通过模拟DataAcquirer(或注入测试一个)并让服务完成工作而不是手动调用onResult(...)。

    package test;

    import org.junit.Before;
    import org.junit.Test;
    import org.junit.runner.RunWith;
    import org.mockito.Mockito;
    import org.mockito.invocation.InvocationOnMock;
    import org.mockito.stubbing.Answer;
    import org.powermock.api.mockito.PowerMockito;
    import org.powermock.core.classloader.annotations.PrepareForTest;
    import org.powermock.modules.junit4.PowerMockRunner;

    import test.DataServiceTest.DataAcquirer;
    import test.DataServiceTest.DataAcquirer.DataCallback;

    import static org.mockito.Matchers.any;

    @RunWith(PowerMockRunner.class)
    @PrepareForTest(DataAcquirer.class)
    public class DataServiceTest {

      @Before
      public void setUp() {
        DataAcquirer mockDataAcquirer = Mockito.mock(DataAcquirer.class);
        Mockito.doAnswer(new Answer() {
          @Override
          public Void answer(InvocationOnMock invocation) throws Throwable {
            DataCallback dataCallback = invocation.getArgumentAt(0, DataCallback.class);

            dataCallback.onResult("test data");

            return null;
          }
        }).when(mockDataAcquirer).subscribe(any(DataCallback.class));

        PowerMockito.mockStatic(DataAcquirer.class);
        Mockito.when(DataAcquirer.getInstance()).thenReturn(mockDataAcquirer);
      }

      @Test
      public void testName() {
        DataAcquirer dataAcquirer = DataAcquirer.getInstance();

        dataAcquirer.subscribe(new DataCallback() {
          @Override
          public void onResult(String data) {
            assertThat(data, is("test data"));
          }
        });
     }

      public static class DataAcquirer {

        public static DataAcquirer getInstance() {
          return new DataAcquirer();
        }

        private DataAcquirer() {
        }

        public void subscribe(DataCallback dataCallback) {
          // real implementation
        }

        public static class DataCallback {

          public void onResult(String data) {
          }

        }
      }
    }