Home | History | Annotate | Download | only in documentsui
      1 /*
      2  * Copyright (C) 2017 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 
     17 package com.android.documentsui;
     18 
     19 import static com.android.documentsui.StubProvider.ROOT_0_ID;
     20 import static com.android.documentsui.StubProvider.ROOT_1_ID;
     21 
     22 import android.content.Context;
     23 import android.content.ContentResolver;
     24 import android.content.Intent;
     25 import android.content.IntentFilter;
     26 import android.content.BroadcastReceiver;
     27 import android.net.Uri;
     28 import android.os.Bundle;
     29 import android.os.RemoteException;
     30 import android.provider.Settings;
     31 import android.support.test.filters.LargeTest;
     32 import android.support.test.filters.Suppress;
     33 import android.support.test.uiautomator.Configurator;
     34 import android.text.TextUtils;
     35 import android.view.KeyEvent;
     36 import android.view.MotionEvent;
     37 
     38 import com.android.documentsui.base.DocumentInfo;
     39 import com.android.documentsui.files.FilesActivity;
     40 import com.android.documentsui.services.TestNotificationService;
     41 
     42 import java.util.concurrent.ArrayBlockingQueue;
     43 import java.util.concurrent.CountDownLatch;
     44 import java.util.concurrent.RejectedExecutionException;
     45 import java.util.concurrent.ThreadPoolExecutor;
     46 import java.util.concurrent.TimeUnit;
     47 import java.util.List;
     48 import java.util.ArrayList;
     49 
     50 /**
     51 * This class test the below points
     52 * - Copy large number of files
     53 */
     54 @LargeTest
     55 public class FileCopyUiTest extends ActivityTest<FilesActivity> {
     56     private static final String PACKAGE_NAME = "com.android.documentsui.tests";
     57 
     58     private static final String ACCESS_APP_NAME = "DocumentsUI Tests";
     59 
     60     private static final String ALLOW = "ALLOW";
     61 
     62     private static final String TURN_OFF = "TURN OFF";
     63 
     64     private static final String COPY = "Copy to";
     65 
     66     private static final String MOVE = "Move to";
     67 
     68     private static final String SELECT_ALL = "Select all";
     69 
     70     private static final int DUMMY_FILE_COUNT = 1000;
     71 
     72     private final List<String> mCopyFileList = new ArrayList<String>();
     73 
     74     private final BroadcastReceiver mReceiver = new BroadcastReceiver() {
     75         @Override
     76         public void onReceive(Context context, Intent intent) {
     77             String action = intent.getAction();
     78             if (TestNotificationService.ACTION_OPERATION_RESULT.equals(action)) {
     79                 mOperationExecuted = intent.getBooleanExtra(
     80                         TestNotificationService.EXTRA_RESULT, false);
     81                 if (!mOperationExecuted) {
     82                     mErrorReason = intent.getStringExtra(
     83                             TestNotificationService.EXTRA_ERROR_REASON);
     84                 }
     85                 mCountDownLatch.countDown();
     86             }
     87         }
     88     };
     89 
     90     private CountDownLatch mCountDownLatch;
     91 
     92     private boolean mOperationExecuted;
     93 
     94     private String mErrorReason;
     95 
     96     public FileCopyUiTest() {
     97         super(FilesActivity.class);
     98     }
     99 
    100     @Override
    101     public void setUp() throws Exception {
    102         super.setUp();
    103 
    104         // Set a flag to prevent many refreshes.
    105         Bundle bundle = new Bundle();
    106         bundle.putBoolean(StubProvider.EXTRA_ENABLE_ROOT_NOTIFICATION, false);
    107         mDocsHelper.configure(null, bundle);
    108 
    109         initTestFiles();
    110 
    111         IntentFilter filter = new IntentFilter();
    112         filter.addAction(TestNotificationService.ACTION_OPERATION_RESULT);
    113         context.registerReceiver(mReceiver, filter);
    114         context.sendBroadcast(new Intent(
    115                 TestNotificationService.ACTION_CHANGE_EXECUTION_MODE));
    116 
    117         mOperationExecuted = false;
    118         mErrorReason = "No response from Notification";
    119         mCountDownLatch = new CountDownLatch(1);
    120     }
    121 
    122     @Override
    123     public void tearDown() throws Exception {
    124         mCountDownLatch.countDown();
    125         mCountDownLatch = null;
    126 
    127         context.unregisterReceiver(mReceiver);
    128         try {
    129             if (isEnableAccessNotification()) {
    130                 disallowNotificationAccess();
    131             }
    132         } catch (Exception e) {
    133             // ignore
    134         }
    135         super.tearDown();
    136     }
    137 
    138     @Override
    139     public void initTestFiles() throws RemoteException {
    140         try {
    141             if (!isEnableAccessNotification()) {
    142                 allowNotificationAccess();
    143             }
    144             createDummyFiles();
    145         } catch (Exception e) {
    146             fail("Initialization failed");
    147         }
    148     }
    149 
    150     private void createDummyFiles() throws Exception {
    151         final ThreadPoolExecutor exec = new ThreadPoolExecutor(
    152                 5, 5, 1000L, TimeUnit.MILLISECONDS,
    153                         new ArrayBlockingQueue<Runnable>(100, true));
    154         for (int i = 0; i < DUMMY_FILE_COUNT; i++) {
    155             final String fileName = "file" + String.format("%04d", i) + ".log";
    156             if (exec.getQueue().size() >= 80) {
    157                 Thread.sleep(50);
    158             }
    159             exec.submit(new Runnable() {
    160                 @Override
    161                 public void run() {
    162                     Uri uri = mDocsHelper.createDocument(rootDir0, "text/plain", fileName);
    163                     try {
    164                         mDocsHelper.writeDocument(uri, new byte[1]);
    165                     } catch (Exception e) {
    166                         // ignore
    167                     }
    168                 }
    169             });
    170             mCopyFileList.add(fileName);
    171         }
    172         exec.shutdown();
    173     }
    174 
    175     private void allowNotificationAccess() throws Exception {
    176         Intent intent = new Intent();
    177         intent.setAction(Settings.ACTION_NOTIFICATION_LISTENER_SETTINGS);
    178         getActivity().startActivity(intent);
    179         device.waitForIdle();
    180 
    181         bots.main.findMenuLabelWithName(ACCESS_APP_NAME).click();
    182         device.waitForIdle();
    183 
    184         bots.main.findMenuLabelWithName(ALLOW).click();
    185         bots.keyboard.pressKey(KeyEvent.KEYCODE_BACK);
    186     }
    187 
    188     private void disallowNotificationAccess() throws Exception {
    189         Intent intent = new Intent();
    190         intent.setAction(Settings.ACTION_NOTIFICATION_LISTENER_SETTINGS);
    191         getActivity().startActivity(intent);
    192         device.waitForIdle();
    193 
    194         bots.main.findMenuLabelWithName(ACCESS_APP_NAME).click();
    195         device.waitForIdle();
    196 
    197         bots.main.findMenuLabelWithName(TURN_OFF).click();
    198         bots.keyboard.pressKey(KeyEvent.KEYCODE_BACK);
    199     }
    200 
    201     private boolean isEnableAccessNotification() {
    202         ContentResolver resolver = getActivity().getContentResolver();
    203         String listeners = Settings.Secure.getString(
    204                 resolver,"enabled_notification_listeners");
    205         if (!TextUtils.isEmpty(listeners)) {
    206             String[] list = listeners.split(":");
    207             for(String item : list) {
    208                 if(item.startsWith(PACKAGE_NAME)) {
    209                     return true;
    210                 }
    211             }
    212         }
    213         return false;
    214     }
    215 
    216     public void testCopyAllDocument() throws Exception {
    217         bots.roots.openRoot(ROOT_0_ID);
    218         bots.main.clickToolbarOverflowItem(SELECT_ALL);
    219         device.waitForIdle();
    220 
    221         bots.main.clickToolbarOverflowItem(COPY);
    222         device.waitForIdle();
    223 
    224         bots.roots.openRoot(ROOT_1_ID);
    225         bots.main.clickDialogOkButton();
    226         device.waitForIdle();
    227 
    228         try {
    229             mCountDownLatch.await(60, TimeUnit.SECONDS);
    230         } catch (Exception e) {
    231             fail("Cannot wait because of error." + e.toString());
    232         }
    233 
    234         assertTrue(mErrorReason, mOperationExecuted);
    235 
    236         bots.roots.openRoot(ROOT_1_ID);
    237         device.waitForIdle();
    238 
    239         List<DocumentInfo> root1 = mDocsHelper.listChildren(rootDir1.documentId, 1000);
    240         List<String> copiedFileList = new ArrayList<String>();
    241         for (DocumentInfo info : root1) {
    242             copiedFileList.add(info.displayName);
    243         }
    244 
    245         for (String name : mCopyFileList) {
    246             assertTrue("Not found " + name, copiedFileList.contains(name));
    247         }
    248     }
    249 }
    250