Почему android эспрессо-тест не проходит при проверке, заканчивается ли текст textView ожидаемой строкой - PullRequest
0 голосов
/ 26 апреля 2020

У меня есть тест android, проверяющий, что внешнее текстовое сообщение обрезается и заканчивается тремя точками при применении android: ellipsize = "end". Я не знаю, почему тест не пройден, несмотря на то, что текст, представленный в упражнении, правильно отформатирован.

enter image description here

@Test
fun when_errorMessage_is_very_long_then_text_of_errorMessageTextView_ends_with_dots() {

    //given
    val errorMessage = """
            Very long error, Very long error, Very long error, Very long error, Very long error,
            Very long error, Very long error, Very long error, Very long error, Very long error,
            Very long error, Very long error, Very long error, Very long error, Very long error,
            Very long error, Very long error, Very long error, Very long error, Very long 
    error,"""

    //when
    presentErrorActivityWith(errorMessage)

    //then
    onView(withId(R.id.errorMessageTextView)).check(matches(withText(endsWith("..."))));
}

screenshot of ErrorActivity

Я использую функциональность, импортированную из

import androidx.test.espresso.Espresso.onView
import androidx.test.espresso.assertion.ViewAssertions.matches
import androidx.test.espresso.matcher.ViewMatchers.withId
import androidx.test.espresso.matcher.ViewMatchers.withText
import androidx.test.ext.junit.runners.AndroidJUnit4

объявление errorMessageTextView в макете ErrorActivity

<TextView
    android:id="@+id/errorMessageTextView"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"

    android:ellipsize="end"
    android:maxLines="2"

    android:paddingLeft="24dp"
    android:paddingRight="24dp"

    android:layout_marginTop="8dp"

    android:layout_marginStart="40dp"
    android:layout_marginLeft="40dp"
    android:layout_marginEnd="40dp"
    android:layout_marginRight="40dp"
    app:layout_constraintTop_toBottomOf="@+id/errorMessageTitleTextView"
    app:layout_constraintEnd_toEndOf="parent"
    app:layout_constraintStart_toStartOf="parent"
    android:text=""/>

Ответы [ 3 ]

1 голос
/ 27 апреля 2020

Чтобы проверить, имеет ли текст TextView эллиптический размер, вы можете создать свой собственный сопоставитель, подобный этому:

fun ellipsized() = object : TypeSafeMatcher<View>() {
    override fun describeTo(description: Description) {
        description.appendText("with ellipsized text")
    }

    override fun matchesSafely(v: View): Boolean {
        if (!(v is TextView)) {
            return false
        }
        val textView: TextView = v
        val layout: Layout = textView.getLayout()
        val lines = layout.lineCount
        if (lines > 0) {
            val ellipsisCount = layout.getEllipsisCount(lines - 1)
            if (ellipsisCount > 0) {
                return true
            }
        }

        return false
    }
}

И назвать его так:

onView(withId(R.id.errorMessageTextView))
    .check(matches(ellipsized()))
0 голосов
/ 26 апреля 2020

Вы не можете проверить TextView с android:ellipsize, проверив, заканчивается ли оно "..."

Это потому, что даже если вы видите, что оно заканчивается на "...", но оно на самом деле не заканчивается на "...".

Чтобы проверить это, вы можете сделать этот тест

@Test
fun check_textview_text() {

    //given
    val errorMessage = """
            Very long error, Very long error, Very long error, Very long error, Very long error,
            Very long error, Very long error, Very long error, Very long error, Very long error,
            Very long error, Very long error, Very long error, Very long error, Very long error,
            Very long error, Very long error, Very long error, Very long error, Very long 
    error,"""

    //when
    presentErrorActivityWith(errorMessage)

    //then
    onView(withId(R.id.errorMessageTextView)).check(matches(withText(containsString(errorMessage ))));
}

Этот тест должен пройти, если ваша TextView содержит ту же строку, что и в errorMessage переменная. Хотя на самом деле вместо этого вы видите на экране три точки «...».

Потому что на самом деле под капотом android система не устанавливает «...» в конец усеченной строки текст поля TextView.

Чтобы проверить android:ellipsize правильный путь:

@RunWith(AndroidJUnit4.class)
public class TextViewLongTextWithEllipsizeTest {
    private static final String TAG = "LOG_TAG";

    @Rule
    public ActivityTestRule mActivityRule = new ActivityTestRule<>(
            LongTextActivity.class);

    /**
     * Testing if a TextView uses "android:ellipsize"
     * at the end of its text as the text is long
     */
    @Test
    public void testTextIsEllipsized() {

        TextView textView = mActivityRule.getActivity().findViewById(R.id.errorMessageTextView);

        Layout layout = textView.getLayout();
        if (layout != null) {
            int ellipsisCount = layout.getEllipsisCount(layout.getLineCount() - 1);
            assertThat(ellipsisCount, is(greaterThan(0))); // if true then text is ellipsized
        }
    }

    /**
     * Testing if a TextView doesn't use "android:ellipsize"
     * at the end of its text as the text is not that long
     */
    @Test
    public void testTextNotEllipsized() {

        TextView textView = mActivityRule.getActivity().findViewById(R.id.no_ellipsize_text);

        Layout layout = textView.getLayout();
        if (layout != null) {
            int ellipsisCount = layout.getEllipsisCount(layout.getLineCount() - 1);
            assertThat(ellipsisCount, not(greaterThan(0))); // if true then text is not ellipsized
        }
    }


}

Подсказка: I только что добавили метод теста, пожалуйста, повторите тест с учетом и при утверждениях перед тестированием.

0 голосов
/ 26 апреля 2020

Это может быть потому, что вы проверяете строку "..." вместо строки "…" (последняя - один символ вместо трех символов точки).

Дважды проверьте это, посмотрев на Эспрессо выход. "Got: AppCompatTextView" ..." содержит text= часть, которая точно сообщает, какой текст Эспрессо находит в представлении.

...