Использование Espresso для Unit Test Карт Google

Я использую Espresso для тестирования некоторых пользовательских интерфейсов в своем приложении. У меня есть фрагмент с картой, и я показываю на нем некоторые элементы, которые я получаю от вызова к моему бэкэнду.

Когда я нажимаю на маркер, я делаю некоторые вещи пользовательского интерфейса

Есть ли способ сделать модульное тестирование на моей карте с помощью эспрессо?

Ответы

Ответ 1

Короткий ответ: С эспрессо на самом деле невозможно. Решением может быть использование UIAutomator: https://developer.android.com/tools/testing-support-library/index.html#UIAutomator https://developer.android.com/training/testing/ui-testing/uiautomator-testing.html

Итак, вам нужно:

1) добавить gradle зависимости:

dependencies {
androidTestCompile 'com.android.support.test:runner:0.2'
androidTestCompile 'com.android.support.test:rules:0.2'
androidTestCompile 'com.android.support.test.uiautomator:uiautomator-v18:2.1.1' }

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

3) Напишите тест, код smth вот так:

UiDevice device = UiDevice.getInstance(getInstrumentation());
UiObject marker = device.findObject(new UiSelector().descriptionContains("marker title"));
marker.click();

Объяснение:

GoogleMap создает пользовательский интерфейс, а также делает его доступным, т.е. содержимое карты можно рассматривать как дерево доступности node info.

Это дерево - виртуальное дерево представлений, оно не представляет собой реальное дерево представлений. Мы придем к этому позже

По умолчанию содержимое описания карты "Карта Google", а маркеров - "{markerTitle}. {markerSnippet}".

Тогда возникает вопрос, почему бы не использовать эспрессо:

onView(withContentDescription("marker title. ")).perform(click());

Потому что он не найдет его, однако:

onView(withContentDescription("Google Map")).perform(click());

будет работать нормально.

Итак, как работает UIAutomator, а Espresso - нет?

Поскольку они используют разные деревья просмотров.

UIAutomator использует дерево доступности node информации, предоставляемой AccessibilityService, в то время как Espresso использует иерархию представлений и, таким образом, обрабатывает всех дочерних элементов любой группы ViewGroup. Доступность node info и иерархия представлений могут или не могут сопоставляться друг с другом. В этом случае

onView (withContentDescription ( "Карта Google" ))

находит не ViewGroup, а TextureView, у которого, как известно, нет детей, поэтому Espresso не может знать, что там нарисовано.

Voila!:)