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 17 package com.android.inputmethod.latin.settings; 18 19 import static org.junit.Assert.assertEquals; 20 import static org.junit.Assert.assertNull; 21 import static org.junit.Assert.fail; 22 import static org.mockito.Matchers.any; 23 import static org.mockito.Mockito.when; 24 25 import android.app.AlertDialog; 26 import android.content.Context; 27 import android.content.DialogInterface; 28 import android.content.Intent; 29 import android.view.View; 30 import android.widget.ListView; 31 32 import androidx.test.InstrumentationRegistry; 33 import androidx.test.filters.MediumTest; 34 import androidx.test.runner.AndroidJUnit4; 35 36 import com.android.inputmethod.latin.utils.ManagedProfileUtils; 37 38 import org.junit.After; 39 import org.junit.Before; 40 import org.junit.Test; 41 import org.junit.runner.RunWith; 42 import org.mockito.Mock; 43 import org.mockito.MockitoAnnotations; 44 45 import java.util.concurrent.CountDownLatch; 46 import java.util.concurrent.TimeUnit; 47 48 @MediumTest 49 @RunWith(AndroidJUnit4.class) 50 public class AccountsSettingsFragmentTests { 51 private static final String FRAG_NAME = AccountsSettingsFragment.class.getName(); 52 private static final long TEST_TIMEOUT_MILLIS = 5000; 53 54 @Mock private ManagedProfileUtils mManagedProfileUtils; 55 56 private TestFragmentActivity mActivity; getActivity()57 private TestFragmentActivity getActivity() { 58 return mActivity; 59 } 60 61 @Before setUp()62 public void setUp() throws Exception { 63 // Initialize the mocks. 64 MockitoAnnotations.initMocks(this); 65 ManagedProfileUtils.setTestInstance(mManagedProfileUtils); 66 67 final Intent intent = new Intent() 68 .setAction(Intent.ACTION_MAIN) 69 .setClass(InstrumentationRegistry.getTargetContext(), TestFragmentActivity.class) 70 .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK) 71 .addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION) 72 .putExtra(TestFragmentActivity.EXTRA_SHOW_FRAGMENT, FRAG_NAME); 73 mActivity = (TestFragmentActivity) InstrumentationRegistry.getInstrumentation() 74 .startActivitySync(intent); 75 } 76 77 @After tearDown()78 public void tearDown() throws Exception { 79 ManagedProfileUtils.setTestInstance(null); 80 mActivity = null; 81 } 82 83 @Test testEmptyAccounts()84 public void testEmptyAccounts() { 85 final AccountsSettingsFragment fragment = 86 (AccountsSettingsFragment) getActivity().mFragment; 87 try { 88 fragment.createAccountPicker(new String[0], null, null /* listener */); 89 fail("Expected IllegalArgumentException, never thrown"); 90 } catch (IllegalArgumentException expected) { 91 // Expected. 92 } 93 } 94 95 private static class DialogHolder { 96 AlertDialog mDialog; DialogHolder()97 DialogHolder() {} 98 } 99 100 @Test testMultipleAccounts_noSettingsForManagedProfile()101 public void testMultipleAccounts_noSettingsForManagedProfile() { 102 when(mManagedProfileUtils.hasWorkProfile(any(Context.class))).thenReturn(true); 103 104 final AccountsSettingsFragment fragment = 105 (AccountsSettingsFragment) getActivity().mFragment; 106 final AlertDialog dialog = initDialog(fragment, null).mDialog; 107 final ListView lv = dialog.getListView(); 108 109 // Nothing to check/uncheck. 110 assertNull(fragment.findPreference(AccountsSettingsFragment.PREF_ACCCOUNT_SWITCHER)); 111 } 112 113 @Test testMultipleAccounts_noCurrentAccount()114 public void testMultipleAccounts_noCurrentAccount() { 115 when(mManagedProfileUtils.hasWorkProfile(any(Context.class))).thenReturn(false); 116 117 final AccountsSettingsFragment fragment = 118 (AccountsSettingsFragment) getActivity().mFragment; 119 final AlertDialog dialog = initDialog(fragment, null).mDialog; 120 final ListView lv = dialog.getListView(); 121 122 // The 1st account should be checked by default. 123 assertEquals("checked-item", 0, lv.getCheckedItemPosition()); 124 // There should be 4 accounts in the list. 125 assertEquals("count", 4, lv.getCount()); 126 // The sign-out button shouldn't exist 127 assertEquals(View.GONE, 128 dialog.getButton(DialogInterface.BUTTON_NEUTRAL).getVisibility()); 129 assertEquals(View.VISIBLE, 130 dialog.getButton(DialogInterface.BUTTON_NEGATIVE).getVisibility()); 131 assertEquals(View.VISIBLE, 132 dialog.getButton(DialogInterface.BUTTON_POSITIVE).getVisibility()); 133 } 134 135 @Test testMultipleAccounts_currentAccount()136 public void testMultipleAccounts_currentAccount() { 137 when(mManagedProfileUtils.hasWorkProfile(any(Context.class))).thenReturn(false); 138 139 final AccountsSettingsFragment fragment = 140 (AccountsSettingsFragment) getActivity().mFragment; 141 final AlertDialog dialog = initDialog(fragment, "3@example.com").mDialog; 142 final ListView lv = dialog.getListView(); 143 144 // The 3rd account should be checked by default. 145 assertEquals("checked-item", 2, lv.getCheckedItemPosition()); 146 // There should be 4 accounts in the list. 147 assertEquals("count", 4, lv.getCount()); 148 // The sign-out button should be shown 149 assertEquals(View.VISIBLE, 150 dialog.getButton(DialogInterface.BUTTON_NEUTRAL).getVisibility()); 151 assertEquals(View.VISIBLE, 152 dialog.getButton(DialogInterface.BUTTON_NEGATIVE).getVisibility()); 153 assertEquals(View.VISIBLE, 154 dialog.getButton(DialogInterface.BUTTON_POSITIVE).getVisibility()); 155 } 156 initDialog( final AccountsSettingsFragment fragment, final String selectedAccount)157 private DialogHolder initDialog( 158 final AccountsSettingsFragment fragment, 159 final String selectedAccount) { 160 final DialogHolder dialogHolder = new DialogHolder(); 161 final CountDownLatch latch = new CountDownLatch(1); 162 163 getActivity().runOnUiThread(new Runnable() { 164 @Override 165 public void run() { 166 final AlertDialog dialog = fragment.createAccountPicker( 167 new String[] { 168 "1@example.com", 169 "2@example.com", 170 "3@example.com", 171 "4@example.com"}, 172 selectedAccount, null /* positiveButtonListner */); 173 dialog.show(); 174 dialogHolder.mDialog = dialog; 175 latch.countDown(); 176 } 177 }); 178 179 try { 180 latch.await(TEST_TIMEOUT_MILLIS, TimeUnit.MILLISECONDS); 181 } catch (InterruptedException ex) { 182 fail(); 183 } 184 InstrumentationRegistry.getInstrumentation().waitForIdleSync(); 185 return dialogHolder; 186 } 187 } 188