Commit c5fec8c6 authored by Brian Sheedy's avatar Brian Sheedy Committed by Commit Bot

Fix XR consent dialog tests

Fixes the XR consent dialog tests that were broken by a recent change to
not show the consent dialog on repeated sessions on the same page. This
is achieved by keeping track of what session types we've successfully
created in the WebXR boilerplate code.

Bug: 995843
Change-Id: I261bfda8526bf35fc0fc3134a2690e521644547e
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1764672Reviewed-by: default avatarAlexander Cooper <alcooper@chromium.org>
Reviewed-by: default avatarPiotr Bialecki <bialpio@chromium.org>
Commit-Queue: Brian Sheedy <bsheedy@chromium.org>
Cr-Commit-Position: refs/heads/master@{#689547}
parent fe35349c
......@@ -190,7 +190,9 @@ public class ArImmersiveOverlay
// The JS app may have put an element into fullscreen mode during the immersive session,
// even if this wasn't visible to the user. Ensure that we fully exit out of any active
// fullscreen state on session end to avoid being left in a confusing state.
mActivity.getActivityTab().exitFullscreenMode();
if (mActivity.getActivityTab() != null) {
mActivity.getActivityTab().exitFullscreenMode();
}
// Restore orientation.
ScreenOrientationProvider.getInstance().setOrientationDelegate(null);
......
......@@ -15,7 +15,6 @@ import org.chromium.content_public.browser.WebContents;
public class WebVrTestFramework extends WebXrVrTestFramework {
public WebVrTestFramework(ChromeActivityTestRule rule) {
super(rule);
mShouldExpectConsentDialog = false;
}
/**
......@@ -53,4 +52,15 @@ public class WebVrTestFramework extends WebXrVrTestFramework {
public void endSession(WebContents webContents) {
runJavaScriptOrFail("vrDisplay.exitPresent()", POLL_TIMEOUT_SHORT_MS, webContents);
}
/**
* Checks whether a WebVR session would trigger the consent dialog.
*
* @param webContents The WebContents to check in.
* @return False, as WebVR doesn't use the consent dialog.
*/
@Override
public boolean shouldExpectConsentDialog(WebContents webContents) {
return false;
}
}
......@@ -5,6 +5,7 @@
package org.chromium.chrome.browser.vr;
import static org.chromium.chrome.browser.vr.WebXrArTestFramework.PAGE_LOAD_TIMEOUT_S;
import static org.chromium.chrome.browser.vr.WebXrArTestFramework.POLL_TIMEOUT_SHORT_MS;
import android.os.Build;
import android.support.test.filters.MediumTest;
......@@ -23,6 +24,7 @@ import org.chromium.base.test.util.CommandLineFlags;
import org.chromium.base.test.util.MinAndroidSdkLevel;
import org.chromium.chrome.browser.ChromeSwitches;
import org.chromium.chrome.browser.vr.rules.XrActivityRestriction;
import org.chromium.chrome.browser.vr.util.PermissionUtils;
import org.chromium.chrome.browser.vr.util.XrTestRuleUtils;
import org.chromium.chrome.test.ChromeActivityTestRule;
import org.chromium.chrome.test.ChromeJUnit4RunnerDelegate;
......@@ -75,12 +77,14 @@ public class WebXrArSessionTest {
}
/**
* Tests that AR session consent can be declined or granted per session.
* Tests that declining AR consent causes future attempts to still display the consent dialog,
* but consenting causes future attempts to skip the consent dialog as long as no navigation
* occurs.
*/
@Test
@MediumTest
@XrActivityRestriction({XrActivityRestriction.SupportedActivity.ALL})
public void testArVaryingPerSessionConsent() throws InterruptedException {
public void testConsentPersistanceOnSamePage() throws InterruptedException {
mWebXrArTestFramework.loadUrlAndAwaitInitialization(
mWebXrArTestFramework.getEmbeddedServerUrlForHtmlTestFile(
"test_ar_request_session_succeeds"),
......@@ -92,12 +96,18 @@ public class WebXrArSessionTest {
mWebXrArTestFramework.assertNoJavaScriptErrors();
// Start new session, accept consent prompt this time.
PermissionUtils.waitForConsentPromptDismissal(mTestRule.getActivity());
mWebXrArTestFramework.enterSessionWithUserGestureOrFail(contents);
mWebXrArTestFramework.endSession();
mWebXrArTestFramework.assertNoJavaScriptErrors();
// Start yet another session, decline consent prompt again.
mWebXrArTestFramework.enterSessionWithUserGestureAndDeclineConsentOrFail(contents);
// Start yet another session, but go through a path that doesn't automatically handle
// the consent dialog to ensure that it doesn't actually appear.
mWebXrArTestFramework.pollJavaScriptBooleanOrFail(
"sessionInfos[sessionTypes.AR].currentSession == null", POLL_TIMEOUT_SHORT_MS);
mWebXrArTestFramework.enterSessionWithUserGesture();
mWebXrArTestFramework.pollJavaScriptBooleanOrFail(
"sessionInfos[sessionTypes.AR].currentSession != null", POLL_TIMEOUT_SHORT_MS);
mWebXrArTestFramework.assertNoJavaScriptErrors();
}
......
......@@ -4,6 +4,8 @@
package org.chromium.chrome.browser.vr;
import org.junit.Assert;
import org.chromium.chrome.browser.vr.util.PermissionUtils;
import org.chromium.chrome.test.ChromeActivityTestRule;
import org.chromium.content_public.browser.WebContents;
......@@ -35,8 +37,10 @@ public class WebXrArTestFramework extends WebXrTestFramework {
// We expect a session consent prompt (in this case the AR-specific one), but should not
// get prompted for page camera permission.
PermissionUtils.waitForConsentPrompt(getRule().getActivity());
PermissionUtils.acceptConsentPrompt(getRule().getActivity());
if (shouldExpectConsentDialog()) {
PermissionUtils.waitForConsentPrompt(getRule().getActivity());
PermissionUtils.acceptConsentPrompt(getRule().getActivity());
}
pollJavaScriptBooleanOrFail("sessionInfos[sessionTypes.AR].currentSession != null",
POLL_TIMEOUT_LONG_MS, webContents);
......@@ -49,6 +53,9 @@ public class WebXrArTestFramework extends WebXrTestFramework {
* @param webContents The Webcontents to start the AR session in.
*/
public void enterSessionWithUserGestureAndDeclineConsentOrFail(WebContents webContents) {
if (!shouldExpectConsentDialog()) {
Assert.fail("Attempted to decline the consent dialog when it would not appear.");
}
runJavaScriptOrFail(
"sessionTypeToRequest = sessionTypes.AR", POLL_TIMEOUT_LONG_MS, webContents);
......@@ -75,4 +82,16 @@ public class WebXrArTestFramework extends WebXrTestFramework {
runJavaScriptOrFail("sessionInfos[sessionTypes.AR].currentSession.end()",
POLL_TIMEOUT_SHORT_MS, webContents);
}
/**
* Checks whether an immersive AR session would trigger the consent dialog.
*
* @param webContents The WebContents to check in.
* @return True if an immersive AR session request would trigger the consent dialog, otherwise
* false.
*/
@Override
public boolean shouldExpectConsentDialog(WebContents webContents) {
return shouldExpectConsentDialog("sessionTypes.AR", webContents);
}
}
......@@ -103,7 +103,7 @@ public abstract class WebXrTestFramework extends XrTestFramework {
/**
* Ends whatever type of session a subclass enters with enterSessionWithUserGesture.
*
* @param webContents The WebContents to end the session in
* @param webContents The WebContents to end the session in.
*/
public abstract void endSession(WebContents webContents);
......@@ -113,4 +113,39 @@ public abstract class WebXrTestFramework extends XrTestFramework {
public void endSession() {
endSession(getCurrentWebContents());
}
/**
* Helper function to run shouldExpectConsentDialog with the correct session type for the
* framework.
*
* @param webContents The WebContents to check the consent dialog in.
* @return True if the a request for the session type would trigger the consent dialog to be
* shown, otherwise false.
*/
public abstract boolean shouldExpectConsentDialog(WebContents webContents);
/**
* Helper function to run shouldExpectConsentDialog with the current tab's WebContents.
* @return True if the a request for the session type would trigger the consent dialog to be
* shown, otherwise false.
*/
public boolean shouldExpectConsentDialog() {
return shouldExpectConsentDialog(getCurrentWebContents());
}
/**
* Checks whether a session request of the given type is expected to trigger the consent
* dialog.
*
* @param sessionType The session type to pass to JavaScript defined in webxr_boilerplate.js,
* e.g. sessionTypes.AR
* @param webCointents The WebContents to check in.
* @return True if the given session type is expected to trigger the consent dialog, otherwise
* false.
*/
protected boolean shouldExpectConsentDialog(String sessionType, WebContents webContents) {
return runJavaScriptOrFail("sessionTypeWouldTriggerConsent(" + sessionType + ")",
POLL_TIMEOUT_SHORT_MS, webContents)
.equals("true");
}
}
......@@ -30,9 +30,6 @@ public class WebXrVrTestFramework extends WebXrTestFramework {
public static final int CONSENT_DIALOG_ACTION_ALLOW = 1;
public static final int CONSENT_DIALOG_ACTION_DENY = 2;
// If set, a consent dialog is expected on all enterSessionWithUserGesture* methods.
protected boolean mShouldExpectConsentDialog = true;
@ConsentDialogAction
protected int mConsentDialogAction = CONSENT_DIALOG_ACTION_ALLOW;
......@@ -69,7 +66,7 @@ public class WebXrVrTestFramework extends WebXrTestFramework {
}
super.enterSessionWithUserGesture(webContents);
if (!mShouldExpectConsentDialog) return;
if (!shouldExpectConsentDialog()) return;
PermissionUtils.waitForConsentPrompt(getRule().getActivity());
if (mConsentDialogAction == CONSENT_DIALOG_ACTION_ALLOW)
PermissionUtils.acceptConsentPrompt(getRule().getActivity());
......@@ -104,4 +101,16 @@ public class WebXrVrTestFramework extends WebXrTestFramework {
runJavaScriptOrFail("sessionInfos[sessionTypes.IMMERSIVE].currentSession.end()",
POLL_TIMEOUT_SHORT_MS, webContents);
}
/**
* Checks whether an immersive VR session would trigger the consent dialog.
*
* @param webContents The WebContents to check in.
* @return True if an immersive VR session request would trigger the consent dialog, otherwise
* false.
*/
@Override
public boolean shouldExpectConsentDialog(WebContents webContents) {
return shouldExpectConsentDialog("sessionTypes.IMMERSIVE", webContents);
}
}
......@@ -538,6 +538,5 @@ public class WebXrVrTransitionTest {
"window.location.href = 'https://google.com'", POLL_TIMEOUT_SHORT_MS);
PermissionUtils.waitForConsentPromptDismissal(
mWebXrVrTestFramework.getRule().getActivity());
mWebXrVrTestFramework.assertNoJavaScriptErrors();
}
}
......@@ -4,6 +4,8 @@
package org.chromium.chrome.browser.vr.util;
import android.os.SystemClock;
import org.chromium.chrome.browser.ChromeActivity;
import org.chromium.chrome.browser.permissions.PermissionDialogController;
import org.chromium.chrome.browser.vr.ArConsentDialog;
......@@ -67,6 +69,9 @@ public class PermissionUtils {
-> { return !isConsentDialogShown(activity); },
"Consent prompt did not get dismissed in allotted time",
CriteriaHelper.DEFAULT_MAX_TIME_TO_POLL, DIALOG_POLLING_INTERVAL_MS);
// For some reason, the prompt can be dismissed, but we won't be able to show a new one for
// a short period of time (animations?), so wait a little longer to avoid that.
SystemClock.sleep(500);
}
/**
......
......@@ -83,6 +83,13 @@ function getSessionType(session) {
}
}
function sessionTypeWouldTriggerConsent(sessionType) {
if (typeof navigator.xr.startedSessionTypes === 'undefined') {
return true;
}
return !(sessionType in navigator.xr.startedSessionTypes);
}
function onRequestSession() {
switch (sessionTypeToRequest) {
case sessionTypes.IMMERSIVE:
......@@ -115,6 +122,14 @@ function onRequestSession() {
}
function onSessionStarted(session) {
// Record that we've started this session type so that we know not to expect
// the consent dialog for it in the future.
let sessionType = getSessionType(session);
if (typeof navigator.xr.startedSessionTypes === 'undefined') {
navigator.xr.startedSessionTypes = {};
}
navigator.xr.startedSessionTypes[sessionType] = undefined;
session.addEventListener('end', onSessionEnded);
// Initialize the WebGL context for use with XR if it hasn't been already
if (!gl) {
......@@ -132,8 +147,6 @@ function onSessionStarted(session) {
onSessionStartedCallback(session);
}
let sessionType = getSessionType(session);
session.updateRenderState({ baseLayer: new XRWebGLLayer(session, gl) });
session.requestReferenceSpace(referenceSpaceMap[sessionType])
.then( (refSpace) => {
......
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