Commit 3fc155bb authored by Sky Malice's avatar Sky Malice Committed by Commit Bot

Read real CCTToSDialogEnabled policy.

Bug: 1108118
Change-Id: If843abbcd6dd5451775d2d79bc6d55c151552ca9
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2344813
Commit-Queue: Sky Malice <skym@chromium.org>
Reviewed-by: default avatarOwen Min <zmin@chromium.org>
Reviewed-by: default avatarTheresa  <twellington@chromium.org>
Cr-Commit-Position: refs/heads/master@{#799516}
parent 83f2f67e
......@@ -324,6 +324,7 @@ android_library("chrome_java") {
"//chrome/browser/password_check:public_java",
"//chrome/browser/password_manager/android:java",
"//chrome/browser/performance_hints/android:java",
"//chrome/browser/policy/android:java",
"//chrome/browser/preferences:java",
"//chrome/browser/privacy:java",
"//chrome/browser/profiles/android:java",
......@@ -988,6 +989,7 @@ android_library("chrome_test_java") {
"//chrome/browser/password_manager/android:java",
"//chrome/browser/password_manager/android_test_helpers:test_support_java",
"//chrome/browser/performance_hints/android:java",
"//chrome/browser/policy/android:java",
"//chrome/browser/preferences:java",
"//chrome/browser/profiles/android:java",
"//chrome/browser/safe_browsing/android:java",
......
......@@ -6,6 +6,7 @@ include_rules = [
"+chrome/browser/fullscreen/android",
"+chrome/browser/notifications",
"+chrome/browser/password_manager/android",
"+chrome/browser/policy/android",
"+chrome/browser/preferences/android/java",
"+chrome/browser/safe_browsing/android",
"+chrome/browser/safety_check/android",
......
......@@ -13,7 +13,9 @@ import androidx.annotation.VisibleForTesting;
import org.chromium.base.CallbackController;
import org.chromium.base.Log;
import org.chromium.chrome.R;
import org.chromium.chrome.browser.policy.PolicyServiceFactory;
import org.chromium.components.browser_ui.widget.LoadingView;
import org.chromium.policy.PolicyService;
/**
* Another FirstRunFragment that is only used when running with CCT.
......@@ -42,6 +44,7 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport
private boolean mViewCreated;
private LoadingView mLoadingSpinner;
private CallbackController mCallbackController;
private PolicyService.Observer mPolicyServiceObserver;
/**
* Whether app restriction is found on the device. This can be null when this information is not
......@@ -71,6 +74,10 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport
mLoadingSpinner.destroy();
mLoadingSpinner = null;
}
if (mPolicyServiceObserver != null) {
PolicyServiceFactory.getGlobalPolicyService().removeObserver(mPolicyServiceObserver);
mPolicyServiceObserver = null;
}
super.onDestroy();
}
......@@ -153,8 +160,7 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport
mCallbackController.makeCancelable(this::onAppRestrictionDetected));
}
@VisibleForTesting
void onAppRestrictionDetected(boolean hasAppRestriction) {
private void onAppRestrictionDetected(boolean hasAppRestriction) {
mHasRestriction = hasAppRestriction;
if (!shouldWaitForPolicyLoading() && mViewCreated) {
......@@ -164,20 +170,21 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport
}
private void checkEnterprisePolicies() {
// TODO(crbug.com/1106812): Monitor policy changes when it is ready.
if (!sBlockPolicyLoadingForTest) {
onCctTosPolicyDetected(getPolicyCctTosDialogEnabled());
}
PolicyService policyService = PolicyServiceFactory.getGlobalPolicyService();
if (policyService.isInitializationComplete()) {
updateCctTosPolicy();
} else {
mPolicyServiceObserver = () -> {
policyService.removeObserver(mPolicyServiceObserver);
mPolicyServiceObserver = null;
updateCctTosPolicy();
};
policyService.addObserver(mPolicyServiceObserver);
}
private boolean getPolicyCctTosDialogEnabled() {
// TODO(crbug.com/1108118): Do the actual fetching for CCT Policy to replace the fake one.
return true;
}
@VisibleForTesting
void onCctTosPolicyDetected(boolean cctTosDialogEnabled) {
mPolicyCctTosDialogEnabled = cctTosDialogEnabled;
private void updateCctTosPolicy() {
mPolicyCctTosDialogEnabled = FirstRunUtils.isCctTosDialogEnabled();
if (mViewCreated) {
mLoadingSpinner.hideLoadingUI();
}
......@@ -192,9 +199,4 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupport
Log.d(TAG, "TosAndUmaFirstRunFragmentWithEnterpriseSupport finished.");
getPageDelegate().exitFirstRun();
}
@VisibleForTesting
static void setBlockPolicyLoadingForTest(boolean blockPolicyLoadingForTest) {
sBlockPolicyLoadingForTest = blockPolicyLoadingForTest;
}
}
......@@ -48,7 +48,7 @@ import org.chromium.components.search_engines.TemplateUrl;
import org.chromium.content_public.browser.UiThreadTaskTraits;
import org.chromium.content_public.browser.test.util.Criteria;
import org.chromium.content_public.browser.test.util.CriteriaHelper;
import org.chromium.content_public.browser.test.util.TestThreadUtils;
import org.chromium.policy.AbstractAppRestrictionsProvider;
import java.util.HashMap;
import java.util.List;
......@@ -95,7 +95,6 @@ public class FirstRunIntegrationTest {
public void tearDown() {
FirstRunActivity.setEnableEnterpriseCCTForTest(false);
FirstRunAppRestrictionInfo.setInstanceForTest(null);
TosAndUmaFirstRunFragmentWithEnterpriseSupport.setBlockPolicyLoadingForTest(false);
if (mLastActivity != null) mLastActivity.finish();
}
......@@ -257,7 +256,9 @@ public class FirstRunIntegrationTest {
public void testExitFirstRunWithPolicy() {
setHasAppRestrictionForMock();
FirstRunActivity.setEnableEnterpriseCCTForTest(true);
TosAndUmaFirstRunFragmentWithEnterpriseSupport.setBlockPolicyLoadingForTest(true);
Bundle restrictions = new Bundle();
restrictions.putBoolean("CCTToSDialogEnabled", false);
AbstractAppRestrictionsProvider.setTestRestrictions(restrictions);
Intent intent =
CustomTabsTestUtils.createMinimalCustomTabIntent(mContext, "https://test.com");
......@@ -266,20 +267,10 @@ public class FirstRunIntegrationTest {
FirstRunActivity freActivity = waitForActivity(FirstRunActivity.class);
CriteriaHelper.pollUiThread(
() -> freActivity.getSupportFragmentManager().getFragments().size() > 0);
TosAndUmaFirstRunFragmentWithEnterpriseSupport fragment =
(TosAndUmaFirstRunFragmentWithEnterpriseSupport) freActivity
.getSupportFragmentManager()
.getFragments()
.get(0);
// Make sure native is initialized so that the subseuqent transition doesn't get blocked.
CriteriaHelper.pollUiThread((() -> freActivity.isNativeSideIsInitializedForTest()),
"native never initialized.");
// This policy cause the FRE to be skipped. It responds by relaunching the original intent,
// which should cause a {@link CustomTabActivity} because this was originally a CCT intent.
TestThreadUtils.runOnUiThreadBlocking(() -> fragment.onCctTosPolicyDetected(false));
waitForActivity(CustomTabActivity.class);
}
......
// Copyright 2015 The Chromium Authors. All rights reserved.
// Copyright 2020 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
......@@ -33,14 +33,18 @@ import org.chromium.base.CommandLine;
import org.chromium.chrome.R;
import org.chromium.chrome.browser.customtabs.CustomTabsTestUtils;
import org.chromium.chrome.browser.flags.ChromeSwitches;
import org.chromium.chrome.browser.policy.PolicyServiceFactory;
import org.chromium.chrome.test.ChromeJUnit4ClassRunner;
import org.chromium.content_public.browser.test.util.Criteria;
import org.chromium.content_public.browser.test.util.CriteriaHelper;
import org.chromium.content_public.browser.test.util.TestThreadUtils;
import org.chromium.policy.PolicyService;
import org.chromium.ui.test.util.DisableAnimationsTestRule;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.util.ArrayList;
import java.util.List;
/**
* Test for first run activity and {@link TosAndUmaFirstRunFragmentWithEnterpriseSupport}.
......@@ -62,10 +66,16 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupportTest {
@Mock
public FirstRunAppRestrictionInfo mMockAppRestrictionInfo;
@Mock
public PolicyService mPolicyService;
@Mock
public FirstRunUtils.Natives mFirstRunUtils;
private FirstRunActivityTestObserver mTestObserver = new FirstRunActivityTestObserver();
private FirstRunActivity mActivity;
private TosAndUmaFirstRunFragmentWithEnterpriseSupport mFragment;
private final List<PolicyService.Observer> mPolicyServiceObservers = new ArrayList<>();
private final List<Callback<Boolean>> mAppRestrictonsCallbacks = new ArrayList<>();
private View mTosText;
private View mAcceptButton;
......@@ -78,56 +88,60 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupportTest {
Assert.assertFalse(
CommandLine.getInstance().hasSwitch(ChromeSwitches.DISABLE_FIRST_RUN_EXPERIENCE));
// Static switches.
FirstRunActivity.setEnableEnterpriseCCTForTest(true);
FirstRunAppRestrictionInfo.setInstanceForTest(mMockAppRestrictionInfo);
TosAndUmaFirstRunFragmentWithEnterpriseSupport.setBlockPolicyLoadingForTest(true);
PolicyServiceFactory.setPolicyServiceForTest(mPolicyService);
FirstRunUtilsJni.TEST_HOOKS.setInstanceForTesting(mFirstRunUtils);
}
@After
public void tearDown() {
FirstRunActivity.setEnableEnterpriseCCTForTest(false);
FirstRunAppRestrictionInfo.setInstanceForTest(null);
TosAndUmaFirstRunFragmentWithEnterpriseSupport.setBlockPolicyLoadingForTest(false);
PolicyServiceFactory.setPolicyServiceForTest(null);
FirstRunUtilsJni.TEST_HOOKS.setInstanceForTesting(mFirstRunUtils);
if (mActivity != null) mActivity.finish();
}
@Test
@SmallTest
public void testNoRestriction() {
setAppRestrictiosnMockNotInitialized();
launchFirstRunThroughCustomTab();
assertUIState(FragmentState.LOADING);
TestThreadUtils.runOnUiThreadBlocking(() -> mFragment.onAppRestrictionDetected(false));
TestThreadUtils.runOnUiThreadBlocking(() -> setAppRestrictiosnMockInitialized(false));
assertUIState(FragmentState.NO_POLICY);
}
@Test
@SmallTest
public void testWithRestriction_NoPolicy() {
setHasAppRestrictionForMock();
public void testWithRestriction_DialogEnabled() {
setAppRestrictiosnMockInitialized(true);
setPolicyServiceMockNotInitialized();
launchFirstRunThroughCustomTab();
assertUIState(FragmentState.LOADING);
waitUntilNativeLoaded();
TestThreadUtils.runOnUiThreadBlocking(() -> mFragment.onCctTosPolicyDetected(true));
setMockCctTosDialogEnabled(true);
TestThreadUtils.runOnUiThreadBlocking(() -> setPolicyServiceMockInitialized());
assertUIState(FragmentState.NO_POLICY);
}
@Test
@SmallTest
public void testWithRestriction_WithPolicy() {
setHasAppRestrictionForMock();
public void testWithRestriction_DialogDisabled() {
setAppRestrictiosnMockInitialized(true);
setPolicyServiceMockNotInitialized();
launchFirstRunThroughCustomTab();
assertUIState(FragmentState.LOADING);
waitUntilNativeLoaded();
setMockCctTosDialogEnabled(false);
TestThreadUtils.runOnUiThreadBlocking(() -> setPolicyServiceMockInitialized());
TestThreadUtils.runOnUiThreadBlocking(() -> mFragment.onCctTosPolicyDetected(false));
assertUIState(FragmentState.HAS_POLICY);
CriteriaHelper.pollUiThread(() -> mTestObserver.exitFirstRunCallback.getCallCount() > 0);
// TODO(https://crbug.com/1113229): Rework this to not depend on {@link FirstRunActivity}
// implementation details.
Assert.assertTrue(FirstRunStatus.isEphemeralSkipFirstRun());
}
/**
......@@ -165,6 +179,11 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupportTest {
.getSupportFragmentManager()
.getFragments()
.get(0);
// Force this to happen now to try to make the tests more deterministic. Ideally the tests
// could control when this happens and test for difference sequences.
waitUntilNativeLoaded();
mTosText = mActivity.findViewById(R.id.tos_and_privacy);
mAcceptButton = mActivity.findViewById(R.id.tos_and_privacy);
mLargeSpinner = mActivity.findViewById(R.id.progress_spinner_large);
......@@ -187,19 +206,55 @@ public class TosAndUmaFirstRunFragmentWithEnterpriseSupportTest {
tosVisibility, mAcceptButton.getVisibility());
}
/** Set up mock FirstRunAppRestrictionInfo that there is app restriction on the device */
private void setHasAppRestrictionForMock() {
private void waitUntilNativeLoaded() {
CriteriaHelper.pollUiThread(
(() -> mActivity.isNativeSideIsInitializedForTest()), "native never initialized.");
}
private void setAppRestrictiosnMockNotInitialized() {
Mockito.doAnswer(invocation -> {
Callback<Boolean> callback = invocation.getArgument(0);
callback.onResult(true);
mAppRestrictonsCallbacks.add(callback);
return null;
})
.when(mMockAppRestrictionInfo)
.getHasAppRestriction(any());
}
private void waitUntilNativeLoaded() {
CriteriaHelper.pollUiThread(
(() -> mActivity.isNativeSideIsInitializedForTest()), "native never initialized.");
private void setAppRestrictiosnMockInitialized(boolean hasAppRestrictons) {
Mockito.doAnswer(invocation -> {
Callback<Boolean> callback = invocation.getArgument(0);
callback.onResult(hasAppRestrictons);
return null;
})
.when(mMockAppRestrictionInfo)
.getHasAppRestriction(any());
for (Callback<Boolean> callback : mAppRestrictonsCallbacks) {
callback.onResult(hasAppRestrictons);
}
}
private void setPolicyServiceMockNotInitialized() {
Mockito.when(mPolicyService.isInitializationComplete()).thenReturn(false);
Mockito.doAnswer(invocation -> {
PolicyService.Observer observer = invocation.getArgument(0);
mPolicyServiceObservers.add(observer);
return null;
})
.when(mPolicyService)
.addObserver(any());
}
private void setPolicyServiceMockInitialized() {
Mockito.when(mPolicyService.isInitializationComplete()).thenReturn(true);
for (PolicyService.Observer observer : mPolicyServiceObservers) {
observer.onPolicyServiceInitialized();
}
mPolicyServiceObservers.clear();
}
private void setMockCctTosDialogEnabled(boolean cctTosDialogEnabled) {
Mockito.when(mFirstRunUtils.getCctTosDialogEnabled()).thenReturn(cctTosDialogEnabled);
}
}
......@@ -13,6 +13,7 @@ android_library("java") {
"//base:jni_java",
"//chrome/browser/profiles/android:java",
"//components/policy/android:policy_java",
"//third_party/android_deps:androidx_annotation_annotation_java",
]
annotation_processor_deps = [ "//base/android/jni_generator:jni_processor" ]
sources = _jni_sources
......
......@@ -4,6 +4,8 @@
package org.chromium.chrome.browser.policy;
import androidx.annotation.VisibleForTesting;
import org.chromium.base.annotations.JNINamespace;
import org.chromium.base.annotations.NativeMethods;
import org.chromium.chrome.browser.profiles.Profile;
......@@ -16,12 +18,16 @@ import org.chromium.policy.PolicyService;
*/
@JNINamespace("policy::android")
public class PolicyServiceFactory {
private static PolicyService sPolicyServiceForTest;
/**
* Returns the PolicyService instance that contains browser policies.
* The associated C++ instance is deleted during shutdown.
*/
public static PolicyService getGlobalPolicyService() {
return PolicyServiceFactoryJni.get().getGlobalPolicyService();
return sPolicyServiceForTest == null
? PolicyServiceFactoryJni.get().getGlobalPolicyService()
: sPolicyServiceForTest;
}
/**
......@@ -30,7 +36,17 @@ public class PolicyServiceFactory {
* deletion.
*/
public static PolicyService getProfilePolicyService(Profile profile) {
return PolicyServiceFactoryJni.get().getProfilePolicyService(profile);
return sPolicyServiceForTest == null
? PolicyServiceFactoryJni.get().getProfilePolicyService(profile)
: sPolicyServiceForTest;
}
/**
* @param policyService Mock {@link PolicyService} for testing.
*/
@VisibleForTesting
public static void setPolicyServiceForTest(PolicyService policyService) {
sPolicyServiceForTest = policyService;
}
@NativeMethods
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment