diff --git a/res/xml/mobile_network_settings.xml b/res/xml/mobile_network_settings.xml index 62a88b75646..038688e390c 100644 --- a/res/xml/mobile_network_settings.xml +++ b/res/xml/mobile_network_settings.xml @@ -210,7 +210,7 @@ android:title="@string/network_operator_category" settings:controller="com.android.settings.network.telephony.NetworkPreferenceCategoryController"> - diff --git a/src/com/android/settings/network/helper/LifecycleCallbackAdapter.java b/src/com/android/settings/network/helper/LifecycleCallbackAdapter.java deleted file mode 100644 index 548eae572f4..00000000000 --- a/src/com/android/settings/network/helper/LifecycleCallbackAdapter.java +++ /dev/null @@ -1,100 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.settings.network.helper; - -import androidx.annotation.MainThread; -import androidx.annotation.NonNull; -import androidx.annotation.VisibleForTesting; -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LifecycleEventObserver; -import androidx.lifecycle.LifecycleOwner; - -import java.util.concurrent.atomic.AtomicReference; - -/** - * A {@link androidx.lifecycle.LifecycleObserver} implementation of adapter over callback. - * - * Which including: - * 1. Request to active callback when Lifecycle.State.STARTED - * 2. Request to inactive callback when Lifecycle.State.STOPPED - * 3. Close (no further resume) when Lifecycle.State.DESTROYED - */ -@VisibleForTesting -abstract class LifecycleCallbackAdapter implements LifecycleEventObserver, AutoCloseable { - private static final String TAG = "LifecycleCallbackAdapter"; - private AtomicReference mLifecycle = new AtomicReference(); - - /** - * Constructor - * @param lifecycle {@link Lifecycle} to monitor - */ - @VisibleForTesting - protected LifecycleCallbackAdapter(@NonNull Lifecycle lifecycle) { - mLifecycle.set(lifecycle); - lifecycle.addObserver(this); - } - - /** - * Get {@link Lifecycle} under monitor. - * @return {@link Lifecycle}. Return {@code null} when closed. - */ - @VisibleForTesting - public Lifecycle getLifecycle() { - return mLifecycle.get(); - } - - /** - * Check current callback status. - * @return true when callback is active. - */ - public abstract boolean isCallbackActive(); - - /** - * Change callback status. - * @param isActive true to active callback, otherwise inactive. - */ - public abstract void setCallbackActive(boolean isActive); - - /** - * Implementation of LifecycleEventObserver. - */ - public void onStateChanged(LifecycleOwner source, Lifecycle.Event event) { - if (mLifecycle.get() == null) { - return; - } - - Lifecycle.State state = event.getTargetState(); - boolean expectCallbackActive = state.isAtLeast(Lifecycle.State.STARTED); - if (expectCallbackActive != isCallbackActive()) { - setCallbackActive(expectCallbackActive); - } - if (state == Lifecycle.State.DESTROYED) { - close(); - } - } - - /** - * Implementation of AutoCloseable. - */ - @MainThread - public void close() { - Lifecycle lifecycle = mLifecycle.getAndSet(null); - if (lifecycle != null) { - lifecycle.removeObserver(this); - } - } -} diff --git a/src/com/android/settings/network/helper/LifecycleCallbackConverter.java b/src/com/android/settings/network/helper/LifecycleCallbackConverter.java deleted file mode 100644 index f35b69a4177..00000000000 --- a/src/com/android/settings/network/helper/LifecycleCallbackConverter.java +++ /dev/null @@ -1,132 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.settings.network.helper; - -import androidx.annotation.AnyThread; -import androidx.annotation.NonNull; -import androidx.annotation.UiThread; -import androidx.annotation.VisibleForTesting; -import androidx.lifecycle.Lifecycle; - -import com.android.settingslib.utils.ThreadUtils; - -import java.util.concurrent.atomic.AtomicLong; -import java.util.function.Consumer; - -/** - * A {@link LifecycleCallbackAdapter} which support carrying a result from any threads back to UI - * thread through {@link #postResult(T)}. - * - * A {@link Consumer} would be invoked from UI thread for further processing on the result. - * - * Note: Result not in STARTED or RESUMED stage will be discarded silently. - * This is to align with the criteria set within - * {@link LifecycleCallbackAdapter#onStateChanged()}. - */ -@VisibleForTesting -public class LifecycleCallbackConverter extends LifecycleCallbackAdapter { - private static final String TAG = "LifecycleCallbackConverter"; - - private final Thread mUiThread; - private final Consumer mResultCallback; - - /** - * A record of number of active status change. - * Even numbers (0, 2, 4, 6 ...) are inactive status. - * Odd numbers (1, 3, 5, 7 ...) are active status. - */ - private final AtomicLong mNumberOfActiveStatusChange = new AtomicLong(); - - /** - * Constructor - * - * @param lifecycle {@link Lifecycle} to monitor - * @param resultCallback for further processing the result - */ - @VisibleForTesting - @UiThread - public LifecycleCallbackConverter( - @NonNull Lifecycle lifecycle, @NonNull Consumer resultCallback) { - super(lifecycle); - mUiThread = Thread.currentThread(); - mResultCallback = resultCallback; - } - - /** - * Post a result (from any thread) back to UI thread. - * - * @param result the object ready to be passed back to {@link Consumer}. - */ - @AnyThread - @VisibleForTesting - public void postResult(T result) { - /** - * Since mNumberOfActiveStatusChange only increase, it is a concept of sequence number. - * Carry it when sending data in between different threads allow to verify if the data - * has arrived on time. And drop the data when expired. - */ - long currentNumberOfChange = mNumberOfActiveStatusChange.get(); - if (Thread.currentThread() == mUiThread) { - dispatchExtResult(currentNumberOfChange, result); // Dispatch directly - } else { - postResultToUiThread(currentNumberOfChange, result); - } - } - - @AnyThread - protected void postResultToUiThread(long numberOfStatusChange, T result) { - ThreadUtils.postOnMainThread(() -> dispatchExtResult(numberOfStatusChange, result)); - } - - @UiThread - protected void dispatchExtResult(long numberOfStatusChange, T result) { - /** - * For a postResult() sending in between different threads, not only create a latency - * but also enqueued into main UI thread for dispatch. - * - * To align behavior within {@link LifecycleCallbackAdapter#onStateChanged()}, - * some checking on both numberOfStatusChange and {@link Lifecycle} status are required. - */ - if (isActiveStatus(numberOfStatusChange) - && (numberOfStatusChange == mNumberOfActiveStatusChange.get()) - && getLifecycle().getCurrentState().isAtLeast(Lifecycle.State.STARTED)) { - mResultCallback.accept(result); - } - } - - private static final boolean isActiveStatus(long numberOfStatusChange) { - return ((numberOfStatusChange & 1L) != 0L); - } - - /* Implementation of LifecycleCallbackAdapter */ - @UiThread - public boolean isCallbackActive() { - return isActiveStatus(mNumberOfActiveStatusChange.get()); - } - - /* Implementation of LifecycleCallbackAdapter */ - @UiThread - public void setCallbackActive(boolean updatedActiveStatus) { - /** - * Make sure only increase when active status got changed. - * This is to implement the definition of mNumberOfActiveStatusChange. - */ - if (isCallbackActive() != updatedActiveStatus) { - mNumberOfActiveStatusChange.getAndIncrement(); - } - } -} diff --git a/src/com/android/settings/network/helper/LifecycleCallbackIntentReceiver.java b/src/com/android/settings/network/helper/LifecycleCallbackIntentReceiver.java deleted file mode 100644 index 8aaa53e0af8..00000000000 --- a/src/com/android/settings/network/helper/LifecycleCallbackIntentReceiver.java +++ /dev/null @@ -1,104 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.settings.network.helper; - -import android.content.BroadcastReceiver; -import android.content.Context; -import android.content.Intent; -import android.content.IntentFilter; -import android.os.Handler; -import androidx.annotation.NonNull; -import androidx.annotation.VisibleForTesting; -import androidx.lifecycle.Lifecycle; -import java.util.function.Consumer; - -/** - * A {@link BroadcastReceiver} for {@link Intent}. - * - * This is {@link BroadcastReceiver} supported by {@link LifecycleCallbackConverter}, - * and only register when state is either START or RESUME. - */ -@VisibleForTesting -public class LifecycleCallbackIntentReceiver extends LifecycleCallbackConverter { - private static final String TAG = "LifecycleCallbackIntentReceiver"; - - @VisibleForTesting - protected final BroadcastReceiver mReceiver; - - private final Runnable mRegisterCallback; - private final Runnable mUnRegisterCallback; - - /** - * Constructor - * @param lifecycle {@link Lifecycle} to monitor - * @param context for this BroadcastReceiver - * @param filter the IntentFilter for BroadcastReceiver - * @param broadcastPermission for permission when listening - * @param scheduler for running in background thread - * @param resultCallback for the Intent from BroadcastReceiver - */ - @VisibleForTesting - public LifecycleCallbackIntentReceiver(@NonNull Lifecycle lifecycle, - @NonNull Context context, @NonNull IntentFilter filter, - String broadcastPermission, Handler scheduler, - @NonNull Consumer resultCallback) { - super(lifecycle, resultCallback); - - // BroadcastReceiver - mReceiver = new BroadcastReceiver() { - public void onReceive(Context context, Intent intent) { - if (isInitialStickyBroadcast()) { - return; - } - final String action = intent.getAction(); - if ((action == null) || (action.length() <= 0)) { - return; - } - postResult(intent); - } - }; - - // Register operation - mRegisterCallback = () -> { - Intent initIntent = context.registerReceiver(mReceiver, - filter, broadcastPermission, scheduler); - if (initIntent != null) { - postResult(initIntent); - } - }; - - // Un-Register operation - mUnRegisterCallback = () -> { - context.unregisterReceiver(mReceiver); - }; - } - - @Override - public void setCallbackActive(boolean isActive) { - super.setCallbackActive(isActive); - Runnable op = (isActive) ? mRegisterCallback : mUnRegisterCallback; - op.run(); - } - - @Override - public void close() { - super.close(); - if (isCallbackActive()) { - setCallbackActive(false); - } - } -} diff --git a/src/com/android/settings/network/helper/LifecycleCallbackTelephonyAdapter.java b/src/com/android/settings/network/helper/LifecycleCallbackTelephonyAdapter.java deleted file mode 100644 index 0fae4f27aaf..00000000000 --- a/src/com/android/settings/network/helper/LifecycleCallbackTelephonyAdapter.java +++ /dev/null @@ -1,72 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.settings.network.helper; - -import android.telephony.TelephonyCallback; -import android.telephony.TelephonyManager; - -import androidx.annotation.NonNull; -import androidx.annotation.VisibleForTesting; -import androidx.lifecycle.Lifecycle; - -import java.util.concurrent.Executor; -import java.util.function.Consumer; - -/** - * A {@link LifecycleCallbackConverter} for supporting the register/unregister work for - * {@link TelephonyCallback}. - */ -@VisibleForTesting -public class LifecycleCallbackTelephonyAdapter extends LifecycleCallbackConverter { - private static final String TAG = "LifecycleCallbackTelephony"; - - private final Runnable mRegisterCallback; - private final Runnable mUnRegisterCallback; - - /** - * Constructor - * @param lifecycle {@link Lifecycle} to monitor - * @param telephonyManager {@link TelephonyManager} to interact with - * @param telephonyCallback {@link TelephonyCallback} - * @param executor {@link Executor} for receiving the notify from telephony framework. - * @param resultCallback for the result from {@link TelephonyCallback} - */ - @VisibleForTesting - public LifecycleCallbackTelephonyAdapter(@NonNull Lifecycle lifecycle, - @NonNull TelephonyManager telephonyManager, - @NonNull TelephonyCallback telephonyCallback, - Executor executor, @NonNull Consumer resultCallback) { - super(lifecycle, resultCallback); - - // Register operation - mRegisterCallback = () -> { - telephonyManager.registerTelephonyCallback(executor, telephonyCallback); - }; - - // Un-Register operation - mUnRegisterCallback = () -> { - telephonyManager.unregisterTelephonyCallback(telephonyCallback); - }; - } - - @Override - public void setCallbackActive(boolean isActive) { - super.setCallbackActive(isActive); - Runnable op = (isActive) ? mRegisterCallback : mUnRegisterCallback; - op.run(); - } -} diff --git a/src/com/android/settings/network/helper/ServiceStateStatus.java b/src/com/android/settings/network/helper/ServiceStateStatus.java deleted file mode 100644 index 40e9e3fbcb5..00000000000 --- a/src/com/android/settings/network/helper/ServiceStateStatus.java +++ /dev/null @@ -1,105 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.settings.network.helper; - -import android.telephony.ServiceState; -import android.telephony.TelephonyCallback; -import android.telephony.TelephonyManager; - -import androidx.annotation.NonNull; -import androidx.annotation.VisibleForTesting; -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LiveData; - -import java.util.concurrent.Executor; -import java.util.function.Consumer; - -/** - * A {@link LiveData} as a mapping of allowed network types reported from {@link TelephonyCallback}. - * Only got update when Lifecycle.State is considered as STARTED or RESUMED. - * - * {@code null} when status unknown. Other values are {@link ServiceState}. - * - * @deprecated Please us {@link com.android.settings.network.telephony.ServiceStateFlowKt} instead. - */ -@Deprecated -public class ServiceStateStatus extends LiveData { - private static final String TAG = "ServiceStateStatus"; - - @VisibleForTesting - protected ServiceStateProducer mServiceStateProducer; - - @VisibleForTesting - protected LifecycleCallbackTelephonyAdapter mAdapter; - - @VisibleForTesting - protected Consumer mLiveDataUpdater = status -> setValue(status); - - /** - * Constructor - * @param lifecycle {@link Lifecycle} to monitor - * @param telephonyManager {@link TelephonyManager} to interact with - * @param executor {@link Executor} for receiving the notify from telephony framework. - */ - @VisibleForTesting - public ServiceStateStatus(@NonNull Lifecycle lifecycle, - @NonNull TelephonyManager telephonyManager, Executor executor) { - super(); - - mServiceStateProducer = new ServiceStateProducer(this); - - mAdapter = new LifecycleCallbackTelephonyAdapter(lifecycle, - telephonyManager, mServiceStateProducer, executor, mLiveDataUpdater) { - @Override - public void setCallbackActive(boolean isActive) { - super.setCallbackActive(isActive); - if (!isActive) { - /** - * Set to unknown status when no longer actively monitoring - * {@link TelephonyCallback}. - */ - mLiveDataUpdater.accept(null); - } - } - }; - } - - /** - * An implementation of TelephonyCallback. - * - * Change of allowed network type will be forward to - * {@link LifecycleCallbackTelephonyAdapter}. - */ - @VisibleForTesting - protected static class ServiceStateProducer extends TelephonyCallback - implements TelephonyCallback.ServiceStateListener { - private final ServiceStateStatus mStatus; - - /** - * Constructor - * @param status {@link ServiceStateStatus} - */ - public ServiceStateProducer(ServiceStateStatus status) { - mStatus = status; - } - - @Override - public void onServiceStateChanged(ServiceState serviceState) { - mStatus.mAdapter.postResult(serviceState); - } - } -} diff --git a/src/com/android/settings/network/helper/VoiceCallStatus.java b/src/com/android/settings/network/helper/VoiceCallStatus.java deleted file mode 100644 index a5252cb193b..00000000000 --- a/src/com/android/settings/network/helper/VoiceCallStatus.java +++ /dev/null @@ -1,102 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.settings.network.helper; - -import android.telephony.TelephonyCallback; -import android.telephony.TelephonyManager; - -import androidx.annotation.NonNull; -import androidx.annotation.VisibleForTesting; -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LiveData; - -import java.util.concurrent.Executor; -import java.util.function.Consumer; - -/** - * A {@link LiveData} as a mapping of voice call state reported from {@link TelephonyCallback}. - * Only got update when Lifecycle.State is considered as STARTED or RESUMED. - * - * {@code null} when status unknown. Other values are TelephonyManager#CALL_STATE_IDLE, - * TelephonyManager#CALL_STATE_RINGING and TelephonyManager#CALL_STATE_OFFHOOK. - */ -@VisibleForTesting -public class VoiceCallStatus extends LiveData { - private static final String TAG = "VoiceCallStatus"; - - @VisibleForTesting - protected CallStateProducer mCallStateProducer; - - @VisibleForTesting - protected LifecycleCallbackTelephonyAdapter mAdapter; - - @VisibleForTesting - protected Consumer mLiveDataUpdater = status -> setValue(status); - - /** - * Constructor - * @param lifecycle {@link Lifecycle} to monitor - * @param telephonyManager {@link TelephonyManager} to interact with - * @param executor {@link Executor} for receiving the notify from telephony framework. - */ - @VisibleForTesting - public VoiceCallStatus(@NonNull Lifecycle lifecycle, - @NonNull TelephonyManager telephonyManager, Executor executor) { - super(); - - mCallStateProducer = new CallStateProducer(this); - - mAdapter = new LifecycleCallbackTelephonyAdapter(lifecycle, - telephonyManager, mCallStateProducer, executor, mLiveDataUpdater) { - @Override - public void setCallbackActive(boolean isActive) { - super.setCallbackActive(isActive); - if (!isActive) { - /** - * Set to unknown status when no longer actively monitoring - * {@link TelephonyCallback}. - */ - mLiveDataUpdater.accept(null); - } - } - }; - } - - /** - * An implementation of TelephonyCallback. - * - * Status of voice call will be forward to {@link LifecycleCallbackTelephonyAdapter} - */ - @VisibleForTesting - protected static class CallStateProducer extends TelephonyCallback - implements TelephonyCallback.CallStateListener { - private final VoiceCallStatus mStatus; - - /** - * Constructor - * @param status {@link VoiceCallStatus} - */ - public CallStateProducer(VoiceCallStatus status) { - mStatus = status; - } - - @Override - public void onCallStateChanged(int state) { - mStatus.mAdapter.postResult(state); - } - } -} diff --git a/src/com/android/settings/network/telephony/MobileNetworkSettings.java b/src/com/android/settings/network/telephony/MobileNetworkSettings.java index dbe8ae86817..0812ccc83cd 100644 --- a/src/com/android/settings/network/telephony/MobileNetworkSettings.java +++ b/src/com/android/settings/network/telephony/MobileNetworkSettings.java @@ -276,7 +276,7 @@ public class MobileNetworkSettings extends AbstractMobileNetworkSettings impleme use(OpenNetworkSelectPagePreferenceController.class).init(mSubId); final AutoSelectPreferenceController autoSelectPreferenceController = use(AutoSelectPreferenceController.class) - .init(getLifecycle(), mSubId) + .init(mSubId) .addListener(openNetworkSelectPagePreferenceController); use(NetworkPreferenceCategoryController.class).init(mSubId) .setChildren(Arrays.asList(autoSelectPreferenceController)); diff --git a/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceController.java b/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceController.java deleted file mode 100644 index 36e2aa8e935..00000000000 --- a/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceController.java +++ /dev/null @@ -1,339 +0,0 @@ -/* - * Copyright (C) 2018 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.settings.network.telephony.gsm; - -import static com.android.settings.Utils.SETTINGS_PACKAGE_NAME; - -import android.app.ProgressDialog; -import android.content.Context; -import android.content.Intent; -import android.os.Handler; -import android.os.HandlerExecutor; -import android.os.Looper; -import android.os.PersistableBundle; -import android.os.SystemClock; -import android.provider.Settings; -import android.telephony.CarrierConfigManager; -import android.telephony.ServiceState; -import android.telephony.SubscriptionManager; -import android.telephony.TelephonyManager; -import android.util.Log; - -import androidx.annotation.NonNull; -import androidx.annotation.VisibleForTesting; -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LifecycleEventObserver; -import androidx.lifecycle.LifecycleOwner; -import androidx.preference.Preference; -import androidx.preference.PreferenceScreen; -import androidx.preference.TwoStatePreference; - -import com.android.settings.R; -import com.android.settings.network.AllowedNetworkTypesListener; -import com.android.settings.network.CarrierConfigCache; -import com.android.settings.network.helper.ServiceStateStatus; -import com.android.settings.network.telephony.MobileNetworkUtils; -import com.android.settings.network.telephony.TelephonyTogglePreferenceController; -import com.android.settingslib.utils.ThreadUtils; - -import java.util.ArrayList; -import java.util.List; -import java.util.concurrent.Future; -import java.util.concurrent.TimeUnit; -import java.util.concurrent.atomic.AtomicBoolean; -import java.util.concurrent.atomic.AtomicLong; - -/** - * Preference controller for "Auto Select Network" - */ -public class AutoSelectPreferenceController extends TelephonyTogglePreferenceController - implements LifecycleEventObserver{ - private static final long MINIMUM_DIALOG_TIME_MILLIS = TimeUnit.SECONDS.toMillis(1); - private static final String LOG_TAG = "AutoSelectPreferenceController"; - private static final String INTERNAL_LOG_TAG_ONRESUME = "OnResume"; - private static final String INTERNAL_LOG_TAG_AFTERSET = "AfterSet"; - - private final Handler mUiHandler; - private PreferenceScreen mPreferenceScreen; - private AllowedNetworkTypesListener mAllowedNetworkTypesListener; - private TelephonyManager mTelephonyManager; - private boolean mOnlyAutoSelectInHome; - private List mListeners; - @VisibleForTesting - ProgressDialog mProgressDialog; - @VisibleForTesting - TwoStatePreference mSwitchPreference; - private AtomicBoolean mUpdatingConfig; - private int mCacheOfModeStatus; - private AtomicLong mRecursiveUpdate; - ServiceStateStatus mServiceStateStatus; - - public AutoSelectPreferenceController(Context context, String key) { - super(context, key); - mTelephonyManager = context.getSystemService(TelephonyManager.class); - mSubId = SubscriptionManager.INVALID_SUBSCRIPTION_ID; - mRecursiveUpdate = new AtomicLong(); - mUpdatingConfig = new AtomicBoolean(); - mCacheOfModeStatus = TelephonyManager.NETWORK_SELECTION_MODE_UNKNOWN; - mListeners = new ArrayList<>(); - mUiHandler = new Handler(Looper.getMainLooper()); - mAllowedNetworkTypesListener = new AllowedNetworkTypesListener( - new HandlerExecutor(mUiHandler)); - mAllowedNetworkTypesListener.setAllowedNetworkTypesListener( - () -> updatePreference()); - } - - private void updatePreference() { - if (mPreferenceScreen != null) { - displayPreference(mPreferenceScreen); - } - if (mSwitchPreference != null) { - mRecursiveUpdate.getAndIncrement(); - updateState(mSwitchPreference); - mRecursiveUpdate.decrementAndGet(); - } - } - - /** - * Implementation of LifecycleEventObserver. - */ - @SuppressWarnings("FutureReturnValueIgnored") - public void onStateChanged(@NonNull LifecycleOwner lifecycleOwner, - @NonNull Lifecycle.Event event) { - switch (event) { - case ON_START: - mAllowedNetworkTypesListener.register(mContext, mSubId); - break; - case ON_RESUME: - ThreadUtils.postOnBackgroundThread(() -> { - queryNetworkSelectionMode(INTERNAL_LOG_TAG_ONRESUME); - //Update UI in UI thread - mUiHandler.post(() -> { - if (mSwitchPreference != null) { - mRecursiveUpdate.getAndIncrement(); - mSwitchPreference.setChecked(isChecked()); - mRecursiveUpdate.decrementAndGet(); - updateListenerValue(); - } - }); - }); - break; - case ON_STOP: - mAllowedNetworkTypesListener.unregister(mContext, mSubId); - break; - default: - // Do nothing - break; - } - } - - @Override - public int getAvailabilityStatus(int subId) { - return MobileNetworkUtils.shouldDisplayNetworkSelectOptions(mContext, subId) - ? AVAILABLE - : CONDITIONALLY_UNAVAILABLE; - } - - @Override - public void displayPreference(PreferenceScreen screen) { - super.displayPreference(screen); - mPreferenceScreen = screen; - mSwitchPreference = screen.findPreference(getPreferenceKey()); - } - - @Override - public boolean isChecked() { - return mCacheOfModeStatus == TelephonyManager.NETWORK_SELECTION_MODE_AUTO; - } - - @Override - public void updateState(Preference preference) { - super.updateState(preference); - - preference.setSummary(null); - final ServiceState serviceState = mTelephonyManager.getServiceState(); - if (serviceState == null) { - preference.setEnabled(false); - return; - } - - if (serviceState.getRoaming()) { - preference.setEnabled(true); - } else { - preference.setEnabled(!mOnlyAutoSelectInHome); - if (mOnlyAutoSelectInHome) { - preference.setSummary(mContext.getString( - R.string.manual_mode_disallowed_summary, - mTelephonyManager.getSimOperatorName())); - } - } - } - - @Override - public boolean setChecked(boolean isChecked) { - if (mRecursiveUpdate.get() != 0) { - // Changing from software are allowed and changing presentation only. - return true; - } - if (isChecked) { - setAutomaticSelectionMode(); - } else { - if (mSwitchPreference != null) { - Intent intent = new Intent(); - intent.setClassName(SETTINGS_PACKAGE_NAME, - SETTINGS_PACKAGE_NAME + ".Settings$NetworkSelectActivity"); - intent.putExtra(Settings.EXTRA_SUB_ID, mSubId); - mSwitchPreference.setIntent(intent); - } - } - return false; - } - - @VisibleForTesting - Future setAutomaticSelectionMode() { - final long startMillis = SystemClock.elapsedRealtime(); - showAutoSelectProgressBar(); - if (mSwitchPreference != null) { - mSwitchPreference.setIntent(null); - mSwitchPreference.setEnabled(false); - } - return ThreadUtils.postOnBackgroundThread(() -> { - // set network selection mode in background - mUpdatingConfig.set(true); - mTelephonyManager.setNetworkSelectionModeAutomatic(); - mUpdatingConfig.set(false); - - //Update UI in UI thread - final long durationMillis = SystemClock.elapsedRealtime() - startMillis; - - mUiHandler.postDelayed(() -> { - ThreadUtils.postOnBackgroundThread(() -> { - queryNetworkSelectionMode(INTERNAL_LOG_TAG_AFTERSET); - - //Update UI in UI thread - mUiHandler.post(() -> { - mRecursiveUpdate.getAndIncrement(); - if (mSwitchPreference != null) { - mSwitchPreference.setEnabled(true); - mSwitchPreference.setChecked(isChecked()); - } - mRecursiveUpdate.decrementAndGet(); - updateListenerValue(); - dismissProgressBar(); - }); - }); - }, Math.max(MINIMUM_DIALOG_TIME_MILLIS - durationMillis, 0)); - }); - } - - /** - * Initialization based on given subscription id. - **/ - public AutoSelectPreferenceController init(Lifecycle lifecycle, int subId) { - mSubId = subId; - mTelephonyManager = mContext.getSystemService(TelephonyManager.class) - .createForSubscriptionId(mSubId); - final PersistableBundle carrierConfig = - CarrierConfigCache.getInstance(mContext).getConfigForSubId(mSubId); - mOnlyAutoSelectInHome = carrierConfig != null - ? carrierConfig.getBoolean( - CarrierConfigManager.KEY_ONLY_AUTO_SELECT_IN_HOME_NETWORK_BOOL) - : false; - - mServiceStateStatus = new ServiceStateStatus(lifecycle, mTelephonyManager, - new HandlerExecutor(mUiHandler)) { - @Override - protected void setValue(ServiceState status) { - if (status == null) { - return; - } - updateUiAutoSelectValue(status); - } - }; - return this; - } - - public AutoSelectPreferenceController addListener(OnNetworkSelectModeListener lsn) { - mListeners.add(lsn); - - return this; - } - - private void queryNetworkSelectionMode(String tag) { - mCacheOfModeStatus = mTelephonyManager.getNetworkSelectionMode(); - Log.d(LOG_TAG, tag + ": query command done. mCacheOfModeStatus: " + mCacheOfModeStatus); - } - - @VisibleForTesting - void updateUiAutoSelectValue(ServiceState status) { - if (status == null) { - return; - } - if (!mUpdatingConfig.get()) { - int networkSelectionMode = status.getIsManualSelection() - ? TelephonyManager.NETWORK_SELECTION_MODE_MANUAL - : TelephonyManager.NETWORK_SELECTION_MODE_AUTO; - if (mCacheOfModeStatus == networkSelectionMode) { - return; - } - mCacheOfModeStatus = networkSelectionMode; - Log.d(LOG_TAG, "updateUiAutoSelectValue: mCacheOfModeStatus: " + mCacheOfModeStatus); - - mRecursiveUpdate.getAndIncrement(); - updateState(mSwitchPreference); - mRecursiveUpdate.decrementAndGet(); - updateListenerValue(); - } - } - - private void updateListenerValue() { - for (OnNetworkSelectModeListener lsn : mListeners) { - lsn.onNetworkSelectModeUpdated(mCacheOfModeStatus); - } - } - - private void showAutoSelectProgressBar() { - if (mProgressDialog == null) { - mProgressDialog = new ProgressDialog(mContext); - mProgressDialog.setMessage( - mContext.getResources().getString(R.string.register_automatically)); - mProgressDialog.setCanceledOnTouchOutside(false); - mProgressDialog.setCancelable(false); - mProgressDialog.setIndeterminate(true); - } - mProgressDialog.show(); - } - - private void dismissProgressBar() { - if (mProgressDialog != null && mProgressDialog.isShowing()) { - try { - mProgressDialog.dismiss(); - } catch (IllegalArgumentException e) { - // Ignore exception since the dialog will be gone anyway. - } - } - } - - /** - * Callback when network select mode might get updated - * - * @see TelephonyManager#getNetworkSelectionMode() - */ - public interface OnNetworkSelectModeListener { - void onNetworkSelectModeUpdated(int mode); - } -} diff --git a/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceController.kt b/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceController.kt new file mode 100644 index 00000000000..1ed9d9aceda --- /dev/null +++ b/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceController.kt @@ -0,0 +1,224 @@ +/* + * Copyright (C) 2023 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.network.telephony.gsm + +import android.app.ProgressDialog +import android.content.Context +import android.content.Intent +import android.os.PersistableBundle +import android.provider.Settings +import android.telephony.CarrierConfigManager +import android.telephony.ServiceState +import android.telephony.TelephonyManager +import androidx.annotation.VisibleForTesting +import androidx.compose.runtime.Composable +import androidx.compose.runtime.getValue +import androidx.compose.runtime.remember +import androidx.compose.runtime.rememberCoroutineScope +import androidx.compose.ui.res.stringResource +import androidx.lifecycle.LifecycleOwner +import androidx.lifecycle.compose.collectAsStateWithLifecycle +import androidx.preference.Preference +import androidx.preference.PreferenceScreen +import com.android.settings.R +import com.android.settings.Settings.NetworkSelectActivity +import com.android.settings.network.CarrierConfigCache +import com.android.settings.network.telephony.MobileNetworkUtils +import com.android.settings.network.telephony.allowedNetworkTypesFlow +import com.android.settings.network.telephony.serviceStateFlow +import com.android.settings.spa.preference.ComposePreferenceController +import com.android.settingslib.spa.framework.compose.OverridableFlow +import com.android.settingslib.spa.framework.util.collectLatestWithLifecycle +import com.android.settingslib.spa.widget.preference.SwitchPreference +import com.android.settingslib.spa.widget.preference.SwitchPreferenceModel +import kotlin.properties.Delegates.notNull +import kotlin.time.Duration.Companion.seconds +import kotlinx.coroutines.Dispatchers +import kotlinx.coroutines.async +import kotlinx.coroutines.delay +import kotlinx.coroutines.flow.Flow +import kotlinx.coroutines.flow.SharingStarted +import kotlinx.coroutines.flow.filterNotNull +import kotlinx.coroutines.flow.map +import kotlinx.coroutines.flow.onEach +import kotlinx.coroutines.flow.stateIn +import kotlinx.coroutines.launch +import kotlinx.coroutines.withContext + +/** + * Preference controller for "Auto Select Network" + */ +class AutoSelectPreferenceController @JvmOverloads constructor( + context: Context, + key: String, + private val allowedNetworkTypesFlowFactory: (subId: Int) -> Flow = + context::allowedNetworkTypesFlow, + private val serviceStateFlowFactory: (subId: Int) -> Flow = + context::serviceStateFlow, + private val getConfigForSubId: (subId: Int) -> PersistableBundle = { subId -> + CarrierConfigCache.getInstance(context).getConfigForSubId(subId) + }, +) : ComposePreferenceController(context, key) { + + private lateinit var telephonyManager: TelephonyManager + private val listeners = mutableListOf() + + @VisibleForTesting + var progressDialog: ProgressDialog? = null + + private lateinit var preference: Preference + + private var subId by notNull() + + /** + * Initialization based on given subscription id. + */ + fun init(subId: Int): AutoSelectPreferenceController { + this.subId = subId + telephonyManager = mContext.getSystemService(TelephonyManager::class.java)!! + .createForSubscriptionId(subId) + + return this + } + + override fun getAvailabilityStatus() = + if (MobileNetworkUtils.shouldDisplayNetworkSelectOptions(mContext, subId)) AVAILABLE + else CONDITIONALLY_UNAVAILABLE + + override fun displayPreference(screen: PreferenceScreen) { + super.displayPreference(screen) + preference = screen.findPreference(preferenceKey)!! + } + + @Composable + override fun Content() { + val coroutineScope = rememberCoroutineScope() + val serviceStateFlow = remember { + serviceStateFlowFactory(subId) + .stateIn(coroutineScope, SharingStarted.Lazily, null) + .filterNotNull() + } + val isAutoOverridableFlow = remember { + OverridableFlow(serviceStateFlow.map { !it.isManualSelection }) + } + val isAuto by isAutoOverridableFlow.flow + .onEach(::updateListenerValue) + .collectAsStateWithLifecycle(initialValue = null) + val disallowedSummary by serviceStateFlow.map(::getDisallowedSummary) + .collectAsStateWithLifecycle(initialValue = "") + SwitchPreference(object : SwitchPreferenceModel { + override val title = stringResource(R.string.select_automatically) + override val summary = { disallowedSummary } + override val changeable = { disallowedSummary.isEmpty() } + override val checked = { isAuto } + override val onCheckedChange: (Boolean) -> Unit = { newChecked -> + if (newChecked) { + coroutineScope.launch { setAutomaticSelectionMode(isAutoOverridableFlow) } + } else { + mContext.startActivity(Intent().apply { + setClass(mContext, NetworkSelectActivity::class.java) + putExtra(Settings.EXTRA_SUB_ID, subId) + }) + } + } + }) + } + + private suspend fun getDisallowedSummary(serviceState: ServiceState): String = + withContext(Dispatchers.Default) { + if (!serviceState.roaming && onlyAutoSelectInHome()) { + mContext.getString( + R.string.manual_mode_disallowed_summary, + telephonyManager.simOperatorName + ) + } else "" + } + + private fun onlyAutoSelectInHome(): Boolean = + getConfigForSubId(subId) + .getBoolean(CarrierConfigManager.KEY_ONLY_AUTO_SELECT_IN_HOME_NETWORK_BOOL) + + private suspend fun setAutomaticSelectionMode(overrideChannel: OverridableFlow) { + showAutoSelectProgressBar() + + withContext(Dispatchers.Default) { + val minimumDialogTimeDeferred = async { delay(MINIMUM_DIALOG_TIME) } + telephonyManager.setNetworkSelectionModeAutomatic() + minimumDialogTimeDeferred.await() + } + overrideChannel.override(true) + + dismissProgressBar() + } + + override fun onViewCreated(viewLifecycleOwner: LifecycleOwner) { + allowedNetworkTypesFlowFactory(subId).collectLatestWithLifecycle(viewLifecycleOwner) { + preference.isVisible = withContext(Dispatchers.Default) { + MobileNetworkUtils.shouldDisplayNetworkSelectOptions(mContext, subId) + } + } + } + + fun addListener(listener: OnNetworkSelectModeListener): AutoSelectPreferenceController { + listeners.add(listener) + return this + } + + private fun updateListenerValue(isAuto: Boolean) { + for (listener in listeners) { + listener.onNetworkSelectModeUpdated( + if (isAuto) TelephonyManager.NETWORK_SELECTION_MODE_AUTO + else TelephonyManager.NETWORK_SELECTION_MODE_MANUAL + ) + } + } + + private fun showAutoSelectProgressBar() { + if (progressDialog == null) { + progressDialog = ProgressDialog(mContext).apply { + setMessage(mContext.resources.getString(R.string.register_automatically)) + setCanceledOnTouchOutside(false) + setCancelable(false) + isIndeterminate = true + } + } + progressDialog?.show() + } + + private fun dismissProgressBar() { + if (progressDialog?.isShowing == true) { + try { + progressDialog?.dismiss() + } catch (e: IllegalArgumentException) { + // Ignore exception since the dialog will be gone anyway. + } + } + } + + /** + * Callback when network select mode might get updated + * + * @see TelephonyManager.getNetworkSelectionMode + */ + interface OnNetworkSelectModeListener { + fun onNetworkSelectModeUpdated(mode: Int) + } + + companion object { + private val MINIMUM_DIALOG_TIME = 1.seconds + } +} diff --git a/tests/spa_unit/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceControllerTest.kt b/tests/spa_unit/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceControllerTest.kt new file mode 100644 index 00000000000..f821e1a76fd --- /dev/null +++ b/tests/spa_unit/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceControllerTest.kt @@ -0,0 +1,197 @@ +/* + * Copyright (C) 2023 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package com.android.settings.network.telephony.gsm + +import android.content.Context +import android.content.Intent +import android.provider.Settings +import android.telephony.CarrierConfigManager +import android.telephony.ServiceState +import android.telephony.TelephonyManager +import androidx.compose.ui.test.assertIsEnabled +import androidx.compose.ui.test.assertIsNotEnabled +import androidx.compose.ui.test.assertIsOff +import androidx.compose.ui.test.assertIsOn +import androidx.compose.ui.test.junit4.createComposeRule +import androidx.compose.ui.test.onNodeWithText +import androidx.compose.ui.test.onRoot +import androidx.compose.ui.test.performClick +import androidx.core.os.persistableBundleOf +import androidx.preference.PreferenceManager +import androidx.test.core.app.ApplicationProvider +import androidx.test.ext.junit.runners.AndroidJUnit4 +import com.android.settings.R +import com.android.settings.Settings.NetworkSelectActivity +import com.android.settings.spa.preference.ComposePreference +import com.google.common.truth.Truth.assertThat +import kotlinx.coroutines.delay +import kotlinx.coroutines.flow.emptyFlow +import kotlinx.coroutines.flow.flowOf +import kotlinx.coroutines.runBlocking +import org.junit.Before +import org.junit.Rule +import org.junit.Test +import org.junit.runner.RunWith +import org.mockito.kotlin.any +import org.mockito.kotlin.argumentCaptor +import org.mockito.kotlin.doNothing +import org.mockito.kotlin.doReturn +import org.mockito.kotlin.mock +import org.mockito.kotlin.spy +import org.mockito.kotlin.verify +import org.mockito.kotlin.whenever + +@RunWith(AndroidJUnit4::class) +class AutoSelectPreferenceControllerTest { + @get:Rule + val composeTestRule = createComposeRule() + + private val mockTelephonyManager = mock { + on { createForSubscriptionId(SUB_ID) } doReturn mock + on { simOperatorName } doReturn OPERATOR_NAME + } + + private val context: Context = spy(ApplicationProvider.getApplicationContext()) { + on { getSystemService(TelephonyManager::class.java) } doReturn mockTelephonyManager + doNothing().whenever(mock).startActivity(any()) + } + + private val preference = ComposePreference(context).apply { key = TEST_KEY } + private val preferenceScreen = PreferenceManager(context).createPreferenceScreen(context) + + private val serviceState = ServiceState() + + private val carrierConfig = persistableBundleOf() + + private val controller = AutoSelectPreferenceController( + context = context, + key = TEST_KEY, + allowedNetworkTypesFlowFactory = { emptyFlow() }, + serviceStateFlowFactory = { flowOf(serviceState) }, + getConfigForSubId = { carrierConfig }, + ).init(subId = SUB_ID) + + @Before + fun setUp() { + preferenceScreen.addPreference(preference) + controller.displayPreference(preferenceScreen) + } + + @Test + fun isChecked_isAutoSelection_on() { + serviceState.isManualSelection = false + + composeTestRule.setContent { + controller.Content() + } + + composeTestRule.onNodeWithText(context.getString(R.string.select_automatically)) + .assertIsOn() + } + + @Test + fun isChecked_isManualSelection_off() { + serviceState.isManualSelection = true + + composeTestRule.setContent { + controller.Content() + } + + composeTestRule.onNodeWithText(context.getString(R.string.select_automatically)) + .assertIsOff() + } + + + @Test + fun isEnabled_isRoaming_enabled() { + serviceState.roaming = true + + composeTestRule.setContent { + controller.Content() + } + + composeTestRule.onNodeWithText(context.getString(R.string.select_automatically)) + .assertIsEnabled() + } + + @Test + fun isEnabled_notOnlyAutoSelectInHome_enabled() { + serviceState.roaming = false + carrierConfig.putBoolean( + CarrierConfigManager.KEY_ONLY_AUTO_SELECT_IN_HOME_NETWORK_BOOL, false + ) + + composeTestRule.setContent { + controller.Content() + } + + composeTestRule.onNodeWithText(context.getString(R.string.select_automatically)) + .assertIsEnabled() + } + + @Test + fun isEnabled_onlyAutoSelectInHome_notEnabled() { + serviceState.roaming = false + carrierConfig.putBoolean( + CarrierConfigManager.KEY_ONLY_AUTO_SELECT_IN_HOME_NETWORK_BOOL, true + ) + + composeTestRule.setContent { + controller.Content() + } + + composeTestRule.onNodeWithText("Unavailable when connected to T-mobile") + .assertIsNotEnabled() + } + + @Test + fun onClick_turnOff_startNetworkSelectActivity() { + serviceState.isManualSelection = false + + composeTestRule.setContent { + controller.Content() + } + composeTestRule.onRoot().performClick() + + val intent = argumentCaptor { + verify(context).startActivity(capture()) + }.firstValue + assertThat(intent.component!!.className).isEqualTo(NetworkSelectActivity::class.java.name) + assertThat(intent.getIntExtra(Settings.EXTRA_SUB_ID, 0)).isEqualTo(SUB_ID) + } + + @Test + fun onClick_turnOn_setNetworkSelectionModeAutomatic() = runBlocking { + serviceState.isManualSelection = true + controller.progressDialog = mock() + + composeTestRule.setContent { + controller.Content() + } + composeTestRule.onRoot().performClick() + delay(100) + + verify(controller.progressDialog!!).show() + verify(mockTelephonyManager).setNetworkSelectionModeAutomatic() + } + + private companion object { + const val TEST_KEY = "test_key" + const val SUB_ID = 2 + const val OPERATOR_NAME = "T-mobile" + } +} diff --git a/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackAdapterTest.java b/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackAdapterTest.java deleted file mode 100644 index ddeb3f81bd9..00000000000 --- a/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackAdapterTest.java +++ /dev/null @@ -1,111 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package com.android.settings.network.helper; - -import static com.google.common.truth.Truth.assertThat; - -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LifecycleOwner; -import androidx.lifecycle.LifecycleRegistry; -import androidx.test.ext.junit.runners.AndroidJUnit4; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; - -@RunWith(AndroidJUnit4.class) -public class LifecycleCallbackAdapterTest implements LifecycleOwner { - - private final LifecycleRegistry mRegistry = LifecycleRegistry.createUnsafe(this); - - private TestObj mTarget; - - @Before - public void setUp() { - mTarget = new TestObj(getLifecycle()); - } - - public Lifecycle getLifecycle() { - return mRegistry; - } - - @Test - public void lifecycle_get_lifecycleToMonitor() { - assertThat(mTarget.getLifecycle()).isEqualTo(mRegistry); - } - - @Test - public void lifecycle_stateChangeToStart_callbackActive() { - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - - assertThat(mTarget.getCallbackCount()).isEqualTo(0); - assertThat(mTarget.isCallbackActive()).isEqualTo(Boolean.FALSE); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - assertThat(mTarget.getCallbackCount()).isEqualTo(1); - assertThat(mTarget.isCallbackActive()).isEqualTo(Boolean.TRUE); - } - - @Test - public void lifecycle_stateChangeToStop_callbackInActive() { - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_STOP); - - assertThat(mTarget.getCallbackCount()).isEqualTo(2); - assertThat(mTarget.isCallbackActive()).isEqualTo(Boolean.FALSE); - } - - @Test - public void lifecycle_stateChangeToDestroy_noFurtherActive() { - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_STOP); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_DESTROY); - - assertThat(mTarget.getCallbackCount()).isEqualTo(2); - assertThat(mTarget.isCallbackActive()).isEqualTo(Boolean.FALSE); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - assertThat(mTarget.getCallbackCount()).isEqualTo(2); - assertThat(mTarget.isCallbackActive()).isEqualTo(Boolean.FALSE); - } - - public static class TestObj extends LifecycleCallbackAdapter { - boolean mIsActive; - int mNumberOfCallback; - - public TestObj(Lifecycle lifecycle) { - super(lifecycle); - } - - public boolean isCallbackActive() { - return mIsActive; - } - - public void setCallbackActive(boolean isActive) { - mIsActive = isActive; - mNumberOfCallback ++; - } - - protected int getCallbackCount() { - return mNumberOfCallback; - } - } -} diff --git a/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackConverterTest.java b/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackConverterTest.java deleted file mode 100644 index 22377469c22..00000000000 --- a/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackConverterTest.java +++ /dev/null @@ -1,127 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package com.android.settings.network.helper; - -import static com.google.common.truth.Truth.assertThat; - -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LifecycleOwner; -import androidx.lifecycle.LifecycleRegistry; -import androidx.test.ext.junit.runners.AndroidJUnit4; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; - -import java.util.concurrent.Phaser; -import java.util.concurrent.atomic.AtomicReference; -import java.util.function.Consumer; - -@RunWith(AndroidJUnit4.class) -public class LifecycleCallbackConverterTest implements LifecycleOwner { - - private final LifecycleRegistry mRegistry = LifecycleRegistry.createUnsafe(this); - - private Object mTestData; - private TestConsumer mConsumer; - private LifecycleCallbackConverter mConverter; - - @Before - public void setUp() { - mTestData = new Object(); - mConsumer = new TestConsumer(); - } - - private void initEnvPerTestCase() { - mConverter = new LifecycleCallbackConverter(getLifecycle(), mConsumer); - } - - public Lifecycle getLifecycle() { - return mRegistry; - } - - @Test - public void converter_dropResult_whenInActive() { - initEnvPerTestCase(); - mConverter.postResult(mTestData); - - assertThat(mConsumer.getCallbackCount()).isEqualTo(0); - } - - @Test - public void converter_callbackResult_whenActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - mConverter.postResult(mTestData); - assertThat(mConsumer.getCallbackCount()).isEqualTo(1); - assertThat(mConsumer.getData()).isEqualTo(mTestData); - } - - @Test - public void converter_dropResult_whenBackToInActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_STOP); - - mConverter.postResult(mTestData); - assertThat(mConsumer.getCallbackCount()).isEqualTo(0); - } - - @Test - public void converter_passResultToUiThread_whenActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - final Phaser phaser = new Phaser(1); - Thread executionThread = new Thread(() -> { - mConverter.postResult(phaser); - }); - executionThread.start(); - phaser.awaitAdvance(0); - - assertThat(mConsumer.getData()).isEqualTo(phaser); - assertThat(mConsumer.getCallbackCount()).isEqualTo(1); - } - - public static class TestConsumer implements Consumer { - long mNumberOfCallback; - AtomicReference mLatestData; - - public TestConsumer() { - mLatestData = new AtomicReference(); - } - - public void accept(Object data) { - mLatestData.set(data); - mNumberOfCallback ++; - if ((data != null) && (data instanceof Phaser)) { - ((Phaser)data).arrive(); - } - } - - protected long getCallbackCount() { - return mNumberOfCallback; - } - - protected Object getData() { - return mLatestData.get(); - } - } -} diff --git a/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackIntentReceiverTest.java b/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackIntentReceiverTest.java deleted file mode 100644 index 780ee55e93a..00000000000 --- a/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackIntentReceiverTest.java +++ /dev/null @@ -1,190 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package com.android.settings.network.helper; - -import static com.google.common.truth.Truth.assertThat; - -import android.content.Context; -import android.content.Intent; -import android.content.IntentFilter; -import android.os.Handler; -import android.os.HandlerThread; - -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LifecycleOwner; -import androidx.lifecycle.LifecycleRegistry; -import androidx.test.core.app.ApplicationProvider; -import androidx.test.ext.junit.runners.AndroidJUnit4; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; - -import java.util.function.Consumer; - -@RunWith(AndroidJUnit4.class) -public class LifecycleCallbackIntentReceiverTest implements LifecycleOwner { - - private final LifecycleRegistry mRegistry = LifecycleRegistry.createUnsafe(this); - - private static final String TEST_SCHEDULER_HANDLER = "testScheduler"; - private static final String TEST_INTENT_ACTION = "testAction"; - private static final String TEST_INTENT_PERMISSION = "testPermission"; - - private Context mContext; - private Intent mIntent; - private IntentFilter mIntentFilter; - private Handler mHandler; - private TestConsumer mConsumer; - - private TestObj mTarget; - - @Before - public void setUp() { - mContext = ApplicationProvider.getApplicationContext(); - - mIntentFilter = new IntentFilter(TEST_INTENT_ACTION); - mIntent = new Intent(TEST_INTENT_ACTION); - - HandlerThread thread = new HandlerThread(TEST_SCHEDULER_HANDLER); - thread.start(); - - mHandler = new Handler(thread.getLooper()); - mConsumer = new TestConsumer(); - } - - public Lifecycle getLifecycle() { - return mRegistry; - } - - private void initEnvPerTestCase() { - mTarget = new TestObj(getLifecycle(), mContext, - mIntentFilter, TEST_INTENT_PERMISSION, - mHandler, mConsumer); - } - - @Test - public void receiver_register_whenActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - - assertThat(mTarget.getCallbackActiveCount(true) - + mTarget.getCallbackActiveCount(false)).isEqualTo(0); - - mTarget.mReceiver.onReceive(mContext, mIntent); - - assertThat(mConsumer.getCallbackCount()).isEqualTo(0); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - assertThat(mTarget.getCallbackActiveCount(true)).isEqualTo(1); - assertThat(mConsumer.getCallbackCount()).isEqualTo(0); - - mTarget.mReceiver.onReceive(mContext, mIntent); - - assertThat(mConsumer.getCallbackCount()).isEqualTo(1); - assertThat(mConsumer.getData()).isEqualTo(mIntent); - } - - @Test - public void receiver_unregister_whenInActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_STOP); - - assertThat(mTarget.getCallbackActiveCount(false)).isEqualTo(1); - - mTarget.mReceiver.onReceive(mContext, mIntent); - - assertThat(mConsumer.getCallbackCount()).isEqualTo(0); - } - - @Test - public void receiver_register_whenReActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_STOP); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - assertThat(mTarget.getCallbackActiveCount(true)).isEqualTo(2); - - mTarget.mReceiver.onReceive(mContext, mIntent); - - assertThat(mConsumer.getCallbackCount()).isEqualTo(1); - assertThat(mConsumer.getData()).isEqualTo(mIntent); - } - - @Test - public void receiver_close_whenDestroy() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_STOP); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_DESTROY); - - assertThat(mTarget.getCallbackActiveCount(false)).isEqualTo(1); - - mTarget.mReceiver.onReceive(mContext, mIntent); - - assertThat(mConsumer.getCallbackCount()).isEqualTo(0); - } - - public static class TestConsumer implements Consumer { - long mNumberOfCallback; - Intent mLatestData; - - public TestConsumer() {} - - public void accept(Intent data) { - mLatestData = data; - mNumberOfCallback ++; - } - - protected long getCallbackCount() { - return mNumberOfCallback; - } - - protected Intent getData() { - return mLatestData; - } - } - - public static class TestObj extends LifecycleCallbackIntentReceiver { - long mCallbackActiveCount; - long mCallbackInActiveCount; - - public TestObj(Lifecycle lifecycle, Context context, IntentFilter filter, - String broadcastPermission, Handler scheduler, Consumer resultCallback) { - super(lifecycle, context, filter, broadcastPermission, scheduler, resultCallback); - } - - @Override - public void setCallbackActive(boolean isActive) { - if (isActive) { - mCallbackActiveCount ++; - } else { - mCallbackInActiveCount ++; - } - super.setCallbackActive(isActive); - } - - protected long getCallbackActiveCount(boolean forActive) { - return forActive ? mCallbackActiveCount : mCallbackInActiveCount; - } - } -} diff --git a/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackTelephonyAdapterTest.java b/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackTelephonyAdapterTest.java deleted file mode 100644 index 3968a03cf88..00000000000 --- a/tests/unit/src/com/android/settings/network/helper/LifecycleCallbackTelephonyAdapterTest.java +++ /dev/null @@ -1,109 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package com.android.settings.network.helper; - -import static org.mockito.ArgumentMatchers.anyObject; -import static org.mockito.Mockito.doNothing; -import static org.mockito.Mockito.never; -import static org.mockito.Mockito.times; -import static org.mockito.Mockito.verify; - -import android.telephony.TelephonyCallback; -import android.telephony.TelephonyManager; - -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LifecycleOwner; -import androidx.lifecycle.LifecycleRegistry; -import androidx.test.ext.junit.runners.AndroidJUnit4; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.mockito.Mock; -import org.mockito.MockitoAnnotations; - -import java.util.concurrent.atomic.AtomicReference; - -@RunWith(AndroidJUnit4.class) -public class LifecycleCallbackTelephonyAdapterTest implements LifecycleOwner { - - private final LifecycleRegistry mRegistry = LifecycleRegistry.createUnsafe(this); - - @Mock - private TelephonyManager mTelMgr; - - private TestCallback mTestCallback; - private AtomicReference mResult; - private LifecycleCallbackTelephonyAdapter mAdapter; - - @Before - public void setUp() { - MockitoAnnotations.initMocks(this); - - mResult = new AtomicReference(); - mTestCallback = new TestCallback(); - - doNothing().when(mTelMgr).registerTelephonyCallback(null, mTestCallback); - doNothing().when(mTelMgr).unregisterTelephonyCallback(mTestCallback); - } - - public Lifecycle getLifecycle() { - return mRegistry; - } - - private void initEnvPerTestCase() { - mAdapter = new LifecycleCallbackTelephonyAdapter(getLifecycle(), mTelMgr, - mTestCallback, null, result -> mResult.set(result)); - } - - @Test - public void telephonyCallback_register_whenActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - - verify(mTelMgr, never()).registerTelephonyCallback(anyObject(), anyObject()); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - verify(mTelMgr).registerTelephonyCallback(anyObject(), anyObject()); - } - - @Test - public void telephonyCallback_unregister_whenInActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - - verify(mTelMgr, never()).unregisterTelephonyCallback(anyObject()); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - verify(mTelMgr, never()).unregisterTelephonyCallback(anyObject()); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_STOP); - - verify(mTelMgr).unregisterTelephonyCallback(anyObject()); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_DESTROY); - - verify(mTelMgr, times(1)).unregisterTelephonyCallback(anyObject()); - } - - protected static class TestCallback extends TelephonyCallback - implements TelephonyCallback.CallStateListener { - @Override - public void onCallStateChanged(int state) {} - } -} diff --git a/tests/unit/src/com/android/settings/network/helper/ServiceStateStatusTest.java b/tests/unit/src/com/android/settings/network/helper/ServiceStateStatusTest.java deleted file mode 100644 index 133c338e184..00000000000 --- a/tests/unit/src/com/android/settings/network/helper/ServiceStateStatusTest.java +++ /dev/null @@ -1,99 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package com.android.settings.network.helper; - -import static com.google.common.truth.Truth.assertThat; - -import android.telephony.ServiceState; -import android.telephony.TelephonyManager; - -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LifecycleOwner; -import androidx.lifecycle.LifecycleRegistry; -import androidx.test.ext.junit.runners.AndroidJUnit4; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.mockito.Mock; -import org.mockito.MockitoAnnotations; - -import java.util.concurrent.atomic.AtomicReference; - -@RunWith(AndroidJUnit4.class) -public class ServiceStateStatusTest implements LifecycleOwner { - - private final LifecycleRegistry mRegistry = LifecycleRegistry.createUnsafe(this); - - @Mock - private TelephonyManager mTelMgr; - @Mock - private ServiceState mTestData; - - private AtomicReference mStatusStorage; - private ServiceStateStatus mServiceStateStatus; - - @Before - public void setUp() { - MockitoAnnotations.initMocks(this); - - mStatusStorage = new AtomicReference(); - } - - private void initEnvPerTestCase() { - mServiceStateStatus = new ServiceStateStatus(getLifecycle(), mTelMgr, null) { - @Override - protected void setValue(ServiceState status) { - mStatusStorage.set(status); - } - }; - } - - public Lifecycle getLifecycle() { - return mRegistry; - } - - @Test - public void telephonyCallback_updateStatus_whenActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - - mServiceStateStatus.mServiceStateProducer.onServiceStateChanged(mTestData); - - assertThat(mStatusStorage.get()).isEqualTo(null); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - mServiceStateStatus.mServiceStateProducer.onServiceStateChanged(mTestData); - - assertThat(mStatusStorage.get()).isEqualTo(mTestData); - } - - @Test - public void telephonyCallback_updateStatusToNull_whenInActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - mServiceStateStatus.mServiceStateProducer.onServiceStateChanged(mTestData); - - assertThat(mStatusStorage.get()).isEqualTo(mTestData); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_STOP); - - assertThat(mStatusStorage.get()).isEqualTo(null); - } -} diff --git a/tests/unit/src/com/android/settings/network/helper/VoiceCallStatusTest.java b/tests/unit/src/com/android/settings/network/helper/VoiceCallStatusTest.java deleted file mode 100644 index dd4e28a31cf..00000000000 --- a/tests/unit/src/com/android/settings/network/helper/VoiceCallStatusTest.java +++ /dev/null @@ -1,100 +0,0 @@ -/* - * Copyright (C) 2022 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package com.android.settings.network.helper; - -import static com.google.common.truth.Truth.assertThat; - -import android.telephony.TelephonyManager; - -import androidx.lifecycle.Lifecycle; -import androidx.lifecycle.LifecycleOwner; -import androidx.lifecycle.LifecycleRegistry; -import androidx.test.ext.junit.runners.AndroidJUnit4; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.mockito.Mock; -import org.mockito.MockitoAnnotations; - -import java.util.concurrent.atomic.AtomicReference; - -@RunWith(AndroidJUnit4.class) -public class VoiceCallStatusTest implements LifecycleOwner { - - private final LifecycleRegistry mRegistry = LifecycleRegistry.createUnsafe(this); - - @Mock - private TelephonyManager mTelMgr; - - private AtomicReference mStatusStorage; - private VoiceCallStatus mVoiceCallStatus; - - @Before - public void setUp() { - MockitoAnnotations.initMocks(this); - - mStatusStorage = new AtomicReference(); - } - - private void initEnvPerTestCase() { - mVoiceCallStatus = new VoiceCallStatus(getLifecycle(), mTelMgr, null) { - //ArchTaskExecutor.getMainThreadExecutor()) { - @Override - protected void setValue(Integer status) { - mStatusStorage.set(status); - } - }; - } - - public Lifecycle getLifecycle() { - return mRegistry; - } - - @Test - public void telephonyCallback_updateStatus_whenActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - - mVoiceCallStatus.mCallStateProducer.onCallStateChanged( - TelephonyManager.CALL_STATE_RINGING); - - assertThat(mStatusStorage.get()).isEqualTo(null); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - mVoiceCallStatus.mCallStateProducer.onCallStateChanged( - TelephonyManager.CALL_STATE_OFFHOOK); - - assertThat(mStatusStorage.get()).isEqualTo(TelephonyManager.CALL_STATE_OFFHOOK); - } - - @Test - public void telephonyCallback_updateStatusToNull_whenInActive() { - initEnvPerTestCase(); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_CREATE); - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_START); - - mVoiceCallStatus.mCallStateProducer.onCallStateChanged( - TelephonyManager.CALL_STATE_OFFHOOK); - - assertThat(mStatusStorage.get()).isEqualTo(TelephonyManager.CALL_STATE_OFFHOOK); - - mRegistry.handleLifecycleEvent(Lifecycle.Event.ON_STOP); - - assertThat(mStatusStorage.get()).isEqualTo(null); - } -} diff --git a/tests/unit/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceControllerTest.java b/tests/unit/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceControllerTest.java deleted file mode 100644 index 39f2050b7f7..00000000000 --- a/tests/unit/src/com/android/settings/network/telephony/gsm/AutoSelectPreferenceControllerTest.java +++ /dev/null @@ -1,186 +0,0 @@ -/* - * Copyright (C) 2020 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.settings.network.telephony.gsm; - -import static com.google.common.truth.Truth.assertThat; - -import static org.junit.Assert.fail; -import static org.mockito.Mockito.doReturn; -import static org.mockito.Mockito.spy; -import static org.mockito.Mockito.verify; -import static org.mockito.Mockito.when; - -import android.app.ProgressDialog; -import android.content.Context; -import android.os.PersistableBundle; -import android.telephony.CarrierConfigManager; -import android.telephony.ServiceState; -import android.telephony.SubscriptionManager; -import android.telephony.TelephonyManager; - -import androidx.lifecycle.Lifecycle; -import androidx.preference.SwitchPreference; -import androidx.test.core.app.ApplicationProvider; -import androidx.test.ext.junit.runners.AndroidJUnit4; - -import com.android.settings.network.CarrierConfigCache; -import com.android.settings.testutils.ResourcesUtils; - -import org.junit.Before; -import org.junit.Test; -import org.junit.runner.RunWith; -import org.mockito.Answers; -import org.mockito.Mock; -import org.mockito.MockitoAnnotations; - -import java.util.concurrent.ExecutionException; -import java.util.concurrent.Future; - -@RunWith(AndroidJUnit4.class) -public class AutoSelectPreferenceControllerTest { - private static final int SUB_ID = 2; - private static final String OPERATOR_NAME = "T-mobile"; - - @Mock(answer = Answers.RETURNS_DEEP_STUBS) - private TelephonyManager mTelephonyManager; - @Mock - private SubscriptionManager mSubscriptionManager; - @Mock - private CarrierConfigCache mCarrierConfigCache; - @Mock - private ProgressDialog mProgressDialog; - @Mock - private ServiceState mTestServiceState; - @Mock - private Lifecycle mLifecycle; - - private PersistableBundle mCarrierConfig; - private AutoSelectPreferenceController mController; - private SwitchPreference mSwitchPreference; - private Context mContext; - - - @Before - public void setUp() { - MockitoAnnotations.initMocks(this); - - mContext = spy(ApplicationProvider.getApplicationContext()); - - when(mContext.getSystemService(TelephonyManager.class)).thenReturn(mTelephonyManager); - when(mContext.getSystemService(SubscriptionManager.class)).thenReturn(mSubscriptionManager); - CarrierConfigCache.setTestInstance(mContext, mCarrierConfigCache); - when(mTelephonyManager.createForSubscriptionId(SUB_ID)).thenReturn(mTelephonyManager); - - mCarrierConfig = new PersistableBundle(); - mCarrierConfig.putBoolean(CarrierConfigManager.KEY_ONLY_AUTO_SELECT_IN_HOME_NETWORK_BOOL, - true); - when(mCarrierConfigCache.getConfigForSubId(SUB_ID)).thenReturn(mCarrierConfig); - - mSwitchPreference = new SwitchPreference(mContext); - mController = new AutoSelectPreferenceController(mContext, "auto_select"); - mController.mProgressDialog = mProgressDialog; - mController.mSwitchPreference = mSwitchPreference; - mController.init(mLifecycle, SUB_ID); - sleepAfterInit(); - } - - private void sleepAfterInit() { - try { - Thread.sleep(2000); - } catch (Exception e) { - fail("Sleep timeout " + e); - } - } - - @Test - public void setChecked_isChecked_showProgressDialog() { - when(mTelephonyManager.getNetworkSelectionMode()).thenReturn( - TelephonyManager.NETWORK_SELECTION_MODE_AUTO); - - // Wait for asynchronous thread to finish, otherwise test will flake. - Future thread = mController.setAutomaticSelectionMode(); - try { - thread.get(); - } catch (ExecutionException | InterruptedException e) { - e.printStackTrace(); - fail("Exception during automatic selection"); - } - - verify(mProgressDialog).show(); - verify(mTelephonyManager).setNetworkSelectionModeAutomatic(); - } - - @Test - public void updateState_isRoaming_enabled() { - when(mTelephonyManager.getServiceState()).thenReturn(mTestServiceState); - when(mTestServiceState.getRoaming()).thenReturn(true); - - mController.updateState(mSwitchPreference); - - assertThat(mSwitchPreference.isEnabled()).isTrue(); - } - - @Test - public void updateState_notRoamingWithAutoSelectOn_disabled() { - when(mTelephonyManager.getServiceState()).thenReturn(mTestServiceState); - when(mTestServiceState.getRoaming()).thenReturn(false); - doReturn(OPERATOR_NAME).when(mTelephonyManager).getSimOperatorName(); - - mController.updateState(mSwitchPreference); - - assertThat(mSwitchPreference.isEnabled()).isFalse(); - assertThat(mSwitchPreference.getSummary()).isEqualTo( - ResourcesUtils.getResourcesString(mContext, "manual_mode_disallowed_summary", - mTelephonyManager.getSimOperatorName())); - } - - @Test - public void init_carrierConfigNull_shouldNotCrash() { - when(mCarrierConfigCache.getConfigForSubId(SUB_ID)).thenReturn(null); - - // Should not crash - mController.init(mLifecycle, SUB_ID); - } - - @Test - public void updateUiAutoSelectValue_serviceStateGetIsManualSelection_isCheckedFalse() { - when(mTelephonyManager.getNetworkSelectionMode()).thenReturn( - TelephonyManager.NETWORK_SELECTION_MODE_AUTO); - when(mTestServiceState.getIsManualSelection()).thenReturn(true); - mController.init(mLifecycle, SUB_ID); - sleepAfterInit(); - - mController.updateUiAutoSelectValue(mTestServiceState); - - assertThat(mController.isChecked()).isFalse(); - assertThat(mSwitchPreference.isChecked()).isFalse(); - } - - @Test - public void updateUiAutoSelectValue_serviceStateGetIsAutoSelection_isCheckedTrue() { - when(mTelephonyManager.getNetworkSelectionMode()).thenReturn( - TelephonyManager.NETWORK_SELECTION_MODE_MANUAL); - when(mTestServiceState.getIsManualSelection()).thenReturn(false); - mController.init(mLifecycle, SUB_ID); - sleepAfterInit(); - - mController.updateUiAutoSelectValue(mTestServiceState); - - assertThat(mController.isChecked()).isTrue(); - assertThat(mSwitchPreference.isChecked()).isTrue(); - } -}