android — Как правильно протестировать ORM в Android с помощью Mockito?" />

Как правильно протестировать ORM в Android с помощью Mockito?

Я новичок в тестировании Mockito на Android и не могу понять, как тестировать методы источника данных. Я использую RushOrm, который инициализируется в классе приложения приложения:

AndroidInitializeConfig config = new AndroidInitializeConfig(getApplicationContext());
List<Class<? extends Rush>> classes = new ArrayList<>();
classes.add(CardCollection.class);
classes.add(Note.class);
config.setClasses(classes);
RushCore.initialize(config);

Мой класс источника данных:

public class CollectionsRepository implements CollectionDataSource {

    private static CollectionsRepository INSTANCE = null;
    private final CollectionDataSource dataSource;

    // Prevent direct instantiation.
    private CollectionsRepository(@NonNull CollectionDataSource dataSource) {
        this.dataSource = checkNotNull(dataSource);
    }

    public static CollectionsRepository getInstance(CollectionDataSource dataSource) {
        if (INSTANCE == null) {
            INSTANCE = new CollectionsRepository(dataSource);
        }
        return INSTANCE;
    }

    @Override
    public void getCollections(@NonNull LoadCollectionsCallback callback) {
        dataSource.getCollections(callback);
    }

    @Override
    public void getCollection(@NonNull String collectionId, @NonNull GetCollectionCallback callback) {
        dataSource.getCollection(collectionId, callback);
    }

    @Override
    public void saveCollection(@NonNull CardCollection cardCollection, @NonNull final SaveOrUpdateCollectionCallback callback) {
        dataSource.saveCollection(cardCollection, callback);
    }

    @Override
    public void updateCollection(@NonNull CardCollection cardCollection, @NonNull SaveOrUpdateCollectionCallback callback) {
        dataSource.updateCollection(cardCollection, callback);
    }

    @Override
    public void deleteCollection(@NonNull CardCollection cardCollection) {
        dataSource.deleteCollection(cardCollection);
    }

    @Override
    public void deleteAllCollections(@NonNull RushCallback callback) {
        dataSource.deleteAllCollections(callback);
    }
}

Это мой тестовый класс для класса Repository:

@Config(constants = BuildConfig.class, sdk = Build.VERSION_CODES.LOLLIPOP, application = ProjectApplication.class)
@RunWith(MockitoJUnitRunner.class)
public class CollectionsRepositoryTest {

    private CollectionPresenter presenter;

    @Mock
    private CollectionsRepository repository;

    @Mock
    private CollectionContract.View view;

    @Mock
    private CollectionDataSourceImplementation dataSource;

    @Mock
    private CollectionDataSource.GetCollectionCallback getCollectionCallback;
    @Mock
    private CollectionDataSource.LoadCollectionsCallback loadCollectionsCallback;
    @Mock
    private CollectionDataSource.SaveOrUpdateCollectionCallback saveOrUpdateCollectionCallback;

    @Captor
    private ArgumentCaptor<CollectionDataSource.GetCollectionCallback> getCollectionCallbackArgumentCaptor;
    @Captor
    private ArgumentCaptor<CollectionDataSource.LoadCollectionsCallback> loadCollectionsCallbackArgumentCaptor;
    @Captor
    private ArgumentCaptor<CollectionDataSource.SaveOrUpdateCollectionCallback> saveOrUpdateCollectionCallbackArgumentCaptor;

    private static List<CardCollection> collections = Lists.newArrayList(new CardCollection("Title1", "Description1", null),
            new CardCollection("Title2", "Description2", null));
    private final static String collection_title = "title";

    @Before
    public void setUp() {
        // Mockito has a very convenient way to inject mocks by using the @Mock annotation. To
        // inject the mocks in the test the initMocks method needs to be called.
        MockitoAnnotations.initMocks(this);

        // Get a reference to the class under test
        presenter = new CollectionPresenter(repository, view);
    }

    @Test
    public void getCollections() {
        dataSource.getCollections(loadCollectionsCallback);
        verify(dataSource).getCollections(loadCollectionsCallbackArgumentCaptor.capture());
        loadCollectionsCallbackArgumentCaptor.getValue().onSuccess(collections);
    }

    @Test
    public void getCollection() {
        dataSource.getCollection(collection_title, getCollectionCallback);
        verify(dataSource).getCollection(eq(collection_title), any(CollectionDataSourceImplementation.GetCollectionCallback.class));
    }

    @Test
    public void saveCollection() {
        CardCollection collection = new CardCollection("Title", "Description", null);
        dataSource.saveCollection(collection, saveOrUpdateCollectionCallback);
        verify(dataSource).saveCollection(collection, saveOrUpdateCollectionCallbackArgumentCaptor.capture());

        saveOrUpdateCollectionCallbackArgumentCaptor.getValue().onSuccess(collection);
    }

    @Test
    public void updateCollection() {

    }

    @Test
    public void deleteCollection() {

    }

    @Test
    public void deleteAllCollections() {

    }
}

Метод saveCollection не работает. Я гуглюсь и в основном нахожу, как проверить прямое соединение sqlite. Любые идеи будут полезны. Спасибо.

4 голоса | спросил user1140656 24 Jpm1000000pmTue, 24 Jan 2017 13:29:58 +030017 2017, 13:29:58

2 ответа


0

Похоже, вы ошиблись в модульном тестировании:

Что ваши методы делают:

  • метод test вызывает метод для объекта mocked
  • тогда вы "проверяете", что макетный метод был вызван

Проще говоря: это не имеет смысла. Идея состоит в том, что вы передаете поддельные объекты в свой производственный код; а затем вы запускаете какую-то операцию над рабочим кодом. И, наконец, вы подтверждаете, что те звонки, которые вы ожидали увидеть, действительно имели место.

И кроме того: вы не проверяете, что библиотека делает то, что она должна делать (по крайней мере, не в модульных тестах).

Вместо этого ваш модульный тест должен проверять только ту проводку , которую выполняет ваша продукция. Другими словами: единственное, что вам нужно проверить, - это то, что аргументы, которые ваш производственный код передает вызову некоторых библиотечных методов, являются ожидаемыми.

Конечно, вы должны провести некоторое тестирование на "уровне интеграции", чтобы убедиться, что все это работает непрерывно. Но это, как правило, выходит за рамки области применения модульного теста (как уже говорят нам названия!)

ответил GhostCat 1 FebruaryEurope/MoscowbWed, 01 Feb 2017 17:46:03 +0300000000pmWed, 01 Feb 2017 17:46:03 +030017 2017, 17:46:03
0

Я думаю, что ошибка может быть в этой строке:

verify(dataSource).saveCollection(collection, saveOrUpdateCollectionCallbackArgumentCaptor.capture());

Изменить на:

verify(dataSource).saveCollection(collection, saveOrUpdateCollectionCallback);

Вы не можете проверить метод с другим параметром.

ответил antonicg 1 FebruaryEurope/MoscowbWed, 01 Feb 2017 15:03:12 +0300000000pmWed, 01 Feb 2017 15:03:12 +030017 2017, 15:03:12

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

Популярные теги

security × 330linux × 316macos × 2827 × 268performance × 244command-line × 241sql-server × 235joomla-3.x × 222java × 189c++ × 186windows × 180cisco × 168bash × 158c# × 142gmail × 139arduino-uno × 139javascript × 134ssh × 133seo × 132mysql × 132