首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何通过Espresso测试方法更新活动的UI元素?

如何通过Espresso测试方法更新活动的UI元素?
EN

Stack Overflow用户
提问于 2016-02-16 07:21:52
回答 1查看 1.4K关注 0票数 2

我正试图为我的活动编写一个测试用例。我的活动中有一个更新UI的方法。

代码语言:javascript
复制
public void setBooking(Booking booking)
{
    if (booking == null)
    {
        return;
    }

    this.mBooking = booking;
    this.mBookingExt.updateUI();
}

这是我的考试课:

代码语言:javascript
复制
@RunWith(AndroidJUnit4.class)
public class LocatingActivityTest
{
    @Rule
    public ActivityTestRule<BookingActivity> mActivityTestRule = new ActivityTestRule<>(BookingActivity.class);

    private BookingActivity mBookingActivity;

    @Before
    public void setup()
    {
        mBookingActivity = mActivityTestRule.getActivity();
        mBookingActivity.setBooking(BookingTest.getStandardTaxi()); // << My Fake Booking Object

        onView(withId(R.id.book_now)).perform(click());
    }

    @Test
    public void viewsMustBeVisible()
    {
        onView(withId(R.id.locating_text)).check(matches(isCompletelyDisplayed()));
        onView(withId(R.id.sonarView)).check(matches(isCompletelyDisplayed()));
        onView(withId(R.id.cancel_booking)).check(matches(isCompletelyDisplayed()));
    }
}

当我运行测试时,我会得到以下错误:

android.view.ViewRootImpl$CalledFromWrongThreadException:只有创建视图层次结构的原始线程才能触摸其视图。

我认为@Before运行在UI线程上,所以不知道这个抱怨来自哪里!这是我的参考 (ActivityTestRule扩展UiThreadTestRule)。

所以我决定稍微改变一下类的架构。因此,setup()viewsMustBeVisible()改为:

代码语言:javascript
复制
    @Before
    public void setup()
    {
        mBookingTaxiActivity = mActivityTestRule.getActivity();
    }

    @UiThreadTest // from android.support.test.annotation.UiThreadTest
    public void viewsMustBeVisible()
    {
        mBookingTaxiActivity.setBooking(BookingTest.getStandardTaxi()); // << My Fake Booking Object

        onView(withId(R.id.fab_booking)).perform(click());
        onView(withId(R.id.booking_book_now)).check(matches(isEnabled()));
        onView(withId(R.id.booking_book_now)).perform(click());

        onView(withId(R.id.locating_text)).check(matches(isCompletelyDisplayed()));
        onView(withId(R.id.sonarView)).check(matches(isCompletelyDisplayed()));
        onView(withId(R.id.locating_cancel_booking)).check(matches(isCompletelyDisplayed()));
    }

但是,这一次我会遇到以下错误:

java.lang.Exception:没有可运行的方法

最后,我更改了上面的方法,以便在UI线程上运行测试:

代码语言:javascript
复制
    @Test
    public void viewsMustBeVisible()
    {
        mBookingTaxiActivity.runOnUiThread(new Runnable()
        {
            @Override
            public void run()
            {
                mBookingTaxiActivity.setBooking(BookingTest.getStandardTaxi()); // << My Fake Booking Object

                onView(withId(R.id.fab_booking)).perform(click());
                onView(withId(R.id.booking_book_now)).check(matches(isEnabled()));
                onView(withId(R.id.booking_book_now)).perform(click());

                onView(withId(R.id.locating_text)).check(matches(isCompletelyDisplayed()));
                onView(withId(R.id.sonarView)).check(matches(isCompletelyDisplayed()));
                onView(withId(R.id.locating_cancel_booking)).check(matches(isCompletelyDisplayed()));
        });
    }

这里的问题是测试永远不会完成。我等了6-7分钟,它的进度指标还在旋转,似乎永远做不到。

我想我已经检查了更新我的预订对象以及UI元素的所有方法。

EN

回答 1

Stack Overflow用户

发布于 2016-02-17 06:32:50

很好,很多小时后我就拿到了。我不知道有什么不同,但我移动UI线程在活动中工作。新的测试方法如下所示:

代码语言:javascript
复制
    @Test
    public void viewsMustBeVisible()
    {
        onView(withId(R.id.fab_booking)).perform(click());

        mBookingTaxiActivity.setTestBooking(BookingTest.getStandardTaxi());

        onView(withId(R.id.booking_book_now)).check(matches(isEnabled()));
        onView(withId(R.id.booking_book_now)).perform(click());

        onView(withId(R.id.locating_text)).check(matches(isCompletelyDisplayed()));
        onView(withId(R.id.sonarView)).check(matches(isCompletelyDisplayed()));
        onView(withId(R.id.locating_cancel_booking)).check(matches(isCompletelyDisplayed()));
    }

我在活动端创建了一个方法来更新我的对象:

代码语言:javascript
复制
    // Required just for Testing purposes
    @VisibleForTesting
    public void setTestBooking(Booking booking)
    {
        if (booking == null)
        {
            return;
        }

        this.mBooking = booking;

        this.runOnUiThread(new Runnable()
        {
            @Override
            public void run()
            {
                BookingActivity.this.mBookingExt.updateUI();
                findViewById(R.id.booking_book_now).setEnabled(true);
            }
        });
    }

如果你有同样的问题,希望它对你有帮助。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/35426215

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档