• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2020 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 package com.android.test.input
17 
18 import androidx.test.ext.junit.runners.AndroidJUnit4
19 import androidx.test.platform.app.InstrumentationRegistry
20 import androidx.test.filters.MediumTest
21 
22 import android.graphics.Rect
23 import android.os.SystemClock
24 import android.provider.Settings
25 import android.provider.Settings.Global.HIDE_ERROR_DIALOGS
26 import android.support.test.uiautomator.By
27 import android.support.test.uiautomator.UiDevice
28 import android.support.test.uiautomator.UiObject2
29 import android.support.test.uiautomator.Until
30 import android.view.InputDevice
31 import android.view.MotionEvent
32 
33 import org.junit.After
34 import org.junit.Assert.fail
35 import org.junit.Before
36 import org.junit.Test
37 import org.junit.runner.RunWith
38 
39 /**
40  * This test makes sure that an unresponsive gesture monitor gets an ANR.
41  *
42  * The gesture monitor must be registered from a different process than the instrumented process.
43  * Otherwise, when the test runs, you will get:
44  * Test failed to run to completion.
45  * Reason: 'Instrumentation run failed due to 'keyDispatchingTimedOut''.
46  * Check device logcat for details
47  * RUNNER ERROR: Instrumentation run failed due to 'keyDispatchingTimedOut'
48  */
49 @MediumTest
50 @RunWith(AndroidJUnit4::class)
51 class AnrTest {
52     companion object {
53         private const val TAG = "AnrTest"
54     }
55 
56     val mInstrumentation = InstrumentationRegistry.getInstrumentation()
57     var mHideErrorDialogs = 0
58 
59     @Before
setUpnull60     fun setUp() {
61         val contentResolver = mInstrumentation.targetContext.contentResolver
62         mHideErrorDialogs = Settings.Global.getInt(contentResolver, HIDE_ERROR_DIALOGS, 0)
63         Settings.Global.putInt(contentResolver, HIDE_ERROR_DIALOGS, 0)
64     }
65 
66     @After
tearDownnull67     fun tearDown() {
68         val contentResolver = mInstrumentation.targetContext.contentResolver
69         Settings.Global.putInt(contentResolver, HIDE_ERROR_DIALOGS, mHideErrorDialogs)
70     }
71 
72     @Test
testGestureMonitorAnrnull73     fun testGestureMonitorAnr() {
74         startUnresponsiveActivity()
75         val uiDevice: UiDevice = UiDevice.getInstance(mInstrumentation)
76         val obj: UiObject2? = uiDevice.wait(Until.findObject(
77                 By.text("Unresponsive gesture monitor")), 10000)
78 
79         if (obj == null) {
80             fail("Could not find unresponsive activity")
81             return
82         }
83 
84         val rect: Rect = obj.visibleBounds
85         val downTime = SystemClock.uptimeMillis()
86         val downEvent = MotionEvent.obtain(downTime, downTime,
87                 MotionEvent.ACTION_DOWN, rect.left.toFloat(), rect.top.toFloat(), 0 /* metaState */)
88         downEvent.source = InputDevice.SOURCE_TOUCHSCREEN
89 
90         mInstrumentation.uiAutomation.injectInputEvent(downEvent, false /* sync*/)
91 
92         // Todo: replace using timeout from android.hardware.input.IInputManager
93         SystemClock.sleep(5000) // default ANR timeout for gesture monitors
94 
95         clickCloseAppOnAnrDialog()
96     }
97 
clickCloseAppOnAnrDialognull98     private fun clickCloseAppOnAnrDialog() {
99         // Find anr dialog and kill app
100         val uiDevice: UiDevice = UiDevice.getInstance(mInstrumentation)
101         val closeAppButton: UiObject2? =
102                 uiDevice.wait(Until.findObject(By.res("android:id/aerr_close")), 20000)
103         if (closeAppButton == null) {
104             fail("Could not find anr dialog")
105             return
106         }
107         closeAppButton.click()
108     }
109 
startUnresponsiveActivitynull110     private fun startUnresponsiveActivity() {
111         val flags = " -W -n "
112         val startCmd = "am start $flags com.android.test.input/.UnresponsiveGestureMonitorActivity"
113         mInstrumentation.uiAutomation.executeShellCommand(startCmd)
114     }
115 }