From f779e6c9d3190edaa80fec72fc1e106831df9d71 Mon Sep 17 00:00:00 2001 From: Weng Su Date: Fri, 13 Jan 2023 07:52:23 +0800 Subject: [PATCH] Add toggle for Wi-Fi hotspot - Add Wi-Fi hotspot toggle with vertical divider - Disable preference and toggle when Data Saver is enabled Bug: 245569117 Test: manual test make RunSettingsRoboTests ROBOTEST_FILTER=TetherSettingsTest make RunSettingsRoboTests ROBOTEST_FILTER=WifiTetherPreferenceControllerTest atest -c TetheringManagerModelTest Change-Id: Ic2baf7d3d0a7bf9527da38d24ecc511b7c91265a --- res/xml/tether_prefs.xml | 4 +- .../network/tether/TetherSettings.java | 24 ++-- .../network/tether/TetheringManagerModel.java | 34 +++++ .../WifiTetherPreferenceController.java | 82 ++++++++++-- .../network/tether/TetherSettingsTest.java | 117 +++++++++++------- .../tether/TetheringManagerModelTest.java | 16 +++ .../WifiTetherPreferenceControllerTest.java | 70 ++++++++++- 7 files changed, 276 insertions(+), 71 deletions(-) diff --git a/res/xml/tether_prefs.xml b/res/xml/tether_prefs.xml index 97ad5fd4b7d..a6e0a39fc80 100644 --- a/res/xml/tether_prefs.xml +++ b/res/xml/tether_prefs.xml @@ -23,10 +23,10 @@ android:key="tether_prefs_top_intro" settings:searchable="false"/> - diff --git a/src/com/android/settings/network/tether/TetherSettings.java b/src/com/android/settings/network/tether/TetherSettings.java index 6ec15a72de4..68834fb5697 100644 --- a/src/com/android/settings/network/tether/TetherSettings.java +++ b/src/com/android/settings/network/tether/TetherSettings.java @@ -96,11 +96,12 @@ public class TetherSettings extends RestrictedSettingsFragment private static final String TAG = "TetheringSettings"; private static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG); - private RestrictedSwitchPreference mUsbTether; - - private SwitchPreference mBluetoothTether; - - private SwitchPreference mEthernetTether; + @VisibleForTesting + RestrictedSwitchPreference mUsbTether; + @VisibleForTesting + SwitchPreference mBluetoothTether; + @VisibleForTesting + SwitchPreference mEthernetTether; private BroadcastReceiver mTetherChangeReceiver; private BroadcastReceiver mBluetoothStateReceiver; @@ -115,7 +116,8 @@ public class TetherSettings extends RestrictedSettingsFragment private EthernetListener mEthernetListener; private final HashSet mAvailableInterfaces = new HashSet<>(); - private WifiTetherPreferenceController mWifiTetherPreferenceController; + @VisibleForTesting + WifiTetherPreferenceController mWifiTetherPreferenceController; private boolean mUsbConnected; private boolean mMassStorageActive; @@ -125,7 +127,8 @@ public class TetherSettings extends RestrictedSettingsFragment private DataSaverBackend mDataSaverBackend; private boolean mDataSaverEnabled; - private Preference mDataSaverFooter; + @VisibleForTesting + Preference mDataSaverFooter; @VisibleForTesting String[] mUsbRegexs; @@ -146,10 +149,10 @@ public class TetherSettings extends RestrictedSettingsFragment @Override public void onAttach(Context context) { super.onAttach(context); - mWifiTetherPreferenceController = - new WifiTetherPreferenceController(context, getSettingsLifecycle()); TetheringManagerModel model = new ViewModelProvider(this).get(TetheringManagerModel.class); - mTm = model.mTetheringManager; + mWifiTetherPreferenceController = + new WifiTetherPreferenceController(context, getSettingsLifecycle(), model); + mTm = model.getTetheringManager(); model.getTetheredInterfaces().observe(this, this::onTetheredInterfacesChanged); } @@ -248,6 +251,7 @@ public class TetherSettings extends RestrictedSettingsFragment @Override public void onDataSaverChanged(boolean isDataSaving) { mDataSaverEnabled = isDataSaving; + mWifiTetherPreferenceController.setDataSaverEnabled(mDataSaverEnabled); mUsbTether.setEnabled(!mDataSaverEnabled); mBluetoothTether.setEnabled(!mDataSaverEnabled); mEthernetTether.setEnabled(!mDataSaverEnabled); diff --git a/src/com/android/settings/network/tether/TetheringManagerModel.java b/src/com/android/settings/network/tether/TetheringManagerModel.java index 7506c975c32..5c0f9398b95 100644 --- a/src/com/android/settings/network/tether/TetheringManagerModel.java +++ b/src/com/android/settings/network/tether/TetheringManagerModel.java @@ -34,6 +34,7 @@ public class TetheringManagerModel extends AndroidViewModel { protected TetheringManager mTetheringManager; protected EventCallback mEventCallback = new EventCallback(); protected MutableLiveData> mTetheredInterfaces = new MutableLiveData<>(); + protected StartTetheringCallback mStartTetheringCallback = new StartTetheringCallback(); public TetheringManagerModel(@NonNull Application application) { super(application); @@ -62,6 +63,27 @@ public class TetheringManagerModel extends AndroidViewModel { return Transformations.distinctUntilChanged(mTetheredInterfaces); } + /** + * Starts tethering and runs tether provisioning for the given type if needed. If provisioning + * fails, stopTethering will be called automatically. + * + * @param type The tethering type, on of the {@code TetheringManager#TETHERING_*} constants. + */ + public void startTethering(int type) { + mTetheringManager.startTethering(type, getApplication().getMainExecutor(), + mStartTetheringCallback); + } + + /** + * Stops tethering for the given type. Also cancels any provisioning rechecks for that type if + * applicable. + * + * @param type The tethering type, on of the {@code TetheringManager#TETHERING_*} constants. + */ + public void stopTethering(int type) { + mTetheringManager.stopTethering(type); + } + /** * Callback for use with {@link TetheringManager#registerTetheringEventCallback} to find out * tethering upstream status. @@ -72,4 +94,16 @@ public class TetheringManagerModel extends AndroidViewModel { mTetheredInterfaces.setValue(interfaces); } } + + private class StartTetheringCallback implements TetheringManager.StartTetheringCallback { + @Override + public void onTetheringStarted() { + // Do nothing + } + + @Override + public void onTetheringFailed(int error) { + // Do nothing + } + } } diff --git a/src/com/android/settings/wifi/tether/WifiTetherPreferenceController.java b/src/com/android/settings/wifi/tether/WifiTetherPreferenceController.java index 49b437edeee..908ccdcc845 100644 --- a/src/com/android/settings/wifi/tether/WifiTetherPreferenceController.java +++ b/src/com/android/settings/wifi/tether/WifiTetherPreferenceController.java @@ -16,6 +16,9 @@ package com.android.settings.wifi.tether; +import static android.net.TetheringManager.TETHERING_WIFI; +import static android.net.wifi.WifiManager.SAP_START_FAILURE_GENERAL; + import static com.android.settings.wifi.WifiUtils.canShowWifiHotspot; import android.annotation.NonNull; @@ -26,12 +29,15 @@ import android.net.wifi.WifiManager; import android.text.BidiFormatter; import androidx.annotation.VisibleForTesting; -import androidx.preference.Preference; import androidx.preference.PreferenceScreen; import com.android.settings.R; import com.android.settings.Utils; import com.android.settings.core.PreferenceControllerMixin; +import com.android.settings.network.tether.TetheringManagerModel; +import com.android.settings.widget.GenericSwitchController; +import com.android.settings.widget.SwitchWidgetController; +import com.android.settingslib.PrimarySwitchPreference; import com.android.settingslib.core.AbstractPreferenceController; import com.android.settingslib.core.lifecycle.Lifecycle; import com.android.settingslib.core.lifecycle.LifecycleObserver; @@ -43,7 +49,8 @@ import com.android.settingslib.wifi.WifiUtils; import java.util.List; public class WifiTetherPreferenceController extends AbstractPreferenceController - implements PreferenceControllerMixin, LifecycleObserver, OnStart, OnStop { + implements PreferenceControllerMixin, LifecycleObserver, OnStart, OnStop, + SwitchWidgetController.OnSwitchChangeListener { private static final String WIFI_TETHER_SETTINGS = "wifi_tether"; @@ -51,16 +58,24 @@ public class WifiTetherPreferenceController extends AbstractPreferenceController private boolean mIsWifiTetheringAllow; private int mSoftApState; @VisibleForTesting - Preference mPreference; + PrimarySwitchPreference mPreference; @VisibleForTesting WifiTetherSoftApManager mWifiTetherSoftApManager; + @VisibleForTesting + TetheringManagerModel mTetheringManagerModel; + @VisibleForTesting + boolean mIsDataSaverEnabled; + @VisibleForTesting + SwitchWidgetController mSwitch; - public WifiTetherPreferenceController(Context context, Lifecycle lifecycle) { + public WifiTetherPreferenceController(Context context, Lifecycle lifecycle, + TetheringManagerModel tetheringManagerModel) { // TODO(b/246537032):Use fragment context to WifiManager service will caused memory leak this(context, lifecycle, context.getApplicationContext().getSystemService(WifiManager.class), true /* initSoftApManager */, - WifiEnterpriseRestrictionUtils.isWifiTetheringAllowed(context)); + WifiEnterpriseRestrictionUtils.isWifiTetheringAllowed(context), + tetheringManagerModel); } @VisibleForTesting @@ -69,11 +84,13 @@ public class WifiTetherPreferenceController extends AbstractPreferenceController Lifecycle lifecycle, WifiManager wifiManager, boolean initSoftApManager, - boolean isWifiTetheringAllow) { + boolean isWifiTetheringAllow, + TetheringManagerModel tetheringManagerModel) { super(context); mIsWifiTetheringAllow = isWifiTetheringAllow; if (!isWifiTetheringAllow) return; + mTetheringManagerModel = tetheringManagerModel; mWifiManager = wifiManager; if (lifecycle != null) { @@ -97,8 +114,13 @@ public class WifiTetherPreferenceController extends AbstractPreferenceController // unavailable return; } - if (!mIsWifiTetheringAllow && mPreference.isEnabled()) { - mPreference.setEnabled(false); + if (mSwitch == null) { + mSwitch = new GenericSwitchController(mPreference); + mSwitch.setListener(this); + updateSwitch(); + } + mPreference.setEnabled(canEnabled()); + if (!mIsWifiTetheringAllow) { mPreference.setSummary(R.string.not_allowed_by_ent); } } @@ -114,6 +136,9 @@ public class WifiTetherPreferenceController extends AbstractPreferenceController if (mWifiTetherSoftApManager != null) { mWifiTetherSoftApManager.registerSoftApCallback(); } + if (mSwitch != null) { + mSwitch.startListening(); + } } } @@ -123,6 +148,9 @@ public class WifiTetherPreferenceController extends AbstractPreferenceController if (mWifiTetherSoftApManager != null) { mWifiTetherSoftApManager.unRegisterSoftApCallback(); } + if (mSwitch != null) { + mSwitch.stopListening(); + } } } @@ -158,6 +186,7 @@ public class WifiTetherPreferenceController extends AbstractPreferenceController mPreference.setSummary(R.string.wifi_tether_starting); break; case WifiManager.WIFI_AP_STATE_ENABLED: + mSwitch.setChecked(true); final SoftApConfiguration softApConfig = mWifiManager.getSoftApConfiguration(); updateConfigSummary(softApConfig); break; @@ -165,6 +194,7 @@ public class WifiTetherPreferenceController extends AbstractPreferenceController mPreference.setSummary(R.string.wifi_tether_stopping); break; case WifiManager.WIFI_AP_STATE_DISABLED: + mSwitch.setChecked(false); mPreference.setSummary(R.string.wifi_hotspot_off_subtext); break; default: @@ -184,4 +214,40 @@ public class WifiTetherPreferenceController extends AbstractPreferenceController mPreference.setSummary(mContext.getString(R.string.wifi_tether_enabled_subtext, BidiFormatter.getInstance().unicodeWrap(softApConfig.getSsid()))); } + + /** + * Sets the Data Saver state for preference update. + */ + public void setDataSaverEnabled(boolean enabled) { + mIsDataSaverEnabled = enabled; + if (mPreference != null) { + mPreference.setEnabled(canEnabled()); + } + if (mSwitch != null) { + mSwitch.setEnabled(canEnabled()); + } + } + + private boolean canEnabled() { + return mIsWifiTetheringAllow && !mIsDataSaverEnabled; + } + + @VisibleForTesting + protected void updateSwitch() { + if (mWifiManager == null) return; + int wifiApState = mWifiManager.getWifiApState(); + mSwitch.setEnabled(canEnabled()); + mSwitch.setChecked(wifiApState == WifiManager.WIFI_AP_STATE_ENABLED); + handleWifiApStateChanged(wifiApState, SAP_START_FAILURE_GENERAL); + } + + @Override + public boolean onSwitchToggled(boolean isChecked) { + if (isChecked) { + mTetheringManagerModel.startTethering(TETHERING_WIFI); + } else { + mTetheringManagerModel.stopTethering(TETHERING_WIFI); + } + return true; + } } diff --git a/tests/robotests/src/com/android/settings/network/tether/TetherSettingsTest.java b/tests/robotests/src/com/android/settings/network/tether/TetherSettingsTest.java index 2aeb44f27f7..23d9b825ad6 100644 --- a/tests/robotests/src/com/android/settings/network/tether/TetherSettingsTest.java +++ b/tests/robotests/src/com/android/settings/network/tether/TetherSettingsTest.java @@ -55,6 +55,7 @@ import androidx.preference.SwitchPreference; import com.android.settings.R; import com.android.settings.core.FeatureFlags; +import com.android.settings.wifi.tether.WifiTetherPreferenceController; import com.android.settingslib.RestrictedSwitchPreference; import org.junit.Before; @@ -80,6 +81,18 @@ public class TetherSettingsTest { private UserManager mUserManager; @Mock private TetheringManager mTetheringManager; + @Mock + private WifiTetherPreferenceController mWifiTetherPreferenceController; + @Mock + private RestrictedSwitchPreference mUsbTether; + @Mock + private SwitchPreference mBluetoothTether; + @Mock + private SwitchPreference mEthernetTether; + @Mock + private Preference mDataSaverFooter; + + TetherSettings mTetherSettings; @Before public void setUp() throws Exception { @@ -100,6 +113,14 @@ public class TetherSettingsTest { when(mTetheringManager.getTetherableUsbRegexs()).thenReturn(new String[0]); when(mTetheringManager.getTetherableBluetoothRegexs()).thenReturn(new String[0]); + + mTetherSettings = spy(new TetherSettings()); + mTetherSettings.mContext = mContext; + mTetherSettings.mWifiTetherPreferenceController = mWifiTetherPreferenceController; + mTetherSettings.mUsbTether = mUsbTether; + mTetherSettings.mBluetoothTether = mBluetoothTether; + mTetherSettings.mEthernetTether = mEthernetTether; + mTetherSettings.mDataSaverFooter = mDataSaverFooter; } @Test @@ -184,16 +205,14 @@ public class TetherSettingsTest { @Test public void testSetFooterPreferenceTitle_isStaApConcurrencySupported_showStaApString() { - final TetherSettings spyTetherSettings = spy(new TetherSettings()); - spyTetherSettings.mContext = mContext; final Preference mockPreference = mock(Preference.class); - when(spyTetherSettings.findPreference(TetherSettings.KEY_TETHER_PREFS_TOP_INTRO)) + when(mTetherSettings.findPreference(TetherSettings.KEY_TETHER_PREFS_TOP_INTRO)) .thenReturn(mockPreference); final WifiManager mockWifiManager = mock(WifiManager.class); when(mContext.getSystemService(Context.WIFI_SERVICE)).thenReturn(mockWifiManager); when(mockWifiManager.isStaApConcurrencySupported()).thenReturn(true); - spyTetherSettings.setTopIntroPreferenceTitle(); + mTetherSettings.setTopIntroPreferenceTitle(); verify(mockPreference, never()).setTitle(R.string.tethering_footer_info); verify(mockPreference).setTitle(R.string.tethering_footer_info_sta_ap_concurrency); @@ -201,25 +220,23 @@ public class TetherSettingsTest { @Test public void testBluetoothState_updateBluetoothState_bluetoothTetheringStateOn() { - final TetherSettings spyTetherSettings = spy(new TetherSettings()); - spyTetherSettings.mContext = mContext; - spyTetherSettings.mTm = mTetheringManager; + mTetherSettings.mTm = mTetheringManager; final SwitchPreference mockSwitchPreference = mock(SwitchPreference.class); - when(spyTetherSettings.findPreference(TetherSettings.KEY_ENABLE_BLUETOOTH_TETHERING)) + when(mTetherSettings.findPreference(TetherSettings.KEY_ENABLE_BLUETOOTH_TETHERING)) .thenReturn(mockSwitchPreference); final FragmentActivity mockActivity = mock(FragmentActivity.class); - when(spyTetherSettings.getActivity()).thenReturn(mockActivity); + when(mTetherSettings.getActivity()).thenReturn(mockActivity); final ArgumentCaptor captor = ArgumentCaptor.forClass(BroadcastReceiver.class); when(mockActivity.registerReceiver(captor.capture(), any(IntentFilter.class))) .thenReturn(null); // Bluetooth tethering state is on - when(spyTetherSettings.getBluetoothState()).thenReturn(BluetoothAdapter.STATE_ON); - when(spyTetherSettings.isBluetoothTetheringOn()).thenReturn(true); + when(mTetherSettings.getBluetoothState()).thenReturn(BluetoothAdapter.STATE_ON); + when(mTetherSettings.isBluetoothTetheringOn()).thenReturn(true); - spyTetherSettings.setupTetherPreference(); - spyTetherSettings.registerReceiver(); - updateOnlyBluetoothState(spyTetherSettings); + mTetherSettings.setupTetherPreference(); + mTetherSettings.registerReceiver(); + updateOnlyBluetoothState(mTetherSettings); // Simulate Bluetooth tethering state changed final BroadcastReceiver receiver = captor.getValue(); @@ -234,25 +251,23 @@ public class TetherSettingsTest { @Test public void testBluetoothState_updateBluetoothState_bluetoothTetheringStateOff() { - final TetherSettings spyTetherSettings = spy(new TetherSettings()); - spyTetherSettings.mContext = mContext; - spyTetherSettings.mTm = mTetheringManager; + mTetherSettings.mTm = mTetheringManager; final SwitchPreference mockSwitchPreference = mock(SwitchPreference.class); - when(spyTetherSettings.findPreference(TetherSettings.KEY_ENABLE_BLUETOOTH_TETHERING)) + when(mTetherSettings.findPreference(TetherSettings.KEY_ENABLE_BLUETOOTH_TETHERING)) .thenReturn(mockSwitchPreference); final FragmentActivity mockActivity = mock(FragmentActivity.class); - when(spyTetherSettings.getActivity()).thenReturn(mockActivity); + when(mTetherSettings.getActivity()).thenReturn(mockActivity); final ArgumentCaptor captor = ArgumentCaptor.forClass(BroadcastReceiver.class); when(mockActivity.registerReceiver(captor.capture(), any(IntentFilter.class))) .thenReturn(null); // Bluetooth tethering state is off - when(spyTetherSettings.getBluetoothState()).thenReturn(BluetoothAdapter.STATE_ON); - when(spyTetherSettings.isBluetoothTetheringOn()).thenReturn(false); + when(mTetherSettings.getBluetoothState()).thenReturn(BluetoothAdapter.STATE_ON); + when(mTetherSettings.isBluetoothTetheringOn()).thenReturn(false); - spyTetherSettings.setupTetherPreference(); - spyTetherSettings.registerReceiver(); - updateOnlyBluetoothState(spyTetherSettings); + mTetherSettings.setupTetherPreference(); + mTetherSettings.registerReceiver(); + updateOnlyBluetoothState(mTetherSettings); // Simulate Bluetooth tethering state changed final BroadcastReceiver receiver = captor.getValue(); @@ -268,16 +283,14 @@ public class TetherSettingsTest { @Test public void updateState_usbTetheringIsEnabled_checksUsbTethering() { String [] tethered = {"rndis0"}; - TetherSettings spyTetherSettings = spy(new TetherSettings()); RestrictedSwitchPreference tetheringPreference = mock(RestrictedSwitchPreference.class); - when(spyTetherSettings.findPreference(TetherSettings.KEY_USB_TETHER_SETTINGS)) + when(mTetherSettings.findPreference(TetherSettings.KEY_USB_TETHER_SETTINGS)) .thenReturn(tetheringPreference); - spyTetherSettings.mContext = mContext; - spyTetherSettings.mTm = mTetheringManager; - spyTetherSettings.setupTetherPreference(); - spyTetherSettings.mUsbRegexs = tethered; + mTetherSettings.mTm = mTetheringManager; + mTetherSettings.setupTetherPreference(); + mTetherSettings.mUsbRegexs = tethered; - spyTetherSettings.updateUsbState(tethered); + mTetherSettings.updateUsbState(tethered); verify(tetheringPreference).setEnabled(true); verify(tetheringPreference).setChecked(true); @@ -286,16 +299,14 @@ public class TetherSettingsTest { @Test public void updateState_usbTetheringIsDisabled_unchecksUsbTethering() { String [] tethered = {"rndis0"}; - TetherSettings spyTetherSettings = spy(new TetherSettings()); RestrictedSwitchPreference tetheringPreference = mock(RestrictedSwitchPreference.class); - when(spyTetherSettings.findPreference(TetherSettings.KEY_USB_TETHER_SETTINGS)) + when(mTetherSettings.findPreference(TetherSettings.KEY_USB_TETHER_SETTINGS)) .thenReturn(tetheringPreference); - spyTetherSettings.mContext = mContext; - spyTetherSettings.mTm = mTetheringManager; - spyTetherSettings.setupTetherPreference(); - spyTetherSettings.mUsbRegexs = tethered; + mTetherSettings.mTm = mTetheringManager; + mTetherSettings.setupTetherPreference(); + mTetherSettings.mUsbRegexs = tethered; - spyTetherSettings.updateUsbState(new String[0]); + mTetherSettings.updateUsbState(new String[0]); verify(tetheringPreference).setEnabled(false); verify(tetheringPreference).setChecked(false); @@ -362,6 +373,20 @@ public class TetherSettingsTest { verify(tetheringPreference, times(2)).setEnabled(true); } + @Test + public void onDataSaverChanged_dataSaverEnabled_setToController() { + mTetherSettings.onDataSaverChanged(true); + + verify(mWifiTetherPreferenceController).setDataSaverEnabled(true); + } + + @Test + public void onDataSaverChanged_dataSaverDisabled_setToController() { + mTetherSettings.onDataSaverChanged(false); + + verify(mWifiTetherPreferenceController).setDataSaverEnabled(false); + } + private void updateOnlyBluetoothState(TetherSettings tetherSettings) { doReturn(mTetheringManager).when(mContext) .getSystemService(Context.TETHERING_SERVICE); @@ -391,21 +416,19 @@ public class TetherSettingsTest { private void setupUsbStateComponents(RestrictedSwitchPreference preference, ArgumentCaptor captor, FragmentActivity activity) { - TetherSettings spyTetherSettings = spy(new TetherSettings()); SwitchPreference mockSwitchPreference = mock(SwitchPreference.class); - when(spyTetherSettings.findPreference(TetherSettings.KEY_USB_TETHER_SETTINGS)) + when(mTetherSettings.findPreference(TetherSettings.KEY_USB_TETHER_SETTINGS)) .thenReturn(preference); - when(spyTetherSettings.findPreference(TetherSettings.KEY_ENABLE_BLUETOOTH_TETHERING)) + when(mTetherSettings.findPreference(TetherSettings.KEY_ENABLE_BLUETOOTH_TETHERING)) .thenReturn(mockSwitchPreference); - spyTetherSettings.mContext = mContext; - spyTetherSettings.mTm = mTetheringManager; - when(spyTetherSettings.getActivity()).thenReturn(activity); + mTetherSettings.mTm = mTetheringManager; + when(mTetherSettings.getActivity()).thenReturn(activity); when(activity.registerReceiver(captor.capture(), any(IntentFilter.class))) .thenReturn(null); - spyTetherSettings.setupTetherPreference(); - spyTetherSettings.registerReceiver(); - updateOnlyBluetoothState(spyTetherSettings); + mTetherSettings.setupTetherPreference(); + mTetherSettings.registerReceiver(); + updateOnlyBluetoothState(mTetherSettings); } } diff --git a/tests/robotests/src/com/android/settings/network/tether/TetheringManagerModelTest.java b/tests/robotests/src/com/android/settings/network/tether/TetheringManagerModelTest.java index 0e8f00afe05..39589fa132b 100644 --- a/tests/robotests/src/com/android/settings/network/tether/TetheringManagerModelTest.java +++ b/tests/robotests/src/com/android/settings/network/tether/TetheringManagerModelTest.java @@ -16,6 +16,8 @@ package com.android.settings.network.tether; +import static android.net.TetheringManager.TETHERING_WIFI; + import static com.google.common.truth.Truth.assertThat; import static org.mockito.ArgumentMatchers.any; @@ -92,4 +94,18 @@ public class TetheringManagerModelTest { assertThat(mModel.mTetheredInterfaces.getValue()).isEqualTo(mInterfaces); } + + @Test + public void startTethering_startTetheringToTetheringManager() { + mModel.startTethering(TETHERING_WIFI); + + verify(mTetheringManager).startTethering(eq(TETHERING_WIFI), any(), any()); + } + + @Test + public void stopTethering_stopTetheringToTetheringManager() { + mModel.stopTethering(TETHERING_WIFI); + + verify(mTetheringManager).stopTethering(eq(TETHERING_WIFI)); + } } diff --git a/tests/robotests/src/com/android/settings/wifi/tether/WifiTetherPreferenceControllerTest.java b/tests/robotests/src/com/android/settings/wifi/tether/WifiTetherPreferenceControllerTest.java index bc6053b428d..6274a8dff07 100644 --- a/tests/robotests/src/com/android/settings/wifi/tether/WifiTetherPreferenceControllerTest.java +++ b/tests/robotests/src/com/android/settings/wifi/tether/WifiTetherPreferenceControllerTest.java @@ -16,11 +16,15 @@ package com.android.settings.wifi.tether; +import static android.net.TetheringManager.TETHERING_WIFI; +import static android.net.wifi.WifiManager.WIFI_AP_STATE_ENABLED; + import static com.android.settings.wifi.WifiUtils.setCanShowWifiHotspotCached; import static com.google.common.truth.Truth.assertThat; import static org.mockito.ArgumentMatchers.anyString; +import static org.mockito.Mockito.verify; import static org.mockito.Mockito.when; import android.content.Context; @@ -30,7 +34,9 @@ import android.net.wifi.WifiManager; import androidx.preference.PreferenceScreen; import androidx.test.core.app.ApplicationProvider; +import com.android.settings.network.tether.TetheringManagerModel; import com.android.settings.testutils.FakeFeatureFactory; +import com.android.settings.widget.SwitchWidgetController; import com.android.settingslib.PrimarySwitchPreference; import com.android.settingslib.core.lifecycle.Lifecycle; @@ -66,6 +72,10 @@ public class WifiTetherPreferenceControllerTest { private WifiManager mWifiManager; @Mock private PreferenceScreen mScreen; + @Mock + TetheringManagerModel mTetheringManagerModel; + @Mock + private SwitchWidgetController mSwitch; private SoftApConfiguration mSoftApConfiguration; private WifiTetherPreferenceController mController; @@ -80,10 +90,13 @@ public class WifiTetherPreferenceControllerTest { when(mScreen.findPreference(anyString())).thenReturn(mPreference); mSoftApConfiguration = new SoftApConfiguration.Builder().setSsid(SSID).build(); when(mWifiManager.getSoftApConfiguration()).thenReturn(mSoftApConfiguration); + when(mWifiManager.getWifiApState()).thenReturn(WIFI_AP_STATE_ENABLED); mController = new WifiTetherPreferenceController(mContext, mLifecycle, mWifiManager, - false /* initSoftApManager */, true /* isWifiTetheringAllow */); + false /* initSoftApManager */, true /* isWifiTetheringAllow */, + mTetheringManagerModel); mController.displayPreference(mScreen); + mController.mSwitch = mSwitch; } @Test @@ -103,7 +116,8 @@ public class WifiTetherPreferenceControllerTest { @Test public void displayPreference_wifiTetheringNotAllowed_shouldDisable() { mController = new WifiTetherPreferenceController(mContext, mLifecycle, mWifiManager, - false /* initSoftApManager */, false /* isWifiTetheringAllow */); + false /* initSoftApManager */, false /* isWifiTetheringAllow */, + mTetheringManagerModel); mController.displayPreference(mScreen); @@ -114,7 +128,8 @@ public class WifiTetherPreferenceControllerTest { @Test public void displayPreference_wifiTetheringAllowed_shouldEnable() { mController = new WifiTetherPreferenceController(mContext, mLifecycle, mWifiManager, - false /* initSoftApManager */, true /* isWifiTetheringAllow */); + false /* initSoftApManager */, true /* isWifiTetheringAllow */, + mTetheringManagerModel); mController.displayPreference(mScreen); @@ -130,7 +145,7 @@ public class WifiTetherPreferenceControllerTest { @Test public void testHandleWifiApStateChanged_stateEnabled_showEnabledSummary() { - mController.handleWifiApStateChanged(WifiManager.WIFI_AP_STATE_ENABLED, 0 /* reason */); + mController.handleWifiApStateChanged(WIFI_AP_STATE_ENABLED, 0 /* reason */); assertThat(mPreference.getSummary()).isEqualTo("Pixel is active"); } @@ -150,6 +165,53 @@ public class WifiTetherPreferenceControllerTest { "Not sharing internet or content with other devices"); } + @Test + public void handleWifiApStateChanged_stateDisabled_setSwitchUnchecked() { + mController.handleWifiApStateChanged(WifiManager.WIFI_AP_STATE_DISABLED, 0 /* reason */); + + verify(mSwitch).setChecked(false); + } + + @Test + public void handleWifiApStateChanged_stateEnabled_setSwitchChecked() { + mController.handleWifiApStateChanged(WIFI_AP_STATE_ENABLED, 0 /* reason */); + + verify(mSwitch).setChecked(true); + } + + @Test + public void setDataSaverEnabled_setEnabled_setPrefDisabled() { + mController.setDataSaverEnabled(true); + + assertThat(mPreference.isEnabled()).isFalse(); + verify(mSwitch).setEnabled(false); + } + + @Test + public void setDataSaverEnabled_setDisabled_setPrefEnabled() { + mController.setDataSaverEnabled(false); + + assertThat(mPreference.isEnabled()).isTrue(); + verify(mSwitch).setEnabled(true); + } + + @Test + public void onSwitchToggled_isChecked_startTethering() { + boolean ret = mController.onSwitchToggled(true); + + verify(mTetheringManagerModel).startTethering(TETHERING_WIFI); + assertThat(ret).isTrue(); + } + + @Test + public void onSwitchToggled_isUnchecked_stopTethering() { + boolean ret = mController.onSwitchToggled(false); + + verify(mTetheringManagerModel).stopTethering(TETHERING_WIFI); + assertThat(ret).isTrue(); + } + + @Implements(WifiTetherSettings.class) public static final class ShadowWifiTetherSettings {