• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2014 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.cts.deviceowner;
17 
18 import android.app.ActivityManager;
19 import android.content.BroadcastReceiver;
20 import android.content.Context;
21 import android.content.Intent;
22 import android.content.IntentFilter;
23 import android.provider.Settings;
24 
25 // This is not a standard test of an android activity (such as
26 // ActivityInstrumentationTestCase2) as it is attempting to test the actual
27 // life cycle and how it is affected by lock task, rather than mock intents
28 // and setup.
29 public class LockTaskTest extends BaseDeviceOwnerTest {
30 
31     private static final String TEST_PACKAGE = "com.google.android.example.somepackage";
32 
33     private static final int ACTIVITY_RESUMED_TIMEOUT_MILLIS = 60000;  // 60 seconds
34     private static final int ACTIVITY_RUNNING_TIMEOUT_MILLIS = 20000;  // 20 seconds
35 
36     /**
37      * The tests below need to keep detailed track of the state of the activity
38      * that is started and stopped frequently.  To do this it sends a number of
39      * broadcasts that are caught here and translated into booleans (as well as
40      * notify some locks in case we are waiting).  There is also an action used
41      * to specify that the activity has finished handling the current command
42      * (INTENT_ACTION).
43      */
44     private final BroadcastReceiver mReceiver = new BroadcastReceiver() {
45         @Override
46         public void onReceive(Context context, Intent intent) {
47             String action = intent.getAction();
48             if (LockTaskUtilityActivity.CREATE_ACTION.equals(action)) {
49                 synchronized (mActivityRunningLock) {
50                     mIsActivityRunning = true;
51                     mActivityRunningLock.notify();
52                 }
53             } else if (LockTaskUtilityActivity.DESTROY_ACTION.equals(action)) {
54                 synchronized (mActivityRunningLock) {
55                     mIsActivityRunning = false;
56                     mActivityRunningLock.notify();
57                 }
58             } else if (LockTaskUtilityActivity.RESUME_ACTION.equals(action)) {
59                 synchronized (mActivityResumedLock) {
60                     mIsActivityResumed = true;
61                     mActivityResumedLock.notify();
62                 }
63             } else if (LockTaskUtilityActivity.PAUSE_ACTION.equals(action)) {
64                 synchronized (mActivityResumedLock) {
65                     mIsActivityResumed = false;
66                     mActivityResumedLock.notify();
67                 }
68             } else if (LockTaskUtilityActivity.INTENT_ACTION.equals(action)) {
69                 // Notify that intent has been handled.
70                 synchronized (LockTaskTest.this) {
71                     mIntentHandled = true;
72                     LockTaskTest.this.notify();
73                 }
74             }
75         }
76     };
77 
78     private boolean mIsActivityRunning;
79     private boolean mIsActivityResumed;
80     private final Object mActivityRunningLock = new Object();
81     private final Object mActivityResumedLock = new Object();
82     private Boolean mIntentHandled;
83 
84     @Override
setUp()85     protected void setUp() throws Exception {
86         super.setUp();
87         IntentFilter filter = new IntentFilter();
88         filter.addAction(LockTaskUtilityActivity.CREATE_ACTION);
89         filter.addAction(LockTaskUtilityActivity.DESTROY_ACTION);
90         filter.addAction(LockTaskUtilityActivity.INTENT_ACTION);
91         filter.addAction(LockTaskUtilityActivity.RESUME_ACTION);
92         filter.addAction(LockTaskUtilityActivity.PAUSE_ACTION);
93         mContext.registerReceiver(mReceiver, filter);
94     }
95 
96     @Override
tearDown()97     protected void tearDown() throws Exception {
98         mContext.unregisterReceiver(mReceiver);
99         super.tearDown();
100     }
101 
testSetLockTaskPackages()102     public void testSetLockTaskPackages() {
103         mDevicePolicyManager.setLockTaskPackages(getWho(), new String[] { TEST_PACKAGE });
104         assertTrue(mDevicePolicyManager.isLockTaskPermitted(TEST_PACKAGE));
105 
106         mDevicePolicyManager.setLockTaskPackages(getWho(), new String[0]);
107         assertFalse(mDevicePolicyManager.isLockTaskPermitted(TEST_PACKAGE));
108     }
109 
110     // Start lock task, verify that ActivityManager knows thats what is going on.
testStartLockTask()111     public void testStartLockTask() {
112         mDevicePolicyManager.setLockTaskPackages(getWho(), new String[] { PACKAGE_NAME });
113         startLockTask();
114         waitForResume();
115 
116         // Verify that activity open and activity manager is in lock task.
117         ActivityManager activityManager = (ActivityManager)
118                 mContext.getSystemService(Context.ACTIVITY_SERVICE);
119         assertTrue(activityManager.isInLockTaskMode());
120         assertTrue(mIsActivityRunning);
121         assertTrue(mIsActivityResumed);
122 
123         stopAndFinish(activityManager);
124     }
125 
126     // Verifies that the act of finishing is blocked by ActivityManager in lock task.
127     // This results in onDestroy not being called until stopLockTask is called before finish.
testCannotFinish()128     public void testCannotFinish() {
129         mDevicePolicyManager.setLockTaskPackages(getWho(), new String[] { PACKAGE_NAME });
130         startLockTask();
131 
132         // If lock task has not exited then the activity shouldn't actually receive onDestroy.
133         finishAndWait();
134         ActivityManager activityManager = (ActivityManager)
135                 mContext.getSystemService(Context.ACTIVITY_SERVICE);
136         assertTrue(activityManager.isInLockTaskMode());
137         assertTrue(mIsActivityRunning);
138 
139         stopAndFinish(activityManager);
140     }
141 
142     // This test has the UtilityActivity trigger starting another activity (settings)
143     // this should be permitted as a part of lock task (since it isn't a new task).
144     // As a result onPause should be called as it goes to a new activity.
testStartActivityWithinTask()145     public void testStartActivityWithinTask() {
146         mDevicePolicyManager.setLockTaskPackages(getWho(), new String[] { PACKAGE_NAME });
147         startLockTask();
148         waitForResume();
149 
150         Intent launchIntent = new Intent(Settings.ACTION_SETTINGS);
151         Intent lockTaskUtility = getLockTaskUtility();
152         lockTaskUtility.putExtra(LockTaskUtilityActivity.START_ACTIVITY, launchIntent);
153         mContext.startActivity(lockTaskUtility);
154 
155         synchronized (mActivityResumedLock) {
156             if (mIsActivityResumed) {
157                 try {
158                     mActivityResumedLock.wait(ACTIVITY_RESUMED_TIMEOUT_MILLIS);
159                 } catch (InterruptedException e) {
160                 }
161                 assertFalse(mIsActivityResumed);
162             }
163         }
164         stopAndFinish(null);
165     }
166 
167     // This launches an activity that is not part of the current task and therefore
168     // should be blocked.  This is verified by making sure that the activity does
169     // not get a call to onPause.
testCannotStartActivityOutsideTask()170     public void testCannotStartActivityOutsideTask() {
171         mDevicePolicyManager.setLockTaskPackages(getWho(), new String[] { PACKAGE_NAME });
172         startLockTask();
173         waitForResume();
174 
175         Intent launchIntent = new Intent(Settings.ACTION_SETTINGS);
176         launchIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
177         mContext.startActivity(launchIntent);
178 
179         synchronized (mActivityResumedLock) {
180             try {
181                 mActivityResumedLock.wait(ACTIVITY_RESUMED_TIMEOUT_MILLIS);
182             } catch (InterruptedException e) {
183             }
184             assertTrue(mIsActivityResumed);
185         }
186         stopAndFinish(null);
187     }
188 
189     /**
190      * Call stopLockTask and finish on the LockTaskUtilityActivity.
191      *
192      * Verify that the activity is no longer running.
193      *
194      * If activityManager is not null then verify that the ActivityManager
195      * is no longer in lock task mode.
196      */
stopAndFinish(ActivityManager activityManager)197     private void stopAndFinish(ActivityManager activityManager) {
198         stopLockTask();
199         finishAndWait();
200         if (activityManager != null) {
201             assertFalse(activityManager.isInLockTaskMode());
202         }
203         assertFalse(mIsActivityRunning);
204     }
205 
206     /**
207      * Call finish on the LockTaskUtilityActivity and wait for
208      * onDestroy to be called.
209      */
finishAndWait()210     private void finishAndWait() {
211         synchronized (mActivityRunningLock) {
212             finish();
213             if (mIsActivityRunning) {
214                 try {
215                     mActivityRunningLock.wait(ACTIVITY_RUNNING_TIMEOUT_MILLIS);
216                 } catch (InterruptedException e) {
217                 }
218             }
219         }
220     }
221 
222     /**
223      * Wait for onPause to be called on the LockTaskUtilityActivity.
224      */
waitForResume()225     private void waitForResume() {
226         // It may take a moment for the resume to come in.
227         synchronized (mActivityResumedLock) {
228             if (!mIsActivityResumed) {
229                 try {
230                     mActivityResumedLock.wait(ACTIVITY_RESUMED_TIMEOUT_MILLIS);
231                 } catch (InterruptedException e) {
232                 }
233             }
234         }
235     }
236 
237     /**
238      * Calls startLockTask on the LockTaskUtilityActivity
239      */
startLockTask()240     private void startLockTask() {
241         Intent intent = getLockTaskUtility();
242         intent.putExtra(LockTaskUtilityActivity.START_LOCK_TASK, true);
243         startAndWait(intent);
244     }
245 
246     /**
247      * Calls stopLockTask on the LockTaskUtilityActivity
248      */
stopLockTask()249     private void stopLockTask() {
250         Intent intent = getLockTaskUtility();
251         intent.putExtra(LockTaskUtilityActivity.STOP_LOCK_TASK, true);
252         startAndWait(intent);
253     }
254 
255     /**
256      * Calls finish on the LockTaskUtilityActivity
257      */
finish()258     private void finish() {
259         Intent intent = getLockTaskUtility();
260         intent.putExtra(LockTaskUtilityActivity.FINISH, true);
261         startAndWait(intent);
262     }
263 
264     /**
265      * Sends a command intent to the LockTaskUtilityActivity and waits
266      * to receive the broadcast back confirming it has finished processing
267      * the command.
268      */
startAndWait(Intent intent)269     private void startAndWait(Intent intent) {
270         mIntentHandled = false;
271         synchronized (this) {
272             mContext.startActivity(intent);
273             // Give 20 secs to finish.
274             try {
275                 wait(ACTIVITY_RUNNING_TIMEOUT_MILLIS);
276             } catch (InterruptedException e) {
277             }
278             assertTrue(mIntentHandled);
279         }
280     }
281 
282     /**
283      * Get basic intent that points at the LockTaskUtilityActivity.
284      *
285      * This intent includes the flags to make it act as single top.
286      */
getLockTaskUtility()287     private Intent getLockTaskUtility() {
288         Intent intent = new Intent();
289         intent.setClassName(PACKAGE_NAME, LockTaskUtilityActivity.class.getName());
290         intent.addFlags(Intent.FLAG_ACTIVITY_SINGLE_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
291         return intent;
292     }
293 }
294