1 // Copyright 2013 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 package org.chromium.android_webview.test; 6 7 import android.test.suitebuilder.annotation.SmallTest; 8 import android.webkit.ValueCallback; 9 10 import org.chromium.android_webview.AwContents; 11 import org.chromium.base.test.util.Feature; 12 import org.chromium.content.browser.test.util.CallbackHelper; 13 import org.chromium.net.test.util.TestWebServer; 14 15 /** 16 * Tests for AwContentsClient.getVisitedHistory and AwContents.doUpdateVisitedHistory callbacks. 17 */ 18 public class AwContentsClientVisitedHistoryTest extends AwTestBase { 19 public static class GetVisitedHistoryHelper extends CallbackHelper { 20 private ValueCallback<String[]> mCallback; 21 private boolean mSaveCallback = false; 22 23 public ValueCallback<String[]> getCallback() { 24 assert getCallCount() > 0; 25 return mCallback; 26 } 27 28 public void setSaveCallback(boolean value) { 29 mSaveCallback = value; 30 } 31 32 public void notifyCalled(ValueCallback<String[]> callback) { 33 if (mSaveCallback) { 34 mCallback = callback; 35 } 36 notifyCalled(); 37 } 38 } 39 40 public static class DoUpdateVisitedHistoryHelper extends CallbackHelper { 41 String mUrl; 42 boolean mIsReload; 43 44 public String getUrl() { 45 assert getCallCount() > 0; 46 return mUrl; 47 } 48 49 public boolean getIsReload() { 50 assert getCallCount() > 0; 51 return mIsReload; 52 } 53 54 public void notifyCalled(String url, boolean isReload) { 55 mUrl = url; 56 mIsReload = isReload; 57 notifyCalled(); 58 } 59 } 60 61 private static class TestAwContentsClient 62 extends org.chromium.android_webview.test.TestAwContentsClient { 63 64 private GetVisitedHistoryHelper mGetVisitedHistoryHelper; 65 private DoUpdateVisitedHistoryHelper mDoUpdateVisitedHistoryHelper; 66 67 public TestAwContentsClient() { 68 mGetVisitedHistoryHelper = new GetVisitedHistoryHelper(); 69 mDoUpdateVisitedHistoryHelper = new DoUpdateVisitedHistoryHelper(); 70 } 71 72 public GetVisitedHistoryHelper getGetVisitedHistoryHelper() { 73 return mGetVisitedHistoryHelper; 74 } 75 76 public DoUpdateVisitedHistoryHelper getDoUpdateVisitedHistoryHelper() { 77 return mDoUpdateVisitedHistoryHelper; 78 } 79 80 @Override 81 public void getVisitedHistory(ValueCallback<String[]> callback) { 82 getGetVisitedHistoryHelper().notifyCalled(callback); 83 } 84 85 @Override 86 public void doUpdateVisitedHistory(String url, boolean isReload) { 87 getDoUpdateVisitedHistoryHelper().notifyCalled(url, isReload); 88 } 89 } 90 91 private TestAwContentsClient mContentsClient = new TestAwContentsClient(); 92 93 @Feature({"AndroidWebView"}) 94 @SmallTest 95 public void testUpdateVisitedHistoryCallback() throws Throwable { 96 AwTestContainerView testView = createAwTestContainerViewOnMainSync(mContentsClient); 97 AwContents awContents = testView.getAwContents(); 98 99 final String path = "/testUpdateVisitedHistoryCallback.html"; 100 final String html = "testUpdateVisitedHistoryCallback"; 101 102 TestWebServer webServer = null; 103 try { 104 webServer = new TestWebServer(false); 105 final String pageUrl = webServer.setResponse(path, html, null); 106 final DoUpdateVisitedHistoryHelper doUpdateVisitedHistoryHelper = 107 mContentsClient.getDoUpdateVisitedHistoryHelper(); 108 int callCount = doUpdateVisitedHistoryHelper.getCallCount(); 109 loadUrlAsync(awContents, pageUrl); 110 doUpdateVisitedHistoryHelper.waitForCallback(callCount); 111 assertEquals(pageUrl, doUpdateVisitedHistoryHelper.getUrl()); 112 assertEquals(false, doUpdateVisitedHistoryHelper.getIsReload()); 113 114 // Reload 115 callCount = doUpdateVisitedHistoryHelper.getCallCount(); 116 loadUrlAsync(awContents, pageUrl); 117 doUpdateVisitedHistoryHelper.waitForCallback(callCount); 118 assertEquals(pageUrl, doUpdateVisitedHistoryHelper.getUrl()); 119 assertEquals(true, doUpdateVisitedHistoryHelper.getIsReload()); 120 } finally { 121 if (webServer != null) webServer.shutdown(); 122 } 123 } 124 125 @Feature({"AndroidWebView"}) 126 @SmallTest 127 public void testGetVisitedHistoryExerciseCodePath() throws Throwable { 128 // Due to security/privacy restrictions around the :visited css property, it is not 129 // possible test this end to end without using the flaky and brittle capturing picture of 130 // the web page. So we are doing the next best thing, exercising all the code paths. 131 final GetVisitedHistoryHelper visitedHistoryHelper = 132 mContentsClient.getGetVisitedHistoryHelper(); 133 final int callCount = visitedHistoryHelper.getCallCount(); 134 visitedHistoryHelper.setSaveCallback(true); 135 136 AwTestContainerView testView = createAwTestContainerViewOnMainSync(mContentsClient); 137 AwContents awContents = testView.getAwContents(); 138 139 final String path = "/testGetVisitedHistoryExerciseCodePath.html"; 140 final String visitedLinks[] = {"http://foo.com", "http://bar.com", null}; 141 final String html = "<a src=\"http://foo.com\">foo</a><a src=\"http://bar.com\">bar</a>"; 142 143 TestWebServer webServer = null; 144 try { 145 webServer = new TestWebServer(false); 146 final String pageUrl = webServer.setResponse(path, html, null); 147 loadUrlSync(awContents, mContentsClient.getOnPageFinishedHelper(), pageUrl); 148 visitedHistoryHelper.waitForCallback(callCount); 149 assertNotNull(visitedHistoryHelper.getCallback()); 150 151 visitedHistoryHelper.getCallback().onReceiveValue(visitedLinks); 152 visitedHistoryHelper.getCallback().onReceiveValue(null); 153 154 loadUrlSync(awContents, mContentsClient.getOnPageFinishedHelper(), pageUrl); 155 } finally { 156 if (webServer != null) webServer.shutdown(); 157 } 158 } 159 160 @Feature({"AndroidWebView"}) 161 @SmallTest 162 public void testGetVisitedHistoryCallbackAfterDestroy() throws Throwable { 163 GetVisitedHistoryHelper visitedHistoryHelper = 164 mContentsClient.getGetVisitedHistoryHelper(); 165 visitedHistoryHelper.setSaveCallback(true); 166 final int callCount = visitedHistoryHelper.getCallCount(); 167 AwTestContainerView testView = createAwTestContainerViewOnMainSync(mContentsClient); 168 AwContents awContents = testView.getAwContents(); 169 loadUrlAsync(awContents, "about:blank"); 170 visitedHistoryHelper.waitForCallback(callCount); 171 assertNotNull(visitedHistoryHelper.getCallback()); 172 173 destroyAwContentsOnMainSync(awContents); 174 visitedHistoryHelper.getCallback().onReceiveValue(new String[] {"abc.def"}); 175 visitedHistoryHelper.getCallback().onReceiveValue(null); 176 } 177 } 178