Fix provision failure behavior
Test: atest DeviceLockControllerRoboTests
Fix: 296578494
Change-Id: Ieac79c87a51490eab0e4a8f8a41a9392c9dd0bf7
diff --git a/DeviceLockController/res/layout/fragment_device_policies.xml b/DeviceLockController/res/layout/fragment_device_policies.xml
index e80bb36..bd457fa 100644
--- a/DeviceLockController/res/layout/fragment_device_policies.xml
+++ b/DeviceLockController/res/layout/fragment_device_policies.xml
@@ -77,6 +77,7 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/next"
+ android:visibility="gone"
app:layout_constraintTop_toTopOf="parent"
app:layout_constraintEnd_toEndOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
diff --git a/DeviceLockController/res/layout/fragment_provision_info.xml b/DeviceLockController/res/layout/fragment_provision_info.xml
index 459ea80..c9ac059 100644
--- a/DeviceLockController/res/layout/fragment_provision_info.xml
+++ b/DeviceLockController/res/layout/fragment_provision_info.xml
@@ -85,6 +85,7 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/previous"
+ android:visibility="gone"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintStart_toStartOf="parent" />
<Button
@@ -92,6 +93,7 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/next"
+ android:visibility="gone"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/AbstractDeviceLockControllerScheduler.java b/DeviceLockController/src/com/android/devicelockcontroller/AbstractDeviceLockControllerScheduler.java
index d616d09..e85b5dd 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/AbstractDeviceLockControllerScheduler.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/AbstractDeviceLockControllerScheduler.java
@@ -68,9 +68,9 @@
public abstract void scheduleResetDeviceAlarm();
/**
- * Schedule an alarm to factory reset the device with a given delay.
+ * Schedule an alarm to factory reset the device in case of mandatory provision is failed.
*/
- public abstract void scheduleResetDeviceAlarm(Duration delay);
+ public abstract void scheduleMandatoryResetDeviceAlarm();
/** Reschedule the reset device alarm if needed */
public abstract void rescheduleResetDeviceAlarmIfNeeded();
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/DeviceLockControllerScheduler.java b/DeviceLockController/src/com/android/devicelockcontroller/DeviceLockControllerScheduler.java
index 59540e3..582b9af 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/DeviceLockControllerScheduler.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/DeviceLockControllerScheduler.java
@@ -244,7 +244,17 @@
}
@Override
- public void scheduleResetDeviceAlarm(Duration delay) {
+ public void scheduleMandatoryResetDeviceAlarm() {
+ Duration delay = Duration.ofMinutes(RESET_DEVICE_IN_TWO_MINUTES);
+ if (Build.isDebuggable()) {
+ delay = Duration.ofMinutes(
+ SystemProperties.getInt("devicelock.provision.reset-device-minutes",
+ RESET_DEVICE_IN_TWO_MINUTES));
+ }
+ scheduleResetDeviceAlarm(delay);
+ }
+
+ private void scheduleResetDeviceAlarm(Duration delay) {
scheduleResetDeviceAlarmInternal(delay);
Instant whenExpectedToRun = Instant.now(mClock).plus(delay);
DeviceLockNotificationManager.sendDeviceResetTimerNotification(mContext,
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceFinancingDeferredProvisionInfoViewModel.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceFinancingDeferredProvisionInfoViewModel.java
deleted file mode 100644
index d7aae6a..0000000
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceFinancingDeferredProvisionInfoViewModel.java
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * 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.devicelockcontroller.activities;
-
-import android.annotation.NonNull;
-import android.app.Application;
-
-import com.android.devicelockcontroller.R;
-
-import java.util.ArrayList;
-import java.util.List;
-
-
-/**
- * This class provides resources and data used for the deferred provisioning flow of the device
- * financing use case.
- */
-public final class DeviceFinancingDeferredProvisionInfoViewModel extends ProvisionInfoViewModel {
-
- private static final int HEADER_DRAWABLE_ID = R.drawable.ic_info_24px;
-
- private static final int HEADER_TEXT_ID = R.string.enroll_your_device_header;
-
- private static final int SUBHEADER_TEXT_ID = R.string.enroll_your_device_financing_subheader;
-
- private static final Integer[] DRAWABLE_IDS = new Integer[]{
- R.drawable.ic_file_download_24px, R.drawable.ic_lock_outline_24px,
- };
-
- private static final Integer[] TEXT_IDS = new Integer[]{
- R.string.download_kiosk_app, R.string.restrict_device_if_missing_payment,
- };
-
- public DeviceFinancingDeferredProvisionInfoViewModel(@NonNull Application application) {
- super(application);
-
- mHeaderDrawableId = HEADER_DRAWABLE_ID;
- mHeaderTextId = HEADER_TEXT_ID;
- mSubHeaderTextId = SUBHEADER_TEXT_ID;
- List<ProvisionInfo> provisionInfoList = new ArrayList<>();
- for (int i = 0, size = DRAWABLE_IDS.length; i < size; ++i) {
- provisionInfoList.add(new ProvisionInfo(DRAWABLE_IDS[i], TEXT_IDS[i]));
- }
- mProvisionInfoList = provisionInfoList;
- }
-}
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceFinancingProvisionInfoViewModel.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceFinancingProvisionInfoViewModel.java
index fd53afe..52883e8 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceFinancingProvisionInfoViewModel.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceFinancingProvisionInfoViewModel.java
@@ -31,7 +31,7 @@
private static final int HEADER_DRAWABLE_ID = R.drawable.ic_info_24px;
- private static final int HEADER_TEXT_ID = R.string.device_provided_by_provider;
+ private static final int MANDATORY_HEADER_TEXT_ID = R.string.device_provided_by_provider;
private static final Integer[] DRAWABLE_IDS = new Integer[]{
R.drawable.ic_file_download_24px, R.drawable.ic_lock_outline_24px,
@@ -41,11 +41,18 @@
R.string.download_kiosk_app, R.string.restrict_device_if_missing_payment,
};
+ private static final int HEADER_TEXT_ID = R.string.enroll_your_device_header;
+
+ private static final int SUBHEADER_TEXT_ID =
+ R.string.enroll_your_device_financing_subheader;
+
public DeviceFinancingProvisionInfoViewModel(@NonNull Application application) {
super(application);
mHeaderDrawableId = HEADER_DRAWABLE_ID;
+ mMandatoryHeaderTextId = MANDATORY_HEADER_TEXT_ID;
mHeaderTextId = HEADER_TEXT_ID;
+ mSubHeaderTextId = SUBHEADER_TEXT_ID;
List<ProvisionInfo> provisionInfoList = new ArrayList<>();
for (int i = 0, size = DRAWABLE_IDS.length; i < size; ++i) {
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/DevicePoliciesFragment.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/DevicePoliciesFragment.java
index 66f0039..783f9f3 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/DevicePoliciesFragment.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/activities/DevicePoliciesFragment.java
@@ -92,8 +92,13 @@
new ViewModelProvider(requireActivity()).get(ProvisioningProgressViewModel.class);
Button button = view.findViewById(R.id.button_next);
checkNotNull(button);
- button.setOnClickListener(
- v -> provisionHelper.scheduleKioskAppInstallation(requireActivity(),
- provisioningProgressViewModel));
+ viewModel.getIsMandatoryLiveData().observe(this,
+ isMandatory -> {
+ button.setOnClickListener(
+ v -> provisionHelper.scheduleKioskAppInstallation(requireActivity(),
+ provisioningProgressViewModel,
+ isMandatory));
+ button.setVisibility(View.VISIBLE);
+ });
}
}
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/DevicePoliciesViewModel.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/DevicePoliciesViewModel.java
index 88ca681..03ccee4 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/DevicePoliciesViewModel.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/activities/DevicePoliciesViewModel.java
@@ -16,6 +16,7 @@
package com.android.devicelockcontroller.activities;
+import androidx.lifecycle.LiveData;
import androidx.lifecycle.MediatorLiveData;
import androidx.lifecycle.MutableLiveData;
import androidx.lifecycle.ViewModel;
@@ -83,6 +84,12 @@
final MutableLiveData<String> mProviderNameLiveData;
final MediatorLiveData<List<DevicePolicyGroup>> mDevicePolicyGroupListLiveData;
+ public LiveData<Boolean> getIsMandatoryLiveData() {
+ return mIsMandatoryLiveData;
+ }
+
+ private final MutableLiveData<Boolean> mIsMandatoryLiveData = new MutableLiveData<>();
+
public DevicePoliciesViewModel() {
mProviderNameLiveData = new MutableLiveData<>();
Futures.addCallback(SetupParametersClient.getInstance().getKioskAppProviderName(),
@@ -97,6 +104,19 @@
LogUtil.e(TAG, "Failed to get Device Provider name!", t);
}
}, MoreExecutors.directExecutor());
+
+ Futures.addCallback(SetupParametersClient.getInstance().isProvisionMandatory(),
+ new FutureCallback<>() {
+ @Override
+ public void onSuccess(Boolean result) {
+ mIsMandatoryLiveData.postValue(result);
+ }
+
+ @Override
+ public void onFailure(Throwable t) {
+ LogUtil.e(TAG, "Failed to know if provision is mandatory!", t);
+ }
+ }, MoreExecutors.directExecutor());
mDevicePolicyGroupListLiveData = new MediatorLiveData<>();
mDevicePolicyGroupListLiveData.addSource(mProviderNameLiveData,
unused -> mDevicePolicyGroupListLiveData.setValue(DEVICE_POLICY_GROUPS));
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceSubsidyDeferredProvisionInfoViewModel.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceSubsidyDeferredProvisionInfoViewModel.java
deleted file mode 100644
index eb12e62..0000000
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceSubsidyDeferredProvisionInfoViewModel.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * 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.devicelockcontroller.activities;
-
-import android.annotation.NonNull;
-import android.app.Application;
-
-import com.android.devicelockcontroller.R;
-
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * This class provides resources and data used for the deferred provisioning flow of the device
- * subsidy use case.
- */
-public final class DeviceSubsidyDeferredProvisionInfoViewModel extends ProvisionInfoViewModel {
-
- private static final int HEADER_DRAWABLE_ID = R.drawable.ic_info_24px;
-
- private static final int HEADER_TEXT_ID = R.string.enroll_your_device_header;
-
- private static final int SUBHEADER_TEXT_ID = R.string.enroll_your_device_subsidy_subheader;
-
- private static final Integer[] DRAWABLE_IDS = new Integer[]{
- R.drawable.ic_file_download_24px, R.drawable.ic_lock_outline_24px,
- };
-
- private static final Integer[] TEXT_IDS = new Integer[]{
- R.string.download_kiosk_app, R.string.restrict_device_if_dont_make_payment,
- };
-
- public DeviceSubsidyDeferredProvisionInfoViewModel(@NonNull Application application) {
- super(application);
-
- mHeaderDrawableId = HEADER_DRAWABLE_ID;
- mHeaderTextId = HEADER_TEXT_ID;
- mSubHeaderTextId = SUBHEADER_TEXT_ID;
- List<ProvisionInfo> provisionInfoList = new ArrayList<>();
- for (int i = 0, size = DRAWABLE_IDS.length; i < size; ++i) {
- provisionInfoList.add(new ProvisionInfo(DRAWABLE_IDS[i], TEXT_IDS[i]));
- }
- mProvisionInfoList = provisionInfoList;
- }
-}
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceSubsidyProvisionInfoViewModel.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceSubsidyProvisionInfoViewModel.java
index 66c49ed..0a91921 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceSubsidyProvisionInfoViewModel.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/activities/DeviceSubsidyProvisionInfoViewModel.java
@@ -31,7 +31,7 @@
private static final int HEADER_DRAWABLE_ID = R.drawable.ic_info_24px;
- private static final int HEADER_TEXT_ID = R.string.subsidy_program_header;
+ private static final int MANDATORY_HEADER_TEXT_ID = R.string.subsidy_program_header;
private static final Integer[] DRAWABLE_IDS = new Integer[]{
R.drawable.ic_file_download_24px, R.drawable.ic_lock_outline_24px,
@@ -41,11 +41,17 @@
R.string.download_kiosk_app, R.string.restrict_device_if_dont_make_payment,
};
+ private static final int HEADER_TEXT_ID = R.string.enroll_your_device_header;
+
+ private static final int SUBHEADER_TEXT_ID = R.string.enroll_your_device_subsidy_subheader;
+
public DeviceSubsidyProvisionInfoViewModel(@NonNull Application application) {
super(application);
mHeaderDrawableId = HEADER_DRAWABLE_ID;
+ mMandatoryHeaderTextId = MANDATORY_HEADER_TEXT_ID;
mHeaderTextId = HEADER_TEXT_ID;
+ mSubHeaderTextId = SUBHEADER_TEXT_ID;
List<ProvisionInfo> provisionInfoList = new ArrayList<>();
for (int i = 0, size = DRAWABLE_IDS.length; i < size; ++i) {
provisionInfoList.add(new ProvisionInfo(DRAWABLE_IDS[i], TEXT_IDS[i]));
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/LandingActivity.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/LandingActivity.java
index 71acf35..2a59a49 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/LandingActivity.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/activities/LandingActivity.java
@@ -22,7 +22,6 @@
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
-import androidx.fragment.app.Fragment;
import com.android.devicelockcontroller.R;
@@ -41,10 +40,9 @@
controller.hide(WindowInsets.Type.systemBars());
}
if (savedInstanceState == null) {
- Fragment fragment = new ProvisionInfoFragment();
getSupportFragmentManager()
.beginTransaction()
- .add(R.id.fragment_container, fragment)
+ .add(R.id.fragment_container, new ProvisionInfoFragment())
.commit();
}
}
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/ProgressFragment.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/ProgressFragment.java
index 380ba2c..0eb21e7 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/ProgressFragment.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/activities/ProgressFragment.java
@@ -109,7 +109,8 @@
retryButton.setOnClickListener(
view -> provisionHelper.scheduleKioskAppInstallation(
requireActivity(),
- provisioningProgressViewModel));
+ provisioningProgressViewModel,
+ /* isProvisionMandatory= */ false));
Button exitButton = bottomView.findViewById(R.id.button_exit);
checkNotNull(exitButton);
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisionInfoFragment.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisionInfoFragment.java
index c8fc26c..9ad7f36 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisionInfoFragment.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisionInfoFragment.java
@@ -16,10 +16,8 @@
package com.android.devicelockcontroller.activities;
-import static com.android.devicelockcontroller.common.DeviceLockConstants.ACTION_START_DEVICE_FINANCING_DEFERRED_PROVISIONING;
import static com.android.devicelockcontroller.common.DeviceLockConstants.ACTION_START_DEVICE_FINANCING_PROVISIONING;
import static com.android.devicelockcontroller.common.DeviceLockConstants.ACTION_START_DEVICE_FINANCING_SECONDARY_USER_PROVISIONING;
-import static com.android.devicelockcontroller.common.DeviceLockConstants.ACTION_START_DEVICE_SUBSIDY_DEFERRED_PROVISIONING;
import static com.android.devicelockcontroller.common.DeviceLockConstants.ACTION_START_DEVICE_SUBSIDY_PROVISIONING;
import static com.google.common.base.Preconditions.checkNotNull;
@@ -75,29 +73,17 @@
public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
ProvisionInfoViewModel viewModel;
- boolean isDeferredProvisioning = false;
+ ViewModelProvider viewModelProvider = new ViewModelProvider(this);
switch (Objects.requireNonNull(getActivity()).getIntent().getAction()) {
case ACTION_START_DEVICE_FINANCING_PROVISIONING:
- viewModel = new ViewModelProvider(this).get(
- DeviceFinancingProvisionInfoViewModel.class);
- break;
- case ACTION_START_DEVICE_FINANCING_DEFERRED_PROVISIONING:
- viewModel = new ViewModelProvider(this).get(
- DeviceFinancingDeferredProvisionInfoViewModel.class);
- isDeferredProvisioning = true;
+ viewModel = viewModelProvider.get(DeviceFinancingProvisionInfoViewModel.class);
break;
case ACTION_START_DEVICE_FINANCING_SECONDARY_USER_PROVISIONING:
- viewModel = new ViewModelProvider(this).get(
+ viewModel = viewModelProvider.get(
DeviceFinancingSecondaryUserProvisionInfoViewModel.class);
break;
case ACTION_START_DEVICE_SUBSIDY_PROVISIONING:
- viewModel = new ViewModelProvider(this).get(
- DeviceSubsidyProvisionInfoViewModel.class);
- break;
- case ACTION_START_DEVICE_SUBSIDY_DEFERRED_PROVISIONING:
- viewModel = new ViewModelProvider(this).get(
- DeviceSubsidyDeferredProvisionInfoViewModel.class);
- isDeferredProvisioning = true;
+ viewModel = viewModelProvider.get(DeviceSubsidyProvisionInfoViewModel.class);
break;
default:
LogUtil.e(TAG, "Unknown action is received, exiting");
@@ -147,10 +133,15 @@
Button next = view.findViewById(R.id.button_next);
checkNotNull(next);
Context context = requireContext().getApplicationContext();
- if (isDeferredProvisioning) {
- next.setText(R.string.start);
- DeviceLockNotificationManager.cancelDeferredProvisioningNotification(context);
- }
+ viewModel.mIsMandatoryLiveData.observe(this,
+ isMandatory -> {
+ if (!isMandatory) {
+ next.setText(R.string.start);
+ DeviceLockNotificationManager.cancelDeferredProvisioningNotification(
+ context);
+ }
+ next.setVisibility(View.VISIBLE);
+ });
next.setOnClickListener(
v -> startActivity(new Intent(context, ProvisioningActivity.class)));
@@ -159,17 +150,19 @@
mResultLauncher = registerForActivityResult(new ActivityResultContracts.RequestPermission(),
isGranted -> provisionHelper.pauseProvision());
updatePreviousButton(checkNotNull(view.findViewById(R.id.button_previous)), viewModel,
- isDeferredProvisioning, provisionHelper);
+ provisionHelper);
}
private void updatePreviousButton(Button previous, ProvisionInfoViewModel viewModel,
- boolean isDeferredProvisioning, ProvisionHelper provisionHelper) {
- if (!isDeferredProvisioning) {
- previous.setVisibility(View.GONE);
- return;
- }
- previous.setText(R.string.do_it_in_one_hour);
- previous.setVisibility(View.VISIBLE);
+ ProvisionHelper provisionHelper) {
+ viewModel.mIsMandatoryLiveData.observe(this,
+ isMandatory -> {
+ if (!isMandatory) {
+ previous.setText(R.string.do_it_in_one_hour);
+ previous.setVisibility(View.VISIBLE);
+ }
+ });
+
viewModel.mIsProvisionForcedLiveData.observe(getViewLifecycleOwner(),
isProvisionForced -> {
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisionInfoViewModel.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisionInfoViewModel.java
index 3cffca3..8cb5bf0 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisionInfoViewModel.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisionInfoViewModel.java
@@ -44,14 +44,17 @@
public static final String TAG = "ProvisionInfoViewModel";
int mHeaderDrawableId;
+ int mMandatoryHeaderTextId;
int mHeaderTextId;
+ int mMandatorySubHeaderTextId;
int mSubHeaderTextId;
List<ProvisionInfo> mProvisionInfoList;
+ final MutableLiveData<Boolean> mIsMandatoryLiveData = new MutableLiveData<>();
final MutableLiveData<String> mProviderNameLiveData;
final MutableLiveData<String> mTermsAndConditionsUrlLiveData;
final MutableLiveData<Boolean> mIsProvisionForcedLiveData;
- final MediatorLiveData<Pair<Integer, String>> mHeaderTextLiveData;
- final MediatorLiveData<Pair<Integer, String>> mSubHeaderTextLiveData;
+ final MutableLiveData<Pair<Integer, String>> mHeaderTextLiveData = new MutableLiveData<>();
+ final MutableLiveData<Pair<Integer, String>> mSubHeaderTextLiveData = new MutableLiveData<>();
final MediatorLiveData<List<ProvisionInfo>> mProvisionInfoListLiveData;
public ProvisionInfoViewModel(@NonNull Application application) {
@@ -59,19 +62,12 @@
mProviderNameLiveData = new MutableLiveData<>();
mTermsAndConditionsUrlLiveData = new MutableLiveData<>();
mIsProvisionForcedLiveData = new MutableLiveData<>();
- mHeaderTextLiveData = new MediatorLiveData<>();
- mHeaderTextLiveData.addSource(mProviderNameLiveData,
- providerName -> mHeaderTextLiveData.setValue(
- new Pair<>(mHeaderTextId, providerName)));
- mSubHeaderTextLiveData = new MediatorLiveData<>();
- mSubHeaderTextLiveData.addSource(mProviderNameLiveData,
- providerName -> mSubHeaderTextLiveData.setValue(
- new Pair<>(mSubHeaderTextId, providerName)));
mProvisionInfoListLiveData = new MediatorLiveData<>();
SetupParametersClient setupParametersClient = SetupParametersClient.getInstance();
ListenableFuture<String> getKioskAppProviderNameFuture =
setupParametersClient.getKioskAppProviderName();
+ ListenableFuture<Boolean> isMandatoryFuture = setupParametersClient.isProvisionMandatory();
ListenableFuture<String> getTermsAndConditionsUrlFuture =
setupParametersClient.getTermsAndConditionsUrl();
@@ -93,6 +89,31 @@
}
}, MoreExecutors.directExecutor());
+ Futures.whenAllSucceed(isMandatoryFuture, getKioskAppProviderNameFuture).call(
+ () -> {
+ Boolean isMandatory = Futures.getDone(isMandatoryFuture);
+ String kioskProviderName = Futures.getDone(getKioskAppProviderNameFuture);
+ mHeaderTextLiveData.postValue(new Pair<>(
+ isMandatory ? mMandatoryHeaderTextId : mHeaderTextId,
+ kioskProviderName));
+ mSubHeaderTextLiveData.postValue(new Pair<>(
+ isMandatory ? mMandatorySubHeaderTextId : mSubHeaderTextId,
+ kioskProviderName));
+ return null;
+ }, MoreExecutors.directExecutor());
+ Futures.addCallback(isMandatoryFuture,
+ new FutureCallback<>() {
+ @Override
+ public void onSuccess(Boolean isMandatory) {
+ mIsMandatoryLiveData.postValue(isMandatory);
+ }
+
+ @Override
+ public void onFailure(Throwable t) {
+ LogUtil.e(TAG, "Failed to know if provision is mandatory", t);
+ }
+ }, MoreExecutors.directExecutor());
+
Futures.addCallback(
getTermsAndConditionsUrlFuture,
new FutureCallback<>() {
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisioningProgress.java b/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisioningProgress.java
index e56028f..934b463 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisioningProgress.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/activities/ProvisioningProgress.java
@@ -36,6 +36,11 @@
R.string.click_to_contact_financier, /* progressBarVisible=*/ false,
/* bottomViewVisible= */ true);
+ public static final ProvisioningProgress PROVISION_FAILED_MANDATORY = new ProvisioningProgress(
+ R.drawable.ic_warning_24px, R.string.provisioning_failed,
+ R.string.click_to_contact_financier, /* progressBarVisible=*/ false,
+ /* bottomViewVisible= */ false);
+
final int mIconId;
final int mHeaderId;
final int mSubheaderId;
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/common/DeviceLockConstants.java b/DeviceLockController/src/com/android/devicelockcontroller/common/DeviceLockConstants.java
index ef83b51..5b0ae67 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/common/DeviceLockConstants.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/common/DeviceLockConstants.java
@@ -16,8 +16,6 @@
package com.android.devicelockcontroller.common;
-import android.content.Context;
-
import androidx.annotation.IntDef;
import java.lang.annotation.ElementType;
@@ -27,9 +25,6 @@
/** Constants being used by more than one class in the Device Lock application. */
public final class DeviceLockConstants {
-
- public static final String KEY_KIOSK_APP_INSTALLED = "devicelock_kiosk_app_installed";
-
// Constants related to unique device identifiers.
@Retention(RetentionPolicy.SOURCE)
@IntDef(value = {
@@ -119,39 +114,14 @@
public static final String ACTION_START_DEVICE_FINANCING_PROVISIONING =
"com.android.devicelockcontroller.action.START_DEVICE_FINANCING_PROVISIONING";
- public static final String ACTION_START_DEVICE_FINANCING_DEFERRED_PROVISIONING =
- "com.android.devicelockcontroller.action.START_DEVICE_FINANCING_DEFERRED_PROVISIONING";
public static final String ACTION_START_DEVICE_FINANCING_SECONDARY_USER_PROVISIONING =
"com.android.devicelockcontroller.action"
- + ".START_DEVICE_FINANCING_SECONDARY_USER_PROVISIONING";
+ + ".START_DEVICE_FINANCING_SECONDARY_USER_PROVISIONING";
public static final String ACTION_START_DEVICE_SUBSIDY_PROVISIONING =
"com.android.devicelockcontroller.action.START_DEVICE_SUBSIDY_PROVISIONING";
- public static final String ACTION_START_DEVICE_SUBSIDY_DEFERRED_PROVISIONING =
- "com.android.devicelockcontroller.action.START_DEVICE_SUBSIDY_DEFERRED_PROVISIONING";
-
- /** Uses the package name of {@link Context#getPackageName()} to return the landing activity. */
- public static String getLandingActivity(Context context) {
- return context.getPackageName() + "/"
- + "com.android.devicelockcontroller.activities.LandingActivity";
- }
-
- /** Definitions for setup failure types. */
- @Retention(RetentionPolicy.SOURCE)
- @IntDef(
- value = {
- SetupFailureReason.SETUP_FAILED,
- SetupFailureReason.INSTALL_FAILED,
- })
- public @interface SetupFailureReason {
- /** Setup failed to complete */
- int SETUP_FAILED = 0;
- /** Failed to install the creditor apk. */
- int INSTALL_FAILED = 1;
- }
-
/** Definitions for device provision states. */
@Retention(RetentionPolicy.SOURCE)
@IntDef(
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/policy/DevicePolicyControllerImpl.java b/DeviceLockController/src/com/android/devicelockcontroller/policy/DevicePolicyControllerImpl.java
index 1c3c09b..4ab972f 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/policy/DevicePolicyControllerImpl.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/policy/DevicePolicyControllerImpl.java
@@ -16,9 +16,7 @@
package com.android.devicelockcontroller.policy;
-import static com.android.devicelockcontroller.common.DeviceLockConstants.ACTION_START_DEVICE_FINANCING_DEFERRED_PROVISIONING;
import static com.android.devicelockcontroller.common.DeviceLockConstants.ACTION_START_DEVICE_FINANCING_PROVISIONING;
-import static com.android.devicelockcontroller.common.DeviceLockConstants.ACTION_START_DEVICE_SUBSIDY_DEFERRED_PROVISIONING;
import static com.android.devicelockcontroller.common.DeviceLockConstants.ACTION_START_DEVICE_SUBSIDY_PROVISIONING;
import static com.android.devicelockcontroller.policy.DeviceStateController.DeviceState.CLEARED;
import static com.android.devicelockcontroller.policy.DeviceStateController.DeviceState.LOCKED;
@@ -286,25 +284,19 @@
SetupParametersClient client = SetupParametersClient.getInstance();
ListenableFuture<@ProvisioningType Integer> provisioningType =
client.getProvisioningType();
- ListenableFuture<Boolean> isMandatory = client.isProvisionMandatory();
- return Futures.whenAllSucceed(provisioningType, isMandatory).call(
- () -> {
+ return Futures.transform(provisioningType,
+ type -> {
Intent resultIntent = new Intent(mContext, LandingActivity.class);
- switch (Futures.getDone(provisioningType)) {
+ switch (type) {
case ProvisioningType.TYPE_FINANCED:
// TODO(b/288923554) this used to return an intent with action
// ACTION_START_DEVICE_FINANCING_SECONDARY_USER_PROVISIONING
// for secondary users. Rework once a decision has been made about
// what to show to users.
return resultIntent.setAction(
- Futures.getDone(isMandatory)
- ? ACTION_START_DEVICE_FINANCING_PROVISIONING
- : ACTION_START_DEVICE_FINANCING_DEFERRED_PROVISIONING);
+ ACTION_START_DEVICE_FINANCING_PROVISIONING);
case ProvisioningType.TYPE_SUBSIDY:
- return resultIntent.setAction(
- Futures.getDone(isMandatory)
- ? ACTION_START_DEVICE_SUBSIDY_PROVISIONING
- : ACTION_START_DEVICE_SUBSIDY_DEFERRED_PROVISIONING);
+ return resultIntent.setAction(ACTION_START_DEVICE_SUBSIDY_PROVISIONING);
case ProvisioningType.TYPE_UNDEFINED:
default:
throw new IllegalArgumentException("Provisioning type is unknown!");
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionHelper.java b/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionHelper.java
index 0adaa62..3d51559 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionHelper.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionHelper.java
@@ -33,5 +33,6 @@
* Start installation and open kiosk when it finish.
*/
void scheduleKioskAppInstallation(LifecycleOwner owner,
- ProvisioningProgressController progressController);
+ ProvisioningProgressController progressController,
+ boolean isProvisionMandatory);
}
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionHelperImpl.java b/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionHelperImpl.java
index 1234983..70a6d36 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionHelperImpl.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionHelperImpl.java
@@ -101,7 +101,7 @@
@Override
public void scheduleKioskAppInstallation(LifecycleOwner owner,
- ProvisioningProgressController progressController) {
+ ProvisioningProgressController progressController, boolean isMandatory) {
LogUtil.v(TAG, "Trigger setup flow");
progressController.setProvisioningProgress(ProvisioningProgress.GETTING_DEVICE_READY);
Futures.addCallback(SetupParametersClient.getInstance().getKioskPackage(),
@@ -168,8 +168,15 @@
@Override
public void onFailure(Throwable t) {
LogUtil.w(TAG, "Failed to install kiosk app!", t);
- progressController.setProvisioningProgress(
- ProvisioningProgress.PROVISIONING_FAILED);
+ if (isMandatory) {
+ progressController.setProvisioningProgress(
+ ProvisioningProgress.PROVISION_FAILED_MANDATORY);
+ new DeviceLockControllerScheduler(
+ mContext).scheduleMandatoryResetDeviceAlarm();
+ } else {
+ progressController.setProvisioningProgress(
+ ProvisioningProgress.PROVISIONING_FAILED);
+ }
}
}, sExecutor);
}
diff --git a/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionStateControllerImpl.java b/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionStateControllerImpl.java
index 849df9e..53551da 100644
--- a/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionStateControllerImpl.java
+++ b/DeviceLockController/src/com/android/devicelockcontroller/policy/ProvisionStateControllerImpl.java
@@ -39,8 +39,6 @@
import androidx.annotation.VisibleForTesting;
import androidx.work.WorkManager;
-import com.android.devicelockcontroller.AbstractDeviceLockControllerScheduler;
-import com.android.devicelockcontroller.DeviceLockControllerScheduler;
import com.android.devicelockcontroller.provision.worker.ReportDeviceProvisionStateWorker;
import com.android.devicelockcontroller.receivers.LockedBootCompletedReceiver;
import com.android.devicelockcontroller.storage.GlobalParametersClient;
@@ -68,7 +66,6 @@
private final DevicePolicyController mPolicyController;
private final DeviceStateController mDeviceStateController;
private final Executor mBgExecutor;
- private AbstractDeviceLockControllerScheduler mScheduler;
@GuardedBy("this")
private ListenableFuture<@ProvisionState Integer> mCurrentStateFuture;
@@ -162,10 +159,6 @@
} else if (state == PROVISION_FAILED) {
ReportDeviceProvisionStateWorker.reportSetupFailed(
WorkManager.getInstance(mContext));
- if (mScheduler == null) {
- mScheduler = new DeviceLockControllerScheduler(mContext);
- }
- mScheduler.scheduleNextProvisionFailedStepAlarm();
} else if (state == PROVISION_IN_PROGRESS) {
mContext.getPackageManager().setComponentEnabledSetting(
new ComponentName(mContext, LockedBootCompletedReceiver.class),
diff --git a/DeviceLockController/tests/robolectric/src/com/android/devicelockcontroller/policy/ProvisionHelperImplTest.java b/DeviceLockController/tests/robolectric/src/com/android/devicelockcontroller/policy/ProvisionHelperImplTest.java
index 3300cf8..cd7183d 100644
--- a/DeviceLockController/tests/robolectric/src/com/android/devicelockcontroller/policy/ProvisionHelperImplTest.java
+++ b/DeviceLockController/tests/robolectric/src/com/android/devicelockcontroller/policy/ProvisionHelperImplTest.java
@@ -125,8 +125,8 @@
kioskPackageInfo.packageName = TEST_PACKAGE_NAME;
pm.installPackage(kioskPackageInfo);
setupLifecycle();
-
- mProvisionHelper.scheduleKioskAppInstallation(mMockLifecycleOwner, mProgressController);
+ mProvisionHelper.scheduleKioskAppInstallation(mMockLifecycleOwner,
+ mProgressController, /* isProvisionMandatory= */ false);
ArgumentCaptor<ProvisioningProgress> argumentCaptor = ArgumentCaptor.forClass(
ProvisioningProgress.class);