blob: fd93592f31744b825f8ce5b5c7aada28b4860d50 [file] [log] [blame]
// Copyright 2014 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.
package org.chromium.android_webview.test;
import android.support.test.InstrumentationRegistry;
import androidx.test.filters.SmallTest;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Rule;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.chromium.android_webview.AwContentsStatics;
import org.chromium.android_webview.AwWebContentsObserver;
import org.chromium.base.test.util.Feature;
import org.chromium.content_public.browser.GlobalRenderFrameHostId;
import org.chromium.content_public.browser.LifecycleState;
import org.chromium.content_public.browser.NavigationHandle;
import org.chromium.content_public.browser.test.util.TestCallbackHelperContainer;
import org.chromium.ui.base.PageTransition;
import org.chromium.url.GURL;
/**
* Tests for the AwWebContentsObserver class.
*/
@RunWith(AwJUnit4ClassRunner.class)
public class AwWebContentsObserverTest {
@Rule
public AwActivityTestRule mActivityTestRule = new AwActivityTestRule();
private TestAwContentsClient mContentsClient;
private AwTestContainerView mTestContainerView;
private AwWebContentsObserver mWebContentsObserver;
private GURL mExampleURL;
private GURL mExampleURLWithFragment;
private GURL mSyncURL;
private GURL mUnreachableWebDataUrl;
@Before
public void setUp() {
mContentsClient = new TestAwContentsClient();
mTestContainerView = mActivityTestRule.createAwTestContainerViewOnMainSync(mContentsClient);
mUnreachableWebDataUrl = new GURL(AwContentsStatics.getUnreachableWebDataUrl());
mExampleURL = new GURL("http://www.example.com/");
mExampleURLWithFragment = new GURL("http://www.example.com/#anchor");
mSyncURL = new GURL("http://example.org/");
// AwWebContentsObserver constructor must be run on the UI thread.
InstrumentationRegistry.getInstrumentation().runOnMainSync(
() -> mWebContentsObserver =
new AwWebContentsObserver(mTestContainerView.getWebContents(),
mTestContainerView.getAwContents(), mContentsClient));
}
@Test
@SmallTest
@Feature({"AndroidWebView"})
public void testOnPageFinished() throws Throwable {
GlobalRenderFrameHostId frameId = new GlobalRenderFrameHostId(-1, -1);
boolean mainFrame = true;
boolean subFrame = false;
final TestCallbackHelperContainer.OnPageFinishedHelper onPageFinishedHelper =
mContentsClient.getOnPageFinishedHelper();
int callCount = onPageFinishedHelper.getCallCount();
mWebContentsObserver.didFinishLoad(
frameId, mExampleURL, true, mainFrame, LifecycleState.ACTIVE);
mWebContentsObserver.didStopLoading(mExampleURL, true);
onPageFinishedHelper.waitForCallback(callCount);
Assert.assertEquals("onPageFinished should be called for main frame navigations.",
callCount + 1, onPageFinishedHelper.getCallCount());
Assert.assertEquals("onPageFinished should be called for main frame navigations.",
mExampleURL.getSpec(), onPageFinishedHelper.getUrl());
// In order to check that callbacks are *not* firing, first we execute code
// that shoudn't emit callbacks, then code that emits a callback, and check that we
// have got only one callback, and that its URL is from the last call. Since
// callbacks are serialized, that means we didn't have a callback for the first call.
callCount = onPageFinishedHelper.getCallCount();
mWebContentsObserver.didFinishLoad(
frameId, mExampleURL, true, subFrame, LifecycleState.ACTIVE);
mWebContentsObserver.didFinishLoad(
frameId, mSyncURL, true, mainFrame, LifecycleState.ACTIVE);
mWebContentsObserver.didStopLoading(mSyncURL, true);
onPageFinishedHelper.waitForCallback(callCount);
Assert.assertEquals("onPageFinished should only be called for the main frame.",
callCount + 1, onPageFinishedHelper.getCallCount());
Assert.assertEquals("onPageFinished should only be called for the main frame.",
mSyncURL.getSpec(), onPageFinishedHelper.getUrl());
callCount = onPageFinishedHelper.getCallCount();
mWebContentsObserver.didFinishLoad(
frameId, mUnreachableWebDataUrl, false, mainFrame, LifecycleState.ACTIVE);
mWebContentsObserver.didFinishLoad(
frameId, mSyncURL, true, mainFrame, LifecycleState.ACTIVE);
mWebContentsObserver.didStopLoading(mSyncURL, true);
onPageFinishedHelper.waitForCallback(callCount);
Assert.assertEquals("onPageFinished should not be called for the error url.", callCount + 1,
onPageFinishedHelper.getCallCount());
Assert.assertEquals("onPageFinished should not be called for the error url.",
mSyncURL.getSpec(), onPageFinishedHelper.getUrl());
String baseUrl = null;
boolean isInMainFrame = true;
boolean isErrorPage = false;
boolean isSameDocument = true;
boolean fragmentNavigation = true;
boolean isRendererInitiated = true;
int errorCode = 0;
int httpStatusCode = 200;
callCount = onPageFinishedHelper.getCallCount();
simulateNavigation(mExampleURL, isInMainFrame, isErrorPage, !isSameDocument,
!fragmentNavigation, !isRendererInitiated, PageTransition.TYPED);
simulateNavigation(mExampleURLWithFragment, isInMainFrame, isErrorPage, isSameDocument,
fragmentNavigation, isRendererInitiated, PageTransition.TYPED);
onPageFinishedHelper.waitForCallback(callCount);
Assert.assertEquals("onPageFinished should be called for main frame fragment navigations.",
callCount + 1, onPageFinishedHelper.getCallCount());
Assert.assertEquals("onPageFinished should be called for main frame fragment navigations.",
mExampleURLWithFragment.getSpec(), onPageFinishedHelper.getUrl());
callCount = onPageFinishedHelper.getCallCount();
simulateNavigation(mExampleURL, isInMainFrame, isErrorPage, !isSameDocument,
!fragmentNavigation, !isRendererInitiated, PageTransition.TYPED);
mWebContentsObserver.didFinishLoad(
frameId, mSyncURL, true, mainFrame, LifecycleState.ACTIVE);
mWebContentsObserver.didStopLoading(mSyncURL, true);
onPageFinishedHelper.waitForCallback(callCount);
onPageFinishedHelper.waitForCallback(callCount);
Assert.assertEquals(
"onPageFinished should be called only for main frame fragment navigations.",
callCount + 1, onPageFinishedHelper.getCallCount());
Assert.assertEquals(
"onPageFinished should be called only for main frame fragment navigations.",
mSyncURL.getSpec(), onPageFinishedHelper.getUrl());
}
@Test
@SmallTest
@Feature({"AndroidWebView"})
public void testDidFinishNavigation() throws Throwable {
GURL emptyUrl = GURL.emptyGURL();
boolean isInMainFrame = true;
boolean isErrorPage = false;
boolean isSameDocument = true;
boolean fragmentNavigation = false;
boolean isRendererInitiated = false;
TestAwContentsClient.DoUpdateVisitedHistoryHelper doUpdateVisitedHistoryHelper =
mContentsClient.getDoUpdateVisitedHistoryHelper();
int callCount = doUpdateVisitedHistoryHelper.getCallCount();
simulateNavigation(emptyUrl, isInMainFrame, !isErrorPage, !isSameDocument,
fragmentNavigation, isRendererInitiated, PageTransition.TYPED);
doUpdateVisitedHistoryHelper.waitForCallback(callCount);
Assert.assertEquals("doUpdateVisitedHistory should be called for any url.", callCount + 1,
doUpdateVisitedHistoryHelper.getCallCount());
Assert.assertEquals("doUpdateVisitedHistory should be called for any url.",
emptyUrl.getSpec(), doUpdateVisitedHistoryHelper.getUrl());
Assert.assertEquals(false, doUpdateVisitedHistoryHelper.getIsReload());
callCount = doUpdateVisitedHistoryHelper.getCallCount();
simulateNavigation(mExampleURL, isInMainFrame, isErrorPage, !isSameDocument,
fragmentNavigation, isRendererInitiated, PageTransition.TYPED);
doUpdateVisitedHistoryHelper.waitForCallback(callCount);
Assert.assertEquals("doUpdateVisitedHistory should be called for any url.", callCount + 1,
doUpdateVisitedHistoryHelper.getCallCount());
Assert.assertEquals("doUpdateVisitedHistory should be called for any url.",
mExampleURL.getSpec(), doUpdateVisitedHistoryHelper.getUrl());
Assert.assertEquals(false, doUpdateVisitedHistoryHelper.getIsReload());
callCount = doUpdateVisitedHistoryHelper.getCallCount();
simulateNavigation(emptyUrl, isInMainFrame, isErrorPage, !isSameDocument,
fragmentNavigation, isRendererInitiated, PageTransition.TYPED);
simulateNavigation(mExampleURL, !isInMainFrame, isErrorPage, !isSameDocument,
fragmentNavigation, isRendererInitiated, PageTransition.TYPED);
doUpdateVisitedHistoryHelper.waitForCallback(callCount);
Assert.assertEquals("doUpdateVisitedHistory should only be called for the main frame.",
callCount + 1, doUpdateVisitedHistoryHelper.getCallCount());
Assert.assertEquals("doUpdateVisitedHistory should only be called for the main frame.",
emptyUrl.getSpec(), doUpdateVisitedHistoryHelper.getUrl());
Assert.assertEquals(false, doUpdateVisitedHistoryHelper.getIsReload());
callCount = doUpdateVisitedHistoryHelper.getCallCount();
simulateNavigation(mExampleURL, isInMainFrame, isErrorPage, isSameDocument,
!fragmentNavigation, !isRendererInitiated, PageTransition.RELOAD);
doUpdateVisitedHistoryHelper.waitForCallback(callCount);
Assert.assertEquals("doUpdateVisitedHistory should be called for reloads.", callCount + 1,
doUpdateVisitedHistoryHelper.getCallCount());
Assert.assertEquals("doUpdateVisitedHistory should be called for reloads.",
mExampleURL.getSpec(), doUpdateVisitedHistoryHelper.getUrl());
Assert.assertEquals(true, doUpdateVisitedHistoryHelper.getIsReload());
}
private void simulateNavigation(GURL gurl, boolean isInPrimaryMainFrame, boolean isErrorPage,
boolean isSameDocument, boolean isFragmentNavigation, boolean isRendererInitiated,
int transition) {
NavigationHandle navigation = new NavigationHandle(0 /* navigationHandleProxy */, gurl,
isInPrimaryMainFrame, isSameDocument, isRendererInitiated, null, null);
mWebContentsObserver.didStartNavigation(navigation);
navigation.didFinish(gurl, isErrorPage, true /* hasCommitted */, isFragmentNavigation,
false /* isDownload */, false /* isValidSearchFormUrl */, transition,
0 /* errorCode*/, 200 /* httpStatusCode*/);
mWebContentsObserver.didFinishNavigation(navigation);
}
}