1 // Copyright 2012 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.
5 package org.chromium.android_webview.test;
7 import android.content.Context;
8 import android.graphics.Point;
9 import android.os.Build;
10 import android.os.Bundle;
11 import android.os.SystemClock;
12 import android.test.suitebuilder.annotation.MediumTest;
13 import android.test.suitebuilder.annotation.SmallTest;
14 import android.view.WindowManager;
15 import android.webkit.JavascriptInterface;
16 import android.webkit.WebSettings;
18 import org.apache.http.Header;
19 import org.apache.http.HttpRequest;
20 import org.chromium.android_webview.AwContents;
21 import org.chromium.android_webview.AwSettings;
22 import org.chromium.android_webview.AwSettings.LayoutAlgorithm;
23 import org.chromium.android_webview.InterceptedRequestData;
24 import org.chromium.android_webview.test.util.CommonResources;
25 import org.chromium.android_webview.test.util.ImagePageGenerator;
26 import org.chromium.android_webview.test.util.JavascriptEventObserver;
27 import org.chromium.android_webview.test.util.VideoTestWebServer;
28 import org.chromium.base.test.util.DisabledTest;
29 import org.chromium.base.test.util.Feature;
30 import org.chromium.base.test.util.TestFileUtil;
31 import org.chromium.base.test.util.UrlUtils;
32 import org.chromium.content.browser.ContentViewCore;
33 import org.chromium.content.browser.test.util.CallbackHelper;
34 import org.chromium.content.browser.test.util.HistoryUtils;
35 import org.chromium.net.test.util.TestWebServer;
36 import org.chromium.ui.gfx.DeviceDisplayInfo;
39 import java.util.concurrent.Callable;
40 import java.util.concurrent.TimeUnit;
41 import java.util.regex.Matcher;
42 import java.util.regex.Pattern;
45 * A test suite for AwSettings class. The key objective is to verify that each
46 * settings applies either to each individual view or to all views of the
49 public class AwSettingsTest extends AwTestBase {
50 private static final boolean ENABLED = true;
51 private static final boolean DISABLED = false;
54 * A helper class for testing a particular preference from AwSettings.
55 * The generic type T is the type of the setting. Usually, to test an
56 * effect of the preference, JS code is executed that sets document's title.
57 * In this case, requiresJsEnabled constructor argument must be set to true.
59 abstract class AwSettingsTestHelper<T> {
60 protected final AwContents mAwContents;
61 protected final TestAwContentsClient mContentViewClient;
62 protected final AwSettings mAwSettings;
64 AwSettingsTestHelper(AwContents awContents,
65 TestAwContentsClient contentViewClient,
66 boolean requiresJsEnabled) throws Throwable {
67 mAwContents = awContents;
68 mContentViewClient = contentViewClient;
69 mAwSettings = AwSettingsTest.this.getAwSettingsOnUiThread(awContents);
70 if (requiresJsEnabled) {
71 mAwSettings.setJavaScriptEnabled(true);
75 void ensureSettingHasAlteredValue() throws Throwable {
76 ensureSettingHasValue(getAlteredValue());
79 void ensureSettingHasInitialValue() throws Throwable {
80 ensureSettingHasValue(getInitialValue());
83 void setAlteredSettingValue() throws Throwable {
84 setCurrentValue(getAlteredValue());
87 void setInitialSettingValue() throws Throwable {
88 setCurrentValue(getInitialValue());
91 protected abstract T getAlteredValue();
93 protected abstract T getInitialValue();
95 protected abstract T getCurrentValue();
97 protected abstract void setCurrentValue(T value) throws Throwable;
99 protected abstract void doEnsureSettingHasValue(T value) throws Throwable;
101 protected String getTitleOnUiThread() throws Exception {
102 return AwSettingsTest.this.getTitleOnUiThread(mAwContents);
105 protected void loadDataSync(String data) throws Throwable {
106 AwSettingsTest.this.loadDataSync(
108 mContentViewClient.getOnPageFinishedHelper(),
114 protected void loadUrlSync(String url) throws Throwable {
115 AwSettingsTest.this.loadUrlSync(
117 mContentViewClient.getOnPageFinishedHelper(),
121 protected void loadUrlSyncAndExpectError(String url) throws Throwable {
122 AwSettingsTest.this.loadUrlSyncAndExpectError(
124 mContentViewClient.getOnPageFinishedHelper(),
125 mContentViewClient.getOnReceivedErrorHelper(),
129 protected String executeJavaScriptAndWaitForResult(String script) throws Exception {
130 return AwSettingsTest.this.executeJavaScriptAndWaitForResult(
131 mAwContents, mContentViewClient, script);
134 private void ensureSettingHasValue(T value) throws Throwable {
135 assertEquals(value, getCurrentValue());
136 doEnsureSettingHasValue(value);
140 class AwSettingsJavaScriptTestHelper extends AwSettingsTestHelper<Boolean> {
141 private static final String JS_ENABLED_STRING = "JS Enabled";
142 private static final String JS_DISABLED_STRING = "JS Disabled";
144 AwSettingsJavaScriptTestHelper(AwContents awContents,
145 TestAwContentsClient contentViewClient) throws Throwable {
146 super(awContents, contentViewClient, false);
150 protected Boolean getAlteredValue() {
155 protected Boolean getInitialValue() {
160 protected Boolean getCurrentValue() {
161 return mAwSettings.getJavaScriptEnabled();
165 protected void setCurrentValue(Boolean value) {
166 mAwSettings.setJavaScriptEnabled(value);
170 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
171 loadDataSync(getData());
173 value == ENABLED ? JS_ENABLED_STRING : JS_DISABLED_STRING,
174 getTitleOnUiThread());
177 private String getData() {
178 return "<html><head><title>" + JS_DISABLED_STRING + "</title>"
179 + "</head><body onload=\"document.title='" + JS_ENABLED_STRING
180 + "';\"></body></html>";
184 // In contrast to AwSettingsJavaScriptTestHelper, doesn't reload the page when testing
186 class AwSettingsJavaScriptDynamicTestHelper extends AwSettingsJavaScriptTestHelper {
187 AwSettingsJavaScriptDynamicTestHelper(
188 AwContents awContents,
189 TestAwContentsClient contentViewClient) throws Throwable {
190 super(awContents, contentViewClient);
192 super.doEnsureSettingHasValue(getInitialValue());
196 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
197 String oldTitle = getTitleOnUiThread();
198 String newTitle = oldTitle + "_modified";
199 executeJavaScriptAndWaitForResult(getScript(newTitle));
200 assertEquals(value == ENABLED ? newTitle : oldTitle, getTitleOnUiThread());
203 private String getScript(String title) {
204 return "document.title='" + title + "';";
208 class AwSettingsPluginsTestHelper extends AwSettingsTestHelper<Boolean> {
209 private static final String PLUGINS_ENABLED_STRING = "Embed";
210 private static final String PLUGINS_DISABLED_STRING = "NoEmbed";
212 AwSettingsPluginsTestHelper(AwContents awContents,
213 TestAwContentsClient contentViewClient) throws Throwable {
214 super(awContents, contentViewClient, true);
218 protected Boolean getAlteredValue() {
223 protected Boolean getInitialValue() {
228 protected Boolean getCurrentValue() {
229 return mAwSettings.getPluginsEnabled();
233 protected void setCurrentValue(Boolean value) {
234 mAwSettings.setPluginsEnabled(value);
238 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
239 loadDataSync(getData());
241 value == ENABLED ? PLUGINS_ENABLED_STRING : PLUGINS_DISABLED_STRING,
242 getTitleOnUiThread());
245 private String getData() {
246 return "<html><body onload=\"document.title = document.body.innerText;\">"
247 + "<noembed>No</noembed><span>Embed</span></body></html>";
251 class AwSettingsStandardFontFamilyTestHelper extends AwSettingsTestHelper<String> {
252 AwSettingsStandardFontFamilyTestHelper(
253 AwContents awContents,
254 TestAwContentsClient contentViewClient) throws Throwable {
255 super(awContents, contentViewClient, true);
259 protected String getAlteredValue() {
264 protected String getInitialValue() {
269 protected String getCurrentValue() {
270 return mAwSettings.getStandardFontFamily();
274 protected void setCurrentValue(String value) {
275 mAwSettings.setStandardFontFamily(value);
279 protected void doEnsureSettingHasValue(String value) throws Throwable {
280 loadDataSync(getData());
281 assertEquals(value, getTitleOnUiThread());
284 private String getData() {
285 return "<html><body onload=\"document.title = " +
286 "getComputedStyle(document.body).getPropertyValue('font-family');\">"
291 class AwSettingsDefaultFontSizeTestHelper extends AwSettingsTestHelper<Integer> {
292 AwSettingsDefaultFontSizeTestHelper(
293 AwContents awContents,
294 TestAwContentsClient contentViewClient) throws Throwable {
295 super(awContents, contentViewClient, true);
299 protected Integer getAlteredValue() {
304 protected Integer getInitialValue() {
309 protected Integer getCurrentValue() {
310 return mAwSettings.getDefaultFontSize();
314 protected void setCurrentValue(Integer value) {
315 mAwSettings.setDefaultFontSize(value);
319 protected void doEnsureSettingHasValue(Integer value) throws Throwable {
320 loadDataSync(getData());
321 assertEquals(value.toString() + "px", getTitleOnUiThread());
324 private String getData() {
325 return "<html><body onload=\"document.title = " +
326 "getComputedStyle(document.body).getPropertyValue('font-size');\">"
331 class AwSettingsLoadImagesAutomaticallyTestHelper extends AwSettingsTestHelper<Boolean> {
332 private ImagePageGenerator mGenerator;
334 AwSettingsLoadImagesAutomaticallyTestHelper(
335 AwContents awContents,
336 TestAwContentsClient contentViewClient,
337 ImagePageGenerator generator) throws Throwable {
338 super(awContents, contentViewClient, true);
339 mGenerator = generator;
343 protected Boolean getAlteredValue() {
348 protected Boolean getInitialValue() {
353 protected Boolean getCurrentValue() {
354 return mAwSettings.getLoadsImagesAutomatically();
358 protected void setCurrentValue(Boolean value) {
359 mAwSettings.setLoadsImagesAutomatically(value);
363 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
364 loadDataSync(mGenerator.getPageSource());
365 assertEquals(value == ENABLED ?
366 ImagePageGenerator.IMAGE_LOADED_STRING :
367 ImagePageGenerator.IMAGE_NOT_LOADED_STRING,
368 getTitleOnUiThread());
373 class AwSettingsImagesEnabledHelper extends AwSettingsTestHelper<Boolean> {
375 AwSettingsImagesEnabledHelper(
376 AwContents awContents,
377 TestAwContentsClient contentViewClient,
378 TestWebServer webServer,
379 ImagePageGenerator generator) throws Throwable {
380 super(awContents, contentViewClient, true);
381 mWebServer = webServer;
382 mGenerator = generator;
386 protected Boolean getAlteredValue() {
391 protected Boolean getInitialValue() {
396 protected Boolean getCurrentValue() {
397 return mAwSettings.getImagesEnabled();
401 protected void setCurrentValue(Boolean value) {
402 mAwSettings.setImagesEnabled(value);
406 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
407 final String httpImageUrl = mGenerator.getPageUrl(mWebServer);
408 AwSettingsTest.this.loadUrlSync(
410 mContentViewClient.getOnPageFinishedHelper(),
412 assertEquals(value == ENABLED ?
413 ImagePageGenerator.IMAGE_LOADED_STRING :
414 ImagePageGenerator.IMAGE_NOT_LOADED_STRING,
415 getTitleOnUiThread());
418 private TestWebServer mWebServer;
419 private ImagePageGenerator mGenerator;
422 class AwSettingsDefaultTextEncodingTestHelper extends AwSettingsTestHelper<String> {
423 AwSettingsDefaultTextEncodingTestHelper(
424 AwContents awContents,
425 TestAwContentsClient contentViewClient) throws Throwable {
426 super(awContents, contentViewClient, true);
430 protected String getAlteredValue() {
435 protected String getInitialValue() {
440 protected String getCurrentValue() {
441 return mAwSettings.getDefaultTextEncodingName();
445 protected void setCurrentValue(String value) {
446 mAwSettings.setDefaultTextEncodingName(value);
450 protected void doEnsureSettingHasValue(String value) throws Throwable {
451 loadDataSync(getData());
452 assertEquals(value, getTitleOnUiThread());
455 private String getData() {
456 return "<html><body onload='document.title=document.defaultCharset'></body></html>";
460 class AwSettingsUserAgentStringTestHelper extends AwSettingsTestHelper<String> {
461 private final String mDefaultUa;
462 private static final String DEFAULT_UA = "";
463 private static final String CUSTOM_UA = "ChromeViewTest";
465 AwSettingsUserAgentStringTestHelper(
466 AwContents awContents,
467 TestAwContentsClient contentViewClient) throws Throwable {
468 super(awContents, contentViewClient, true);
469 mDefaultUa = mAwSettings.getUserAgentString();
473 protected String getAlteredValue() {
478 protected String getInitialValue() {
483 protected String getCurrentValue() {
484 // The test framework expects that getXXX() == Z after setXXX(Z).
485 // But setUserAgentString("" / null) resets the UA string to default,
486 // and getUserAgentString returns the default UA string afterwards.
487 // To align with the framework, we return an empty string instead of
489 String currentUa = mAwSettings.getUserAgentString();
490 return mDefaultUa.equals(currentUa) ? DEFAULT_UA : currentUa;
494 protected void setCurrentValue(String value) {
495 mAwSettings.setUserAgentString(value);
499 protected void doEnsureSettingHasValue(String value) throws Throwable {
500 loadDataSync(getData());
502 DEFAULT_UA.equals(value) ? mDefaultUa : value,
503 getTitleOnUiThread());
506 private String getData() {
507 return "<html><body onload='document.title=navigator.userAgent'></body></html>";
511 class AwSettingsDomStorageEnabledTestHelper extends AwSettingsTestHelper<Boolean> {
512 private static final String TEST_FILE = "webview/localStorage.html";
513 private static final String NO_LOCAL_STORAGE = "No localStorage";
514 private static final String HAS_LOCAL_STORAGE = "Has localStorage";
516 AwSettingsDomStorageEnabledTestHelper(
517 AwContents awContents,
518 TestAwContentsClient contentViewClient) throws Throwable {
519 super(awContents, contentViewClient, true);
520 AwSettingsTest.assertFileIsReadable(UrlUtils.getTestFilePath(TEST_FILE));
524 protected Boolean getAlteredValue() {
529 protected Boolean getInitialValue() {
534 protected Boolean getCurrentValue() {
535 return mAwSettings.getDomStorageEnabled();
539 protected void setCurrentValue(Boolean value) {
540 mAwSettings.setDomStorageEnabled(value);
544 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
545 // It is not permitted to access localStorage from data URLs in WebKit,
546 // that is why a standalone page must be used.
547 loadUrlSync(UrlUtils.getTestFileUrl(TEST_FILE));
549 value == ENABLED ? HAS_LOCAL_STORAGE : NO_LOCAL_STORAGE,
550 getTitleOnUiThread());
554 class AwSettingsDatabaseTestHelper extends AwSettingsTestHelper<Boolean> {
555 private static final String TEST_FILE = "webview/database_access.html";
556 private static final String NO_DATABASE = "No database";
557 private static final String HAS_DATABASE = "Has database";
559 AwSettingsDatabaseTestHelper(
560 AwContents awContents,
561 TestAwContentsClient contentViewClient) throws Throwable {
562 super(awContents, contentViewClient, true);
563 AwSettingsTest.assertFileIsReadable(UrlUtils.getTestFilePath(TEST_FILE));
567 protected Boolean getAlteredValue() {
572 protected Boolean getInitialValue() {
577 protected Boolean getCurrentValue() {
578 return mAwSettings.getDatabaseEnabled();
582 protected void setCurrentValue(Boolean value) {
583 mAwSettings.setDatabaseEnabled(value);
587 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
588 // It seems accessing the database through a data scheme is not
589 // supported, and fails with a DOM exception (likely a cross-domain
591 loadUrlSync(UrlUtils.getTestFileUrl(TEST_FILE));
593 value == ENABLED ? HAS_DATABASE : NO_DATABASE,
594 getTitleOnUiThread());
598 class AwSettingsUniversalAccessFromFilesTestHelper extends AwSettingsTestHelper<Boolean> {
599 private static final String TEST_CONTAINER_FILE = "webview/iframe_access.html";
600 private static final String TEST_FILE = "webview/hello_world.html";
601 private static final String ACCESS_DENIED_TITLE = "Exception";
603 AwSettingsUniversalAccessFromFilesTestHelper(
604 AwContents awContents,
605 TestAwContentsClient contentViewClient) throws Throwable {
606 super(awContents, contentViewClient, true);
607 AwSettingsTest.assertFileIsReadable(UrlUtils.getTestFilePath(TEST_CONTAINER_FILE));
608 AwSettingsTest.assertFileIsReadable(UrlUtils.getTestFilePath(TEST_FILE));
609 mIframeContainerUrl = UrlUtils.getTestFileUrl(TEST_CONTAINER_FILE);
610 mIframeUrl = UrlUtils.getTestFileUrl(TEST_FILE);
611 // The value of the setting depends on the SDK version.
612 mAwSettings.setAllowUniversalAccessFromFileURLs(false);
613 // If universal access is true, the value of file access doesn't
614 // matter. While if universal access is false, having file access
615 // enabled will allow file loading.
616 mAwSettings.setAllowFileAccessFromFileURLs(false);
620 protected Boolean getAlteredValue() {
625 protected Boolean getInitialValue() {
630 protected Boolean getCurrentValue() {
631 return mAwSettings.getAllowUniversalAccessFromFileURLs();
635 protected void setCurrentValue(Boolean value) {
636 mAwSettings.setAllowUniversalAccessFromFileURLs(value);
640 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
641 loadUrlSync(mIframeContainerUrl);
643 value == ENABLED ? mIframeUrl : ACCESS_DENIED_TITLE,
644 getTitleOnUiThread());
647 private final String mIframeContainerUrl;
648 private final String mIframeUrl;
651 class AwSettingsFileAccessFromFilesIframeTestHelper extends AwSettingsTestHelper<Boolean> {
652 private static final String TEST_CONTAINER_FILE = "webview/iframe_access.html";
653 private static final String TEST_FILE = "webview/hello_world.html";
654 private static final String ACCESS_DENIED_TITLE = "Exception";
656 AwSettingsFileAccessFromFilesIframeTestHelper(
657 AwContents awContents,
658 TestAwContentsClient contentViewClient) throws Throwable {
659 super(awContents, contentViewClient, true);
660 AwSettingsTest.assertFileIsReadable(UrlUtils.getTestFilePath(TEST_CONTAINER_FILE));
661 AwSettingsTest.assertFileIsReadable(UrlUtils.getTestFilePath(TEST_FILE));
662 mIframeContainerUrl = UrlUtils.getTestFileUrl(TEST_CONTAINER_FILE);
663 mIframeUrl = UrlUtils.getTestFileUrl(TEST_FILE);
664 mAwSettings.setAllowUniversalAccessFromFileURLs(false);
665 // The value of the setting depends on the SDK version.
666 mAwSettings.setAllowFileAccessFromFileURLs(false);
670 protected Boolean getAlteredValue() {
675 protected Boolean getInitialValue() {
680 protected Boolean getCurrentValue() {
681 return mAwSettings.getAllowFileAccessFromFileURLs();
685 protected void setCurrentValue(Boolean value) {
686 mAwSettings.setAllowFileAccessFromFileURLs(value);
690 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
691 loadUrlSync(mIframeContainerUrl);
693 value == ENABLED ? mIframeUrl : ACCESS_DENIED_TITLE,
694 getTitleOnUiThread());
697 private final String mIframeContainerUrl;
698 private final String mIframeUrl;
701 class AwSettingsFileAccessFromFilesXhrTestHelper extends AwSettingsTestHelper<Boolean> {
702 private static final String TEST_FILE = "webview/xhr_access.html";
703 private static final String ACCESS_GRANTED_TITLE = "Hello, World!";
704 private static final String ACCESS_DENIED_TITLE = "Exception";
706 AwSettingsFileAccessFromFilesXhrTestHelper(
707 AwContents awContents,
708 TestAwContentsClient contentViewClient) throws Throwable {
709 super(awContents, contentViewClient, true);
710 assertFileIsReadable(UrlUtils.getTestFilePath(TEST_FILE));
711 mXhrContainerUrl = UrlUtils.getTestFileUrl(TEST_FILE);
712 mAwSettings.setAllowUniversalAccessFromFileURLs(false);
713 // The value of the setting depends on the SDK version.
714 mAwSettings.setAllowFileAccessFromFileURLs(false);
718 protected Boolean getAlteredValue() {
723 protected Boolean getInitialValue() {
728 protected Boolean getCurrentValue() {
729 return mAwSettings.getAllowFileAccessFromFileURLs();
733 protected void setCurrentValue(Boolean value) {
734 mAwSettings.setAllowFileAccessFromFileURLs(value);
738 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
739 loadUrlSync(mXhrContainerUrl);
741 value == ENABLED ? ACCESS_GRANTED_TITLE : ACCESS_DENIED_TITLE,
742 getTitleOnUiThread());
745 private final String mXhrContainerUrl;
748 class AwSettingsFileUrlAccessTestHelper extends AwSettingsTestHelper<Boolean> {
749 private static final String TEST_FILE = "webview/hello_world.html";
750 private static final String ACCESS_GRANTED_TITLE = "Hello, World!";
752 AwSettingsFileUrlAccessTestHelper(
753 AwContents awContents,
754 TestAwContentsClient contentViewClient,
755 int startIndex) throws Throwable {
756 super(awContents, contentViewClient, true);
758 AwSettingsTest.assertFileIsReadable(UrlUtils.getTestFilePath(TEST_FILE));
762 protected Boolean getAlteredValue() {
767 protected Boolean getInitialValue() {
772 protected Boolean getCurrentValue() {
773 return mAwSettings.getAllowFileAccess();
777 protected void setCurrentValue(Boolean value) {
778 mAwSettings.setAllowFileAccess(value);
782 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
783 // Use query parameters to avoid hitting a cached page.
784 String fileUrl = UrlUtils.getTestFileUrl(TEST_FILE + "?id=" + mIndex);
786 if (value == ENABLED) {
787 loadUrlSync(fileUrl);
788 assertEquals(ACCESS_GRANTED_TITLE, getTitleOnUiThread());
790 loadUrlSyncAndExpectError(fileUrl);
797 class AwSettingsContentUrlAccessTestHelper extends AwSettingsTestHelper<Boolean> {
799 AwSettingsContentUrlAccessTestHelper(
800 AwContents awContents,
801 TestAwContentsClient contentViewClient,
802 int index) throws Throwable {
803 super(awContents, contentViewClient, true);
804 mTarget = "content_access_" + index;
808 protected Boolean getAlteredValue() {
813 protected Boolean getInitialValue() {
818 protected Boolean getCurrentValue() {
819 return mAwSettings.getAllowContentAccess();
823 protected void setCurrentValue(Boolean value) {
824 mAwSettings.setAllowContentAccess(value);
828 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
829 AwSettingsTest.this.resetResourceRequestCountInContentProvider(mTarget);
830 loadUrlSync(AwSettingsTest.this.createContentUrl(mTarget));
831 if (value == ENABLED) {
832 AwSettingsTest.this.ensureResourceRequestCountInContentProvider(mTarget, 1);
834 AwSettingsTest.this.ensureResourceRequestCountInContentProvider(mTarget, 0);
838 private final String mTarget;
841 class AwSettingsContentUrlAccessFromFileTestHelper extends AwSettingsTestHelper<Boolean> {
842 private static final String TARGET = "content_from_file";
844 AwSettingsContentUrlAccessFromFileTestHelper(
845 AwContents awContents,
846 TestAwContentsClient contentViewClient,
847 int index) throws Throwable {
848 super(awContents, contentViewClient, true);
850 mTempDir = getInstrumentation().getTargetContext().getCacheDir().getPath();
854 protected Boolean getAlteredValue() {
859 protected Boolean getInitialValue() {
864 protected Boolean getCurrentValue() {
865 return mAwSettings.getAllowContentAccess();
869 protected void setCurrentValue(Boolean value) {
870 mAwSettings.setAllowContentAccess(value);
874 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
875 AwSettingsTest.this.resetResourceRequestCountInContentProvider(TARGET);
876 final String fileName = mTempDir + "/" + TARGET + ".html";
878 TestFileUtil.createNewHtmlFile(fileName,
881 // Adding a query avoids hitting a cached image, and also verifies
882 // that content URL query parameters are ignored when accessing
883 // a content provider.
884 AwSettingsTest.this.createContentUrl(TARGET + "?id=" + mIndex) + "\">");
886 loadUrlSync("file://" + fileName);
887 if (value == ENABLED) {
888 AwSettingsTest.this.ensureResourceRequestCountInContentProvider(TARGET, 1);
890 AwSettingsTest.this.ensureResourceRequestCountInContentProvider(TARGET, 0);
893 TestFileUtil.deleteFile(fileName);
898 private String mTempDir;
901 // This class provides helper methods for testing of settings related to
902 // the text autosizing feature.
903 abstract class AwSettingsTextAutosizingTestHelper<T> extends AwSettingsTestHelper<T> {
904 protected static final float PARAGRAPH_FONT_SIZE = 14.0f;
906 AwSettingsTextAutosizingTestHelper(
907 AwContents awContents,
908 TestAwContentsClient contentViewClient) throws Throwable {
909 super(awContents, contentViewClient, true);
910 mNeedToWaitForFontSizeChange = false;
911 loadDataSync(getData());
915 protected void setCurrentValue(T value) throws Throwable {
916 mNeedToWaitForFontSizeChange = false;
917 if (value != getCurrentValue()) {
918 mOldFontSize = getActualFontSize();
919 mNeedToWaitForFontSizeChange = true;
923 protected float getActualFontSize() throws Throwable {
924 if (!mNeedToWaitForFontSizeChange) {
925 executeJavaScriptAndWaitForResult("setTitleToActualFontSize()");
927 final float oldFontSize = mOldFontSize;
928 poll(new Callable<Boolean>() {
930 public Boolean call() throws Exception {
931 executeJavaScriptAndWaitForResult("setTitleToActualFontSize()");
932 float newFontSize = Float.parseFloat(getTitleOnUiThread());
933 return newFontSize != oldFontSize;
936 mNeedToWaitForFontSizeChange = false;
938 return Float.parseFloat(getTitleOnUiThread());
941 protected String getData() {
942 StringBuilder sb = new StringBuilder();
945 "function setTitleToActualFontSize() {" +
946 // parseFloat is used to trim out the "px" suffix.
947 " document.title = parseFloat(getComputedStyle(" +
948 " document.getElementById('par')).getPropertyValue('font-size'));" +
949 "}</script></head>" +
951 "<p id=\"par\" style=\"font-size:");
952 sb.append(PARAGRAPH_FONT_SIZE);
954 // Make the paragraph wide enough for being processed by the font autosizer.
955 for (int i = 0; i < 100; i++) {
956 sb.append("Hello, World! ");
958 sb.append("</p></body></html>");
959 return sb.toString();
962 private boolean mNeedToWaitForFontSizeChange;
963 private float mOldFontSize;
966 class AwSettingsLayoutAlgorithmTestHelper extends
967 AwSettingsTextAutosizingTestHelper<LayoutAlgorithm> {
969 AwSettingsLayoutAlgorithmTestHelper(
970 AwContents awContents,
971 TestAwContentsClient contentViewClient) throws Throwable {
972 super(awContents, contentViewClient);
973 // Font autosizing doesn't step in for narrow layout widths.
974 mAwSettings.setUseWideViewPort(true);
978 protected LayoutAlgorithm getAlteredValue() {
979 return LayoutAlgorithm.TEXT_AUTOSIZING;
983 protected LayoutAlgorithm getInitialValue() {
984 return LayoutAlgorithm.NARROW_COLUMNS;
988 protected LayoutAlgorithm getCurrentValue() {
989 return mAwSettings.getLayoutAlgorithm();
993 protected void setCurrentValue(LayoutAlgorithm value) throws Throwable {
994 super.setCurrentValue(value);
995 mAwSettings.setLayoutAlgorithm(value);
999 protected void doEnsureSettingHasValue(LayoutAlgorithm value) throws Throwable {
1000 final float actualFontSize = getActualFontSize();
1001 if (value == LayoutAlgorithm.TEXT_AUTOSIZING) {
1002 assertFalse("Actual font size: " + actualFontSize,
1003 actualFontSize == PARAGRAPH_FONT_SIZE);
1005 assertTrue("Actual font size: " + actualFontSize,
1006 actualFontSize == PARAGRAPH_FONT_SIZE);
1011 class AwSettingsTextZoomTestHelper extends AwSettingsTextAutosizingTestHelper<Integer> {
1012 private static final int INITIAL_TEXT_ZOOM = 100;
1013 private final float mInitialActualFontSize;
1015 AwSettingsTextZoomTestHelper(
1016 AwContents awContents,
1017 TestAwContentsClient contentViewClient) throws Throwable {
1018 super(awContents, contentViewClient);
1019 mInitialActualFontSize = getActualFontSize();
1023 protected Integer getAlteredValue() {
1024 return INITIAL_TEXT_ZOOM * 2;
1028 protected Integer getInitialValue() {
1029 return INITIAL_TEXT_ZOOM;
1033 protected Integer getCurrentValue() {
1034 return mAwSettings.getTextZoom();
1038 protected void setCurrentValue(Integer value) throws Throwable {
1039 super.setCurrentValue(value);
1040 mAwSettings.setTextZoom(value);
1044 protected void doEnsureSettingHasValue(Integer value) throws Throwable {
1045 final float actualFontSize = getActualFontSize();
1046 // Ensure that actual vs. initial font size ratio is similar to actual vs. initial
1047 // text zoom values ratio.
1048 final float ratiosDelta = Math.abs(
1049 (actualFontSize / mInitialActualFontSize) -
1050 (value / (float) INITIAL_TEXT_ZOOM));
1052 "|(" + actualFontSize + " / " + mInitialActualFontSize + ") - (" +
1053 value + " / " + INITIAL_TEXT_ZOOM + ")| = " + ratiosDelta,
1054 ratiosDelta <= 0.2f);
1058 class AwSettingsTextZoomAutosizingTestHelper
1059 extends AwSettingsTextAutosizingTestHelper<Integer> {
1060 private static final int INITIAL_TEXT_ZOOM = 100;
1061 private final float mInitialActualFontSize;
1063 AwSettingsTextZoomAutosizingTestHelper(
1064 AwContents awContents,
1065 TestAwContentsClient contentViewClient) throws Throwable {
1066 super(awContents, contentViewClient);
1067 mAwSettings.setLayoutAlgorithm(LayoutAlgorithm.TEXT_AUTOSIZING);
1068 // The initial font size can be adjusted by font autosizer depending on the page's
1070 mInitialActualFontSize = getActualFontSize();
1074 protected Integer getAlteredValue() {
1075 return INITIAL_TEXT_ZOOM * 2;
1079 protected Integer getInitialValue() {
1080 return INITIAL_TEXT_ZOOM;
1084 protected Integer getCurrentValue() {
1085 return mAwSettings.getTextZoom();
1089 protected void setCurrentValue(Integer value) throws Throwable {
1090 super.setCurrentValue(value);
1091 mAwSettings.setTextZoom(value);
1095 protected void doEnsureSettingHasValue(Integer value) throws Throwable {
1096 final float actualFontSize = getActualFontSize();
1097 // Ensure that actual vs. initial font size ratio is similar to actual vs. initial
1098 // text zoom values ratio.
1099 final float ratiosDelta = Math.abs(
1100 (actualFontSize / mInitialActualFontSize) -
1101 (value / (float) INITIAL_TEXT_ZOOM));
1103 "|(" + actualFontSize + " / " + mInitialActualFontSize + ") - (" +
1104 value + " / " + INITIAL_TEXT_ZOOM + ")| = " + ratiosDelta,
1105 ratiosDelta <= 0.2f);
1109 class AwSettingsJavaScriptPopupsTestHelper extends AwSettingsTestHelper<Boolean> {
1110 private static final String POPUP_ENABLED = "Popup enabled";
1111 private static final String POPUP_BLOCKED = "Popup blocked";
1113 AwSettingsJavaScriptPopupsTestHelper(
1114 AwContents awContents,
1115 TestAwContentsClient contentViewClient) throws Throwable {
1116 super(awContents, contentViewClient, true);
1120 protected Boolean getAlteredValue() {
1125 protected Boolean getInitialValue() {
1130 protected Boolean getCurrentValue() {
1131 return mAwSettings.getJavaScriptCanOpenWindowsAutomatically();
1135 protected void setCurrentValue(Boolean value) {
1136 mAwSettings.setJavaScriptCanOpenWindowsAutomatically(value);
1140 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
1141 loadDataSync(getData());
1142 final boolean expectPopupEnabled = value;
1143 poll(new Callable<Boolean>() {
1145 public Boolean call() throws Exception {
1146 String title = getTitleOnUiThread();
1147 return expectPopupEnabled ? POPUP_ENABLED.equals(title) :
1148 POPUP_BLOCKED.equals(title);
1151 assertEquals(value ? POPUP_ENABLED : POPUP_BLOCKED, getTitleOnUiThread());
1154 private String getData() {
1155 return "<html><head>" +
1157 " function tryOpenWindow() {" +
1158 " var newWindow = window.open(" +
1159 " 'data:text/html;charset=utf-8," +
1160 " <html><head><title>" + POPUP_ENABLED + "</title></head></html>');" +
1161 " if (!newWindow) document.title = '" + POPUP_BLOCKED + "';" +
1163 "</script></head>" +
1164 "<body onload='tryOpenWindow()'></body></html>";
1168 class AwSettingsCacheModeTestHelper extends AwSettingsTestHelper<Integer> {
1170 AwSettingsCacheModeTestHelper(
1171 AwContents awContents,
1172 TestAwContentsClient contentViewClient,
1174 TestWebServer webServer) throws Throwable {
1175 super(awContents, contentViewClient, true);
1177 mWebServer = webServer;
1181 protected Integer getAlteredValue() {
1182 // We use the value that results in a behaviour completely opposite to default.
1183 return WebSettings.LOAD_CACHE_ONLY;
1187 protected Integer getInitialValue() {
1188 return WebSettings.LOAD_DEFAULT;
1192 protected Integer getCurrentValue() {
1193 return mAwSettings.getCacheMode();
1197 protected void setCurrentValue(Integer value) {
1198 mAwSettings.setCacheMode(value);
1202 protected void doEnsureSettingHasValue(Integer value) throws Throwable {
1203 final String htmlPath = "/cache_mode_" + mIndex + ".html";
1205 final String url = mWebServer.setResponse(htmlPath, "response", null);
1206 assertEquals(0, mWebServer.getRequestCount(htmlPath));
1207 if (value == WebSettings.LOAD_DEFAULT) {
1209 assertEquals(1, mWebServer.getRequestCount(htmlPath));
1211 loadUrlSyncAndExpectError(url);
1212 assertEquals(0, mWebServer.getRequestCount(htmlPath));
1217 private TestWebServer mWebServer;
1220 // To verify whether UseWideViewport works, we check, if the page width specified
1221 // in the "meta viewport" tag is applied. When UseWideViewport is turned off, the
1222 // "viewport" tag is ignored, and the layout width is set to device width in DIP pixels.
1223 // We specify a very high width value to make sure that it doesn't intersect with
1224 // device screen widths (in DIP pixels).
1225 class AwSettingsUseWideViewportTestHelper extends AwSettingsTestHelper<Boolean> {
1226 private static final String VIEWPORT_TAG_LAYOUT_WIDTH = "3000";
1228 AwSettingsUseWideViewportTestHelper(
1229 AwContents awContents,
1230 TestAwContentsClient contentViewClient) throws Throwable {
1231 super(awContents, contentViewClient, true);
1235 protected Boolean getAlteredValue() {
1240 protected Boolean getInitialValue() {
1245 protected Boolean getCurrentValue() {
1246 return mAwSettings.getUseWideViewPort();
1250 protected void setCurrentValue(Boolean value) {
1251 mAwSettings.setUseWideViewPort(value);
1255 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
1256 loadDataSync(getData());
1257 final String bodyWidth = getTitleOnUiThread();
1259 assertTrue(bodyWidth, VIEWPORT_TAG_LAYOUT_WIDTH.equals(bodyWidth));
1261 assertFalse(bodyWidth, VIEWPORT_TAG_LAYOUT_WIDTH.equals(bodyWidth));
1265 private String getData() {
1266 return "<html><head>" +
1267 "<meta name='viewport' content='width=" + VIEWPORT_TAG_LAYOUT_WIDTH + "' />" +
1269 "<body onload='document.title=document.body.clientWidth'></body></html>";
1273 class AwSettingsLoadWithOverviewModeTestHelper extends AwSettingsTestHelper<Boolean> {
1274 private static final float DEFAULT_PAGE_SCALE = 1.0f;
1276 AwSettingsLoadWithOverviewModeTestHelper(
1277 AwContents awContents,
1278 TestAwContentsClient contentViewClient,
1279 boolean withViewPortTag) throws Throwable {
1280 super(awContents, contentViewClient, true);
1281 mWithViewPortTag = withViewPortTag;
1282 mAwSettings.setUseWideViewPort(true);
1286 protected Boolean getAlteredValue() {
1291 protected Boolean getInitialValue() {
1296 protected Boolean getCurrentValue() {
1297 return mAwSettings.getLoadWithOverviewMode();
1301 protected void setCurrentValue(Boolean value) {
1302 mExpectScaleChange = mAwSettings.getLoadWithOverviewMode() != value;
1303 if (mExpectScaleChange) {
1304 mOnScaleChangedCallCount =
1305 mContentViewClient.getOnScaleChangedHelper().getCallCount();
1307 mAwSettings.setLoadWithOverviewMode(value);
1311 protected void doEnsureSettingHasValue(Boolean value) throws Throwable {
1312 loadDataSync(getData());
1313 if (mExpectScaleChange) {
1314 mContentViewClient.getOnScaleChangedHelper().
1315 waitForCallback(mOnScaleChangedCallCount);
1316 mExpectScaleChange = false;
1318 float currentScale = AwSettingsTest.this.getScaleOnUiThread(mAwContents);
1320 assertTrue("Expected: " + currentScale + " < " + DEFAULT_PAGE_SCALE,
1321 currentScale < DEFAULT_PAGE_SCALE);
1323 assertEquals(DEFAULT_PAGE_SCALE, currentScale);
1327 private String getData() {
1328 return "<html><head>" +
1329 (mWithViewPortTag ? "<meta name='viewport' content='width=3000' />" : "") +
1331 "<body></body></html>";
1334 private final boolean mWithViewPortTag;
1335 private boolean mExpectScaleChange;
1336 private int mOnScaleChangedCallCount;
1339 // The test verifies that JavaScript is disabled upon WebView
1340 // creation without accessing AwSettings. If the test passes,
1341 // it means that WebView-specific web preferences configuration
1342 // is applied on WebView creation. JS state is used, because it is
1343 // enabled by default in Chrome, but must be disabled by default
1346 @Feature({"AndroidWebView", "Preferences"})
1347 public void testJavaScriptDisabledByDefault() throws Throwable {
1348 final String JS_ENABLED_STRING = "JS has run";
1349 final String JS_DISABLED_STRING = "JS has not run";
1350 final String TEST_PAGE_HTML =
1351 "<html><head><title>" + JS_DISABLED_STRING + "</title>"
1352 + "</head><body onload=\"document.title='" + JS_ENABLED_STRING
1353 + "';\"></body></html>";
1354 final TestAwContentsClient contentClient = new TestAwContentsClient();
1355 final AwTestContainerView testContainerView =
1356 createAwTestContainerViewOnMainSync(contentClient);
1357 final AwContents awContents = testContainerView.getAwContents();
1360 contentClient.getOnPageFinishedHelper(),
1364 assertEquals(JS_DISABLED_STRING, getTitleOnUiThread(awContents));
1368 @Feature({"AndroidWebView", "Preferences"})
1369 public void testJavaScriptEnabledWithTwoViews() throws Throwable {
1370 ViewPair views = createViews();
1371 runPerViewSettingsTest(
1372 new AwSettingsJavaScriptTestHelper(views.getContents0(), views.getClient0()),
1373 new AwSettingsJavaScriptTestHelper(views.getContents1(), views.getClient1()));
1377 @Feature({"AndroidWebView", "Preferences"})
1378 public void testJavaScriptEnabledDynamicWithTwoViews() throws Throwable {
1379 ViewPair views = createViews();
1380 runPerViewSettingsTest(
1381 new AwSettingsJavaScriptDynamicTestHelper(views.getContents0(), views.getClient0()),
1382 new AwSettingsJavaScriptDynamicTestHelper(views.getContents1(), views.getClient1()));
1386 @Feature({"AndroidWebView", "Preferences"})
1387 public void testPluginsEnabledWithTwoViews() throws Throwable {
1388 ViewPair views = createViews();
1389 runPerViewSettingsTest(
1390 new AwSettingsPluginsTestHelper(views.getContents0(), views.getClient0()),
1391 new AwSettingsPluginsTestHelper(views.getContents1(), views.getClient1()));
1395 @Feature({"AndroidWebView", "Preferences"})
1396 public void testStandardFontFamilyWithTwoViews() throws Throwable {
1397 ViewPair views = createViews();
1398 runPerViewSettingsTest(
1399 new AwSettingsStandardFontFamilyTestHelper(views.getContents0(), views.getClient0()),
1400 new AwSettingsStandardFontFamilyTestHelper(views.getContents1(), views.getClient1()));
1404 @Feature({"AndroidWebView", "Preferences"})
1405 public void testDefaultFontSizeWithTwoViews() throws Throwable {
1406 ViewPair views = createViews();
1407 runPerViewSettingsTest(
1408 new AwSettingsDefaultFontSizeTestHelper(views.getContents0(), views.getClient0()),
1409 new AwSettingsDefaultFontSizeTestHelper(views.getContents1(), views.getClient1()));
1412 // The test verifies that after changing the LoadsImagesAutomatically
1413 // setting value from false to true previously skipped images are
1414 // automatically loaded.
1416 @Feature({"AndroidWebView", "Preferences"})
1417 public void testLoadsImagesAutomaticallyNoPageReload() throws Throwable {
1418 final TestAwContentsClient contentClient = new TestAwContentsClient();
1419 final AwTestContainerView testContainerView =
1420 createAwTestContainerViewOnMainSync(contentClient);
1421 final AwContents awContents = testContainerView.getAwContents();
1422 AwSettings settings = getAwSettingsOnUiThread(awContents);
1423 settings.setJavaScriptEnabled(true);
1424 ImagePageGenerator generator = new ImagePageGenerator(0, false);
1425 settings.setLoadsImagesAutomatically(false);
1426 loadDataSync(awContents,
1427 contentClient.getOnPageFinishedHelper(),
1428 generator.getPageSource(),
1429 "text/html", false);
1430 assertEquals(ImagePageGenerator.IMAGE_NOT_LOADED_STRING,
1431 getTitleOnUiThread(awContents));
1432 settings.setLoadsImagesAutomatically(true);
1433 poll(new Callable<Boolean>() {
1435 public Boolean call() throws Exception {
1436 return !ImagePageGenerator.IMAGE_NOT_LOADED_STRING.equals(
1437 getTitleOnUiThread(awContents));
1440 assertEquals(ImagePageGenerator.IMAGE_LOADED_STRING, getTitleOnUiThread(awContents));
1445 @Feature({"AndroidWebView", "Preferences"})
1446 public void testLoadsImagesAutomaticallyWithTwoViews() throws Throwable {
1447 ViewPair views = createViews();
1448 runPerViewSettingsTest(
1449 new AwSettingsLoadImagesAutomaticallyTestHelper(
1450 views.getContents0(), views.getClient0(), new ImagePageGenerator(0, true)),
1451 new AwSettingsLoadImagesAutomaticallyTestHelper(
1452 views.getContents1(), views.getClient1(), new ImagePageGenerator(1, true)));
1456 @Feature({"AndroidWebView", "Preferences"})
1457 public void testDefaultTextEncodingWithTwoViews() throws Throwable {
1458 ViewPair views = createViews();
1459 runPerViewSettingsTest(
1460 new AwSettingsDefaultTextEncodingTestHelper(views.getContents0(), views.getClient0()),
1461 new AwSettingsDefaultTextEncodingTestHelper(views.getContents1(), views.getClient1()));
1464 // The test verifies that the default user agent string follows the format
1465 // defined in Android CTS tests:
1467 // Mozilla/5.0 (Linux;[ U;] Android <version>;[ <language>-<country>;]
1468 // [<devicemodel>;] Build/<buildID>) AppleWebKit/<major>.<minor> (KHTML, like Gecko)
1469 // Version/<major>.<minor>[ Mobile] Safari/<major>.<minor>
1471 @Feature({"AndroidWebView", "Preferences"})
1472 public void testUserAgentStringDefault() throws Throwable {
1473 final TestAwContentsClient contentClient = new TestAwContentsClient();
1474 final AwTestContainerView testContainerView =
1475 createAwTestContainerViewOnMainSync(contentClient);
1476 final AwContents awContents = testContainerView.getAwContents();
1477 AwSettings settings = getAwSettingsOnUiThread(awContents);
1478 final String actualUserAgentString = settings.getUserAgentString();
1479 assertEquals(actualUserAgentString, AwSettings.getDefaultUserAgent());
1480 final String patternString =
1481 "Mozilla/5\\.0 \\(Linux;( U;)? Android ([^;]+);( (\\w+)-(\\w+);)?" +
1482 "\\s?(.*)\\sBuild/(.+)\\) AppleWebKit/(\\d+)\\.(\\d+) \\(KHTML, like Gecko\\) " +
1483 "Version/\\d+\\.\\d Chrome/\\d+\\.\\d+\\.\\d+\\.\\d+" +
1484 "( Mobile)? Safari/(\\d+)\\.(\\d+)";
1485 final Pattern userAgentExpr = Pattern.compile(patternString);
1486 Matcher patternMatcher = userAgentExpr.matcher(actualUserAgentString);
1487 assertTrue(String.format("User agent string did not match expected pattern. %nExpected " +
1488 "pattern:%n%s%nActual:%n%s", patternString, actualUserAgentString),
1489 patternMatcher.find());
1490 // No country-language code token.
1491 assertEquals(null, patternMatcher.group(3));
1492 if ("REL".equals(Build.VERSION.CODENAME)) {
1493 // Model is only added in release builds
1494 assertEquals(Build.MODEL, patternMatcher.group(6));
1495 // Release version is valid only in release builds
1496 assertEquals(Build.VERSION.RELEASE, patternMatcher.group(2));
1498 assertEquals(Build.ID, patternMatcher.group(7));
1502 @Feature({"AndroidWebView", "Preferences"})
1503 public void testUserAgentStringOverride() throws Throwable {
1504 final TestAwContentsClient contentClient = new TestAwContentsClient();
1505 final AwTestContainerView testContainerView =
1506 createAwTestContainerViewOnMainSync(contentClient);
1507 final AwContents awContents = testContainerView.getAwContents();
1508 AwSettings settings = getAwSettingsOnUiThread(awContents);
1509 final String defaultUserAgentString = settings.getUserAgentString();
1511 // Check that an attempt to reset the default UA string has no effect.
1512 settings.setUserAgentString(null);
1513 assertEquals(defaultUserAgentString, settings.getUserAgentString());
1514 settings.setUserAgentString("");
1515 assertEquals(defaultUserAgentString, settings.getUserAgentString());
1517 // Check that we can also set the default value.
1518 settings.setUserAgentString(defaultUserAgentString);
1519 assertEquals(defaultUserAgentString, settings.getUserAgentString());
1521 // Set a custom UA string, verify that it can be reset back to default.
1522 final String customUserAgentString = "AwSettingsTest";
1523 settings.setUserAgentString(customUserAgentString);
1524 assertEquals(customUserAgentString, settings.getUserAgentString());
1525 settings.setUserAgentString(null);
1526 assertEquals(defaultUserAgentString, settings.getUserAgentString());
1529 // Verify that the current UA override setting has a priority over UA
1530 // overrides in navigation history entries.
1532 @Feature({"AndroidWebView", "Preferences"})
1533 public void testUserAgentStringOverrideForHistory() throws Throwable {
1534 final TestAwContentsClient contentClient = new TestAwContentsClient();
1535 final AwTestContainerView testContainerView =
1536 createAwTestContainerViewOnMainSync(contentClient);
1537 final AwContents awContents = testContainerView.getAwContents();
1538 final ContentViewCore contentView = testContainerView.getContentViewCore();
1539 CallbackHelper onPageFinishedHelper = contentClient.getOnPageFinishedHelper();
1540 AwSettings settings = getAwSettingsOnUiThread(awContents);
1541 settings.setJavaScriptEnabled(true);
1542 final String defaultUserAgentString = settings.getUserAgentString();
1543 final String customUserAgentString = "AwSettingsTest";
1544 // We are using different page titles to make sure that we are really
1545 // going back and forward between them.
1546 final String pageTemplate =
1547 "<html><head><title>%s</title></head>" +
1548 "<body onload='document.title+=navigator.userAgent'></body>" +
1550 final String page1Title = "Page1";
1551 final String page2Title = "Page2";
1552 final String page1 = String.format(pageTemplate, page1Title);
1553 final String page2 = String.format(pageTemplate, page2Title);
1554 settings.setUserAgentString(customUserAgentString);
1556 awContents, onPageFinishedHelper, page1, "text/html", false);
1557 assertEquals(page1Title + customUserAgentString, getTitleOnUiThread(awContents));
1559 awContents, onPageFinishedHelper, page2, "text/html", false);
1560 assertEquals(page2Title + customUserAgentString, getTitleOnUiThread(awContents));
1561 settings.setUserAgentString(null);
1562 // Must not cause any changes until the next page loading.
1563 assertEquals(page2Title + customUserAgentString, getTitleOnUiThread(awContents));
1564 HistoryUtils.goBackSync(getInstrumentation(), contentView, onPageFinishedHelper);
1565 assertEquals(page1Title + defaultUserAgentString, getTitleOnUiThread(awContents));
1566 HistoryUtils.goForwardSync(getInstrumentation(), contentView,
1567 onPageFinishedHelper);
1568 assertEquals(page2Title + defaultUserAgentString, getTitleOnUiThread(awContents));
1572 @Feature({"AndroidWebView", "Preferences"})
1573 public void testUserAgentStringWithTwoViews() throws Throwable {
1574 ViewPair views = createViews();
1575 runPerViewSettingsTest(
1576 new AwSettingsUserAgentStringTestHelper(views.getContents0(), views.getClient0()),
1577 new AwSettingsUserAgentStringTestHelper(views.getContents1(), views.getClient1()));
1581 @Feature({"AndroidWebView", "Preferences"})
1582 public void testUserAgentWithTestServer() throws Throwable {
1583 final TestAwContentsClient contentClient = new TestAwContentsClient();
1584 final AwTestContainerView testContainerView =
1585 createAwTestContainerViewOnMainSync(contentClient);
1586 AwContents awContents = testContainerView.getAwContents();
1587 AwSettings settings = getAwSettingsOnUiThread(awContents);
1588 final String customUserAgentString =
1589 "testUserAgentWithTestServerUserAgent";
1591 TestWebServer webServer = null;
1592 String fileName = null;
1594 webServer = new TestWebServer(false);
1595 final String httpPath = "/testUserAgentWithTestServer.html";
1596 final String url = webServer.setResponse(httpPath, "foo", null);
1598 settings.setUserAgentString(customUserAgentString);
1599 loadUrlSync(awContents,
1600 contentClient.getOnPageFinishedHelper(),
1603 assertEquals(1, webServer.getRequestCount(httpPath));
1604 HttpRequest request = webServer.getLastRequest(httpPath);
1605 Header[] matchingHeaders = request.getHeaders("User-Agent");
1606 assertEquals(1, matchingHeaders.length);
1608 Header header = matchingHeaders[0];
1609 assertEquals(customUserAgentString, header.getValue());
1611 if (webServer != null) webServer.shutdown();
1616 @Feature({"AndroidWebView", "Preferences"})
1617 public void testDomStorageEnabledWithTwoViews() throws Throwable {
1618 ViewPair views = createViews();
1619 runPerViewSettingsTest(
1620 new AwSettingsDomStorageEnabledTestHelper(views.getContents0(), views.getClient0()),
1621 new AwSettingsDomStorageEnabledTestHelper(views.getContents1(), views.getClient1()));
1624 // Ideally, these three tests below should be combined into one, or tested using
1625 // runPerViewSettingsTest. However, it seems the database setting cannot be toggled
1626 // once set. Filed b/8186497.
1628 @Feature({"AndroidWebView", "Preferences"})
1629 public void testDatabaseInitialValue() throws Throwable {
1630 TestAwContentsClient client = new TestAwContentsClient();
1631 final AwTestContainerView testContainerView =
1632 createAwTestContainerViewOnMainSync(client);
1633 final AwContents awContents = testContainerView.getAwContents();
1634 AwSettingsDatabaseTestHelper helper = new AwSettingsDatabaseTestHelper(awContents, client);
1635 helper.ensureSettingHasInitialValue();
1639 @Feature({"AndroidWebView", "Preferences"})
1640 public void testDatabaseEnabled() throws Throwable {
1641 TestAwContentsClient client = new TestAwContentsClient();
1642 final AwTestContainerView testContainerView =
1643 createAwTestContainerViewOnMainSync(client);
1644 final AwContents awContents = testContainerView.getAwContents();
1645 AwSettingsDatabaseTestHelper helper = new AwSettingsDatabaseTestHelper(awContents, client);
1646 helper.setAlteredSettingValue();
1647 helper.ensureSettingHasAlteredValue();
1651 @Feature({"AndroidWebView", "Preferences"})
1652 public void testDatabaseDisabled() throws Throwable {
1653 TestAwContentsClient client = new TestAwContentsClient();
1654 final AwTestContainerView testContainerView =
1655 createAwTestContainerViewOnMainSync(client);
1656 final AwContents awContents = testContainerView.getAwContents();
1657 AwSettingsDatabaseTestHelper helper = new AwSettingsDatabaseTestHelper(awContents, client);
1658 helper.setInitialSettingValue();
1659 helper.ensureSettingHasInitialValue();
1663 @Feature({"AndroidWebView", "Preferences"})
1664 public void testUniversalAccessFromFilesWithTwoViews() throws Throwable {
1665 ViewPair views = createViews();
1666 runPerViewSettingsTest(
1667 new AwSettingsUniversalAccessFromFilesTestHelper(views.getContents0(),
1668 views.getClient0()),
1669 new AwSettingsUniversalAccessFromFilesTestHelper(views.getContents1(),
1670 views.getClient1()));
1673 // This test verifies that local image resources can be loaded from file:
1674 // URLs regardless of file access state.
1676 @Feature({"AndroidWebView", "Preferences"})
1677 public void testFileAccessFromFilesImage() throws Throwable {
1678 final String testFile = "webview/image_access.html";
1679 assertFileIsReadable(UrlUtils.getTestFilePath(testFile));
1680 final String imageContainerUrl = UrlUtils.getTestFileUrl(testFile);
1681 final String imageHeight = "16";
1682 final TestAwContentsClient contentClient = new TestAwContentsClient();
1683 final AwTestContainerView testContainerView =
1684 createAwTestContainerViewOnMainSync(contentClient);
1685 final AwContents awContents = testContainerView.getAwContents();
1686 AwSettings settings = getAwSettingsOnUiThread(awContents);
1687 settings.setJavaScriptEnabled(true);
1688 settings.setAllowUniversalAccessFromFileURLs(false);
1689 settings.setAllowFileAccessFromFileURLs(false);
1690 loadUrlSync(awContents, contentClient.getOnPageFinishedHelper(), imageContainerUrl);
1691 assertEquals(imageHeight, getTitleOnUiThread(awContents));
1695 @Feature({"AndroidWebView", "Preferences"})
1696 public void testFileAccessFromFilesIframeWithTwoViews() throws Throwable {
1697 ViewPair views = createViews();
1698 runPerViewSettingsTest(
1699 new AwSettingsFileAccessFromFilesIframeTestHelper(
1700 views.getContents0(), views.getClient0()),
1701 new AwSettingsFileAccessFromFilesIframeTestHelper(
1702 views.getContents1(), views.getClient1()));
1706 @Feature({"AndroidWebView", "Preferences"})
1707 public void testFileAccessFromFilesXhrWithTwoViews() throws Throwable {
1708 ViewPair views = createViews();
1709 runPerViewSettingsTest(
1710 new AwSettingsFileAccessFromFilesXhrTestHelper(views.getContents0(),
1711 views.getClient0()),
1712 new AwSettingsFileAccessFromFilesXhrTestHelper(views.getContents1(),
1713 views.getClient1()));
1717 @Feature({"AndroidWebView", "Preferences"})
1718 public void testFileUrlAccessWithTwoViews() throws Throwable {
1719 ViewPair views = createViews();
1720 runPerViewSettingsTest(
1721 new AwSettingsFileUrlAccessTestHelper(views.getContents0(), views.getClient0(), 0),
1722 new AwSettingsFileUrlAccessTestHelper(views.getContents1(), views.getClient1(), 1));
1726 @Feature({"AndroidWebView", "Preferences"})
1727 public void testContentUrlAccessWithTwoViews() throws Throwable {
1728 ViewPair views = createViews();
1729 runPerViewSettingsTest(
1730 new AwSettingsContentUrlAccessTestHelper(views.getContents0(), views.getClient0(), 0),
1731 new AwSettingsContentUrlAccessTestHelper(views.getContents1(), views.getClient1(), 1));
1735 @Feature({"AndroidWebView", "Preferences", "Navigation"})
1736 public void testBlockingContentUrlsFromDataUrls() throws Throwable {
1737 final TestAwContentsClient contentClient = new TestAwContentsClient();
1738 final AwTestContainerView testContainerView =
1739 createAwTestContainerViewOnMainSync(contentClient);
1740 final AwContents awContents = testContainerView.getAwContents();
1741 final String target = "content_from_data";
1742 final String page = "<html><body>" +
1744 createContentUrl(target) + "\">" +
1746 resetResourceRequestCountInContentProvider(target);
1749 contentClient.getOnPageFinishedHelper(),
1753 ensureResourceRequestCountInContentProvider(target, 0);
1757 @Feature({"AndroidWebView", "Preferences", "Navigation"})
1758 public void testContentUrlFromFileWithTwoViews() throws Throwable {
1759 ViewPair views = createViews();
1760 runPerViewSettingsTest(
1761 new AwSettingsContentUrlAccessFromFileTestHelper(
1762 views.getContents0(), views.getClient0(), 0),
1763 new AwSettingsContentUrlAccessFromFileTestHelper(
1764 views.getContents1(), views.getClient1(), 1));
1768 @Feature({"AndroidWebView", "Preferences"})
1769 public void testBlockNetworkImagesDoesNotBlockDataUrlImage() throws Throwable {
1770 final TestAwContentsClient contentClient = new TestAwContentsClient();
1771 final AwTestContainerView testContainerView =
1772 createAwTestContainerViewOnMainSync(contentClient);
1773 final AwContents awContents = testContainerView.getAwContents();
1774 final AwSettings settings = getAwSettingsOnUiThread(awContents);
1775 ImagePageGenerator generator = new ImagePageGenerator(0, false);
1777 settings.setJavaScriptEnabled(true);
1778 settings.setImagesEnabled(false);
1779 loadDataSync(awContents,
1780 contentClient.getOnPageFinishedHelper(),
1781 generator.getPageSource(),
1784 assertEquals(ImagePageGenerator.IMAGE_LOADED_STRING, getTitleOnUiThread(awContents));
1788 @Feature({"AndroidWebView", "Preferences"})
1789 public void testBlockNetworkImagesBlocksNetworkImageAndReloadInPlace() throws Throwable {
1790 final TestAwContentsClient contentClient = new TestAwContentsClient();
1791 final AwTestContainerView testContainerView =
1792 createAwTestContainerViewOnMainSync(contentClient);
1793 final AwContents awContents = testContainerView.getAwContents();
1794 final AwSettings settings = getAwSettingsOnUiThread(awContents);
1795 settings.setJavaScriptEnabled(true);
1796 ImagePageGenerator generator = new ImagePageGenerator(0, false);
1798 TestWebServer webServer = null;
1800 webServer = new TestWebServer(false);
1801 final String httpImageUrl = generator.getPageUrl(webServer);
1803 settings.setImagesEnabled(false);
1804 loadUrlSync(awContents, contentClient.getOnPageFinishedHelper(), httpImageUrl);
1805 assertEquals(ImagePageGenerator.IMAGE_NOT_LOADED_STRING,
1806 getTitleOnUiThread(awContents));
1808 settings.setImagesEnabled(true);
1809 poll(new Callable<Boolean>() {
1811 public Boolean call() throws Exception {
1812 return ImagePageGenerator.IMAGE_LOADED_STRING.equals(
1813 getTitleOnUiThread(awContents));
1817 if (webServer != null) webServer.shutdown();
1822 @Feature({"AndroidWebView", "Preferences"})
1823 public void testBlockNetworkImagesWithTwoViews() throws Throwable {
1824 ViewPair views = createViews();
1825 TestWebServer webServer = null;
1827 webServer = new TestWebServer(false);
1828 runPerViewSettingsTest(
1829 new AwSettingsImagesEnabledHelper(
1830 views.getContents0(),
1833 new ImagePageGenerator(0, true)),
1834 new AwSettingsImagesEnabledHelper(
1835 views.getContents1(),
1838 new ImagePageGenerator(1, true)));
1840 if (webServer != null) webServer.shutdown();
1845 @Feature({"AndroidWebView", "Preferences"})
1846 public void testBlockNetworkLoadsWithHttpResources() throws Throwable {
1847 final TestAwContentsClient contentClient = new TestAwContentsClient();
1848 final AwTestContainerView testContainer =
1849 createAwTestContainerViewOnMainSync(contentClient);
1850 final AwContents awContents = testContainer.getAwContents();
1851 final AwSettings awSettings = getAwSettingsOnUiThread(awContents);
1852 awSettings.setJavaScriptEnabled(true);
1853 ImagePageGenerator generator = new ImagePageGenerator(0, false);
1855 TestWebServer webServer = null;
1856 String fileName = null;
1858 // Set up http image.
1859 webServer = new TestWebServer(false);
1860 final String httpPath = "/image.png";
1861 final String imageUrl = webServer.setResponseBase64(
1862 httpPath, generator.getImageSourceNoAdvance(),
1863 CommonResources.getImagePngHeaders(true));
1865 // Set up file html that loads http iframe.
1866 String pageHtml = "<img src='" + imageUrl + "' " +
1867 "onload=\"document.title='img_onload_fired';\" " +
1868 "onerror=\"document.title='img_onerror_fired';\" />";
1869 Context context = getInstrumentation().getTargetContext();
1870 fileName = context.getCacheDir() + "/block_network_loads_test.html";
1871 TestFileUtil.deleteFile(fileName); // Remove leftover file if any.
1872 TestFileUtil.createNewHtmlFile(fileName, "unset", pageHtml);
1874 // Actual test. Blocking should trigger onerror handler.
1875 awSettings.setBlockNetworkLoads(true);
1878 contentClient.getOnPageFinishedHelper(),
1879 "file:///" + fileName);
1880 assertEquals(0, webServer.getRequestCount(httpPath));
1881 assertEquals("img_onerror_fired", getTitleOnUiThread(awContents));
1883 // Unblock should load normally.
1884 awSettings.setBlockNetworkLoads(false);
1887 contentClient.getOnPageFinishedHelper(),
1888 "file:///" + fileName);
1889 assertEquals(1, webServer.getRequestCount(httpPath));
1890 assertEquals("img_onload_fired", getTitleOnUiThread(awContents));
1892 if (fileName != null) TestFileUtil.deleteFile(fileName);
1893 if (webServer != null) webServer.shutdown();
1897 private static class AudioEvent {
1898 private CallbackHelper mCallback;
1899 public AudioEvent(CallbackHelper callback) {
1900 mCallback = callback;
1903 @JavascriptInterface
1904 public void onCanPlay() {
1905 mCallback.notifyCalled();
1908 @JavascriptInterface
1909 public void onError() {
1910 mCallback.notifyCalled();
1915 @Feature({"AndroidWebView", "Preferences"})
1916 public void testBlockNetworkLoadsWithAudio() throws Throwable {
1917 final TestAwContentsClient contentClient = new TestAwContentsClient();
1918 final AwTestContainerView testContainer =
1919 createAwTestContainerViewOnMainSync(contentClient);
1920 final AwContents awContents = testContainer.getAwContents();
1921 final AwSettings awSettings = getAwSettingsOnUiThread(awContents);
1922 CallbackHelper callback = new CallbackHelper();
1923 awSettings.setJavaScriptEnabled(true);
1925 TestWebServer webServer = null;
1927 webServer = new TestWebServer(false);
1928 final String httpPath = "/audio.mp3";
1929 // Don't care about the response is correct or not, just want
1930 // to know whether Url is accessed.
1931 final String audioUrl = webServer.setResponse(httpPath, "1", null);
1933 String pageHtml = "<html><body><audio controls src='" + audioUrl + "' " +
1934 "oncanplay=\"AudioEvent.onCanPlay();\" " +
1935 "onerror=\"AudioEvent.onError();\" /> </body></html>";
1936 // Actual test. Blocking should trigger onerror handler.
1937 awSettings.setBlockNetworkLoads(true);
1938 awContents.addPossiblyUnsafeJavascriptInterface(
1939 new AudioEvent(callback), "AudioEvent", null);
1940 int count = callback.getCallCount();
1941 loadDataSync(awContents, contentClient.getOnPageFinishedHelper(), pageHtml,
1942 "text/html", false);
1943 callback.waitForCallback(count, 1);
1944 assertEquals(0, webServer.getRequestCount(httpPath));
1946 // The below test failed in Nexus Galaxy.
1947 // See https://code.google.com/p/chromium/issues/detail?id=313463
1948 // Unblock should load normally.
1950 awSettings.setBlockNetworkLoads(false);
1951 count = callback.getCallCount();
1952 loadDataSync(awContents, contentClient.getOnPageFinishedHelper(), pageHtml,
1953 "text/html", false);
1954 callback.waitForCallback(count, 1);
1955 assertTrue(0 != webServer.getRequestCount(httpPath));
1958 if (webServer != null) webServer.shutdown();
1962 // Test an assert URL (file:///android_asset/)
1964 @Feature({"AndroidWebView", "Navigation"})
1965 public void testAssetUrl() throws Throwable {
1966 // Note: this text needs to be kept in sync with the contents of the html file referenced
1968 final String expectedTitle = "Asset File";
1969 final TestAwContentsClient contentClient = new TestAwContentsClient();
1970 final AwTestContainerView testContainerView =
1971 createAwTestContainerViewOnMainSync(contentClient);
1972 final AwContents awContents = testContainerView.getAwContents();
1973 loadUrlSync(awContents,
1974 contentClient.getOnPageFinishedHelper(),
1975 "file:///android_asset/asset_file.html");
1976 assertEquals(expectedTitle, getTitleOnUiThread(awContents));
1979 // Test a resource URL (file:///android_res/).
1981 @Feature({"AndroidWebView", "Navigation"})
1982 public void testResourceUrl() throws Throwable {
1983 // Note: this text needs to be kept in sync with the contents of the html file referenced
1985 final String expectedTitle = "Resource File";
1986 final TestAwContentsClient contentClient = new TestAwContentsClient();
1987 final AwTestContainerView testContainerView =
1988 createAwTestContainerViewOnMainSync(contentClient);
1989 final AwContents awContents = testContainerView.getAwContents();
1990 loadUrlSync(awContents,
1991 contentClient.getOnPageFinishedHelper(),
1992 "file:///android_res/raw/resource_file.html");
1993 assertEquals(expectedTitle, getTitleOnUiThread(awContents));
1996 // Test that the file URL access toggle does not affect asset URLs.
1998 @Feature({"AndroidWebView", "Navigation"})
1999 public void testFileUrlAccessToggleDoesNotBlockAssetUrls() throws Throwable {
2000 // Note: this text needs to be kept in sync with the contents of the html file referenced
2002 final String expectedTitle = "Asset File";
2003 final TestAwContentsClient contentClient = new TestAwContentsClient();
2004 final AwTestContainerView testContainerView =
2005 createAwTestContainerViewOnMainSync(contentClient);
2006 final AwContents awContents = testContainerView.getAwContents();
2007 final AwSettings settings = getAwSettingsOnUiThread(awContents);
2008 settings.setAllowFileAccess(false);
2009 loadUrlSync(awContents,
2010 contentClient.getOnPageFinishedHelper(),
2011 "file:///android_asset/asset_file.html");
2012 assertEquals(expectedTitle, getTitleOnUiThread(awContents));
2015 // Test that the file URL access toggle does not affect resource URLs.
2017 @Feature({"AndroidWebView", "Navigation"})
2018 public void testFileUrlAccessToggleDoesNotBlockResourceUrls() throws Throwable {
2019 // Note: this text needs to be kept in sync with the contents of the html file referenced
2021 final String expectedTitle = "Resource File";
2022 final TestAwContentsClient contentClient = new TestAwContentsClient();
2023 final AwTestContainerView testContainerView =
2024 createAwTestContainerViewOnMainSync(contentClient);
2025 final AwContents awContents = testContainerView.getAwContents();
2026 final AwSettings settings = getAwSettingsOnUiThread(awContents);
2027 settings.setAllowFileAccess(false);
2028 loadUrlSync(awContents,
2029 contentClient.getOnPageFinishedHelper(),
2030 "file:///android_res/raw/resource_file.html");
2031 assertEquals(expectedTitle, getTitleOnUiThread(awContents));
2035 @Feature({"AndroidWebView", "Preferences"})
2036 public void testLayoutAlgorithmWithTwoViews() throws Throwable {
2037 ViewPair views = createViews();
2038 runPerViewSettingsTest(
2039 new AwSettingsLayoutAlgorithmTestHelper(views.getContents0(), views.getClient0()),
2040 new AwSettingsLayoutAlgorithmTestHelper(views.getContents1(), views.getClient1()));
2044 @Feature({"AndroidWebView", "Preferences"})
2045 public void testTextZoomWithTwoViews() throws Throwable {
2046 ViewPair views = createViews();
2047 runPerViewSettingsTest(
2048 new AwSettingsTextZoomTestHelper(views.getContents0(), views.getClient0()),
2049 new AwSettingsTextZoomTestHelper(views.getContents1(), views.getClient1()));
2053 @Feature({"AndroidWebView", "Preferences"})
2054 public void testTextZoomAutosizingWithTwoViews() throws Throwable {
2055 ViewPair views = createViews();
2056 runPerViewSettingsTest(
2057 new AwSettingsTextZoomAutosizingTestHelper(views.getContents0(), views.getClient0()),
2058 new AwSettingsTextZoomAutosizingTestHelper(views.getContents1(), views.getClient1()));
2062 @Feature({"AndroidWebView", "Preferences"})
2063 public void testJavaScriptPopupsWithTwoViews() throws Throwable {
2064 ViewPair views = createViews();
2065 runPerViewSettingsTest(
2066 new AwSettingsJavaScriptPopupsTestHelper(views.getContents0(), views.getClient0()),
2067 new AwSettingsJavaScriptPopupsTestHelper(views.getContents1(), views.getClient1()));
2071 @Feature({"AndroidWebView", "Preferences"})
2072 public void testCacheMode() throws Throwable {
2073 final TestAwContentsClient contentClient = new TestAwContentsClient();
2074 final AwTestContainerView testContainer =
2075 createAwTestContainerViewOnMainSync(contentClient);
2076 final AwContents awContents = testContainer.getAwContents();
2077 final AwSettings awSettings = getAwSettingsOnUiThread(testContainer.getAwContents());
2078 clearCacheOnUiThread(awContents, true);
2080 assertEquals(WebSettings.LOAD_DEFAULT, awSettings.getCacheMode());
2081 TestWebServer webServer = null;
2083 webServer = new TestWebServer(false);
2084 final String htmlPath = "/testCacheMode.html";
2085 final String url = webServer.setResponse(htmlPath, "response", null);
2086 awSettings.setCacheMode(WebSettings.LOAD_CACHE_ELSE_NETWORK);
2087 loadUrlSync(awContents, contentClient.getOnPageFinishedHelper(), url);
2088 assertEquals(1, webServer.getRequestCount(htmlPath));
2089 loadUrlSync(awContents, contentClient.getOnPageFinishedHelper(), url);
2090 assertEquals(1, webServer.getRequestCount(htmlPath));
2092 awSettings.setCacheMode(WebSettings.LOAD_NO_CACHE);
2093 loadUrlSync(awContents, contentClient.getOnPageFinishedHelper(), url);
2094 assertEquals(2, webServer.getRequestCount(htmlPath));
2095 loadUrlSync(awContents, contentClient.getOnPageFinishedHelper(), url);
2096 assertEquals(3, webServer.getRequestCount(htmlPath));
2098 awSettings.setCacheMode(WebSettings.LOAD_CACHE_ONLY);
2099 loadUrlSync(awContents, contentClient.getOnPageFinishedHelper(), url);
2100 assertEquals(3, webServer.getRequestCount(htmlPath));
2101 loadUrlSync(awContents, contentClient.getOnPageFinishedHelper(), url);
2102 assertEquals(3, webServer.getRequestCount(htmlPath));
2104 final String htmlNotInCachePath = "/testCacheMode-not-in-cache.html";
2105 final String urlNotInCache = webServer.setResponse(htmlNotInCachePath, "", null);
2106 loadUrlSyncAndExpectError(awContents,
2107 contentClient.getOnPageFinishedHelper(),
2108 contentClient.getOnReceivedErrorHelper(),
2110 assertEquals(0, webServer.getRequestCount(htmlNotInCachePath));
2112 if (webServer != null) webServer.shutdown();
2117 @Feature({"AndroidWebView", "Preferences"})
2118 // As our implementation of network loads blocking uses the same net::URLRequest settings, make
2119 // sure that setting cache mode doesn't accidentally enable network loads. The reference
2120 // behaviour is that when network loads are blocked, setting cache mode has no effect.
2121 public void testCacheModeWithBlockedNetworkLoads() throws Throwable {
2122 final TestAwContentsClient contentClient = new TestAwContentsClient();
2123 final AwTestContainerView testContainer =
2124 createAwTestContainerViewOnMainSync(contentClient);
2125 final AwContents awContents = testContainer.getAwContents();
2126 final AwSettings awSettings = getAwSettingsOnUiThread(testContainer.getAwContents());
2127 clearCacheOnUiThread(awContents, true);
2129 assertEquals(WebSettings.LOAD_DEFAULT, awSettings.getCacheMode());
2130 awSettings.setBlockNetworkLoads(true);
2131 TestWebServer webServer = null;
2133 webServer = new TestWebServer(false);
2134 final String htmlPath = "/testCacheModeWithBlockedNetworkLoads.html";
2135 final String url = webServer.setResponse(htmlPath, "response", null);
2136 loadUrlSyncAndExpectError(awContents,
2137 contentClient.getOnPageFinishedHelper(),
2138 contentClient.getOnReceivedErrorHelper(),
2140 assertEquals(0, webServer.getRequestCount(htmlPath));
2142 awSettings.setCacheMode(WebSettings.LOAD_CACHE_ELSE_NETWORK);
2143 loadUrlSyncAndExpectError(awContents,
2144 contentClient.getOnPageFinishedHelper(),
2145 contentClient.getOnReceivedErrorHelper(),
2147 assertEquals(0, webServer.getRequestCount(htmlPath));
2149 awSettings.setCacheMode(WebSettings.LOAD_NO_CACHE);
2150 loadUrlSyncAndExpectError(awContents,
2151 contentClient.getOnPageFinishedHelper(),
2152 contentClient.getOnReceivedErrorHelper(),
2154 assertEquals(0, webServer.getRequestCount(htmlPath));
2156 awSettings.setCacheMode(WebSettings.LOAD_CACHE_ONLY);
2157 loadUrlSyncAndExpectError(awContents,
2158 contentClient.getOnPageFinishedHelper(),
2159 contentClient.getOnReceivedErrorHelper(),
2161 assertEquals(0, webServer.getRequestCount(htmlPath));
2163 if (webServer != null) webServer.shutdown();
2168 @Feature({"AndroidWebView", "Preferences"})
2169 public void testCacheModeWithTwoViews() throws Throwable {
2170 ViewPair views = createViews();
2171 TestWebServer webServer = null;
2173 webServer = new TestWebServer(false);
2174 runPerViewSettingsTest(
2175 new AwSettingsCacheModeTestHelper(
2176 views.getContents0(), views.getClient0(), 0, webServer),
2177 new AwSettingsCacheModeTestHelper(
2178 views.getContents1(), views.getClient1(), 1, webServer));
2180 if (webServer != null) webServer.shutdown();
2184 static class ManifestTestHelper {
2185 private final TestWebServer mWebServer;
2186 private final String mHtmlPath;
2187 private final String mHtmlUrl;
2188 private final String mManifestPath;
2191 TestWebServer webServer, String htmlPageName, String manifestName) {
2192 mWebServer = webServer;
2193 mHtmlPath = "/" + htmlPageName;
2194 mHtmlUrl = webServer.setResponse(
2195 mHtmlPath, "<html manifest=\"" + manifestName + "\"></html>", null);
2196 mManifestPath = "/" + manifestName;
2197 webServer.setResponse(
2200 CommonResources.getContentTypeAndCacheHeaders("text/cache-manifest", false));
2203 String getHtmlPath() {
2207 String getHtmlUrl() {
2211 String getManifestPath() {
2212 return mManifestPath;
2215 int waitUntilHtmlIsRequested(final int initialRequestCount) throws Exception {
2216 return waitUntilResourceIsRequested(mHtmlPath, initialRequestCount);
2219 int waitUntilManifestIsRequested(final int initialRequestCount) throws Exception {
2220 return waitUntilResourceIsRequested(mManifestPath, initialRequestCount);
2223 private int waitUntilResourceIsRequested(
2224 final String path, final int initialRequestCount) throws Exception {
2225 poll(new Callable<Boolean>() {
2227 public Boolean call() throws Exception {
2228 return mWebServer.getRequestCount(path) > initialRequestCount;
2231 return mWebServer.getRequestCount(path);
2236 @Feature({"AndroidWebView", "Preferences", "AppCache"})
2237 public void testAppCache() throws Throwable {
2238 final TestAwContentsClient contentClient = new TestAwContentsClient();
2239 final AwTestContainerView testContainer =
2240 createAwTestContainerViewOnMainSync(contentClient);
2241 final AwContents awContents = testContainer.getAwContents();
2242 final AwSettings settings = getAwSettingsOnUiThread(awContents);
2243 settings.setJavaScriptEnabled(true);
2244 // Note that the cache isn't actually enabled until the call to setAppCachePath.
2245 settings.setAppCacheEnabled(true);
2247 TestWebServer webServer = null;
2249 webServer = new TestWebServer(false);
2250 ManifestTestHelper helper = new ManifestTestHelper(
2251 webServer, "testAppCache.html", "appcache.manifest");
2254 contentClient.getOnPageFinishedHelper(),
2255 helper.getHtmlUrl());
2256 helper.waitUntilHtmlIsRequested(0);
2257 // Unfortunately, there is no other good way of verifying that AppCache is
2258 // disabled, other than checking that it didn't try to fetch the manifest.
2260 assertEquals(0, webServer.getRequestCount(helper.getManifestPath()));
2261 settings.setAppCachePath("whatever"); // Enables AppCache.
2264 contentClient.getOnPageFinishedHelper(),
2265 helper.getHtmlUrl());
2266 helper.waitUntilManifestIsRequested(0);
2268 if (webServer != null) webServer.shutdown();
2273 @Feature({"AndroidWebView", "Preferences", "AppCache"})
2274 public void testAppCacheWithTwoViews() throws Throwable {
2275 // We don't use the test helper here, because making sure that AppCache
2276 // is disabled takes a lot of time, so running through the usual drill
2277 // will take about 20 seconds.
2278 ViewPair views = createViews();
2280 AwSettings settings0 = getAwSettingsOnUiThread(views.getContents0());
2281 settings0.setJavaScriptEnabled(true);
2282 settings0.setAppCachePath("whatever");
2283 settings0.setAppCacheEnabled(true);
2284 AwSettings settings1 = getAwSettingsOnUiThread(views.getContents1());
2285 settings1.setJavaScriptEnabled(true);
2286 // AppCachePath setting is global, no need to set it for the second view.
2287 settings1.setAppCacheEnabled(true);
2289 TestWebServer webServer = null;
2291 webServer = new TestWebServer(false);
2292 ManifestTestHelper helper0 = new ManifestTestHelper(
2293 webServer, "testAppCache_0.html", "appcache.manifest_0");
2295 views.getContents0(),
2296 views.getClient0().getOnPageFinishedHelper(),
2297 helper0.getHtmlUrl());
2298 int manifestRequests0 = helper0.waitUntilManifestIsRequested(0);
2299 ManifestTestHelper helper1 = new ManifestTestHelper(
2300 webServer, "testAppCache_1.html", "appcache.manifest_1");
2302 views.getContents1(),
2303 views.getClient1().getOnPageFinishedHelper(),
2304 helper1.getHtmlUrl());
2305 helper1.waitUntilManifestIsRequested(0);
2306 settings1.setAppCacheEnabled(false);
2308 views.getContents0(),
2309 views.getClient0().getOnPageFinishedHelper(),
2310 helper0.getHtmlUrl());
2311 helper0.waitUntilManifestIsRequested(manifestRequests0);
2312 final int prevManifestRequestCount =
2313 webServer.getRequestCount(helper1.getManifestPath());
2314 int htmlRequests1 = webServer.getRequestCount(helper1.getHtmlPath());
2316 views.getContents1(),
2317 views.getClient1().getOnPageFinishedHelper(),
2318 helper1.getHtmlUrl());
2319 helper1.waitUntilHtmlIsRequested(htmlRequests1);
2320 // Unfortunately, there is no other good way of verifying that AppCache is
2321 // disabled, other than checking that it didn't try to fetch the manifest.
2324 prevManifestRequestCount, webServer.getRequestCount(helper1.getManifestPath()));
2326 if (webServer != null) webServer.shutdown();
2331 @Feature({"AndroidWebView", "Preferences"})
2332 public void testUseWideViewportWithTwoViews() throws Throwable {
2333 ViewPair views = createViews();
2334 runPerViewSettingsTest(
2335 new AwSettingsUseWideViewportTestHelper(views.getContents0(), views.getClient0()),
2336 new AwSettingsUseWideViewportTestHelper(views.getContents1(), views.getClient1()));
2340 @Feature({"AndroidWebView", "Preferences"})
2341 public void testUseWideViewportWithTwoViewsNoQuirks() throws Throwable {
2342 ViewPair views = createViews(false);
2343 runPerViewSettingsTest(
2344 new AwSettingsUseWideViewportTestHelper(views.getContents0(), views.getClient0()),
2345 new AwSettingsUseWideViewportTestHelper(views.getContents1(), views.getClient1()));
2348 private void useWideViewportLayoutWidthTest(
2349 final AwContents awContents, CallbackHelper onPageFinishedHelper) throws Throwable {
2350 AwSettings settings = getAwSettingsOnUiThread(awContents);
2352 final String pageTemplate = "<html><head>%s</head>" +
2353 "<body onload='document.title=document.body.clientWidth'></body></html>";
2354 final String pageNoViewport = String.format(pageTemplate, "");
2355 final String pageViewportDeviceWidth = String.format(
2357 "<meta name='viewport' content='width=device-width' />");
2358 final String viewportTagSpecifiedWidth = "3000";
2359 final String pageViewportSpecifiedWidth = String.format(
2361 "<meta name='viewport' content='width=" + viewportTagSpecifiedWidth + "' />");
2363 DeviceDisplayInfo deviceInfo =
2364 DeviceDisplayInfo.create(getInstrumentation().getTargetContext());
2365 int displayWidth = (int) (deviceInfo.getDisplayWidth() / deviceInfo.getDIPScale());
2367 settings.setJavaScriptEnabled(true);
2368 assertFalse(settings.getUseWideViewPort());
2369 // When UseWideViewPort is off, "width" setting of "meta viewport"
2370 // tags is ignored, and the layout width is set to device width in CSS pixels.
2371 // Thus, all 3 pages will have the same body width.
2372 loadDataSync(awContents, onPageFinishedHelper, pageNoViewport, "text/html", false);
2373 int actualWidth = Integer.parseInt(getTitleOnUiThread(awContents));
2374 // Avoid rounding errors.
2375 assertTrue("Expected: " + displayWidth + ", Actual: " + actualWidth,
2376 Math.abs(displayWidth - actualWidth) <= 1);
2377 loadDataSync(awContents, onPageFinishedHelper, pageViewportDeviceWidth, "text/html", false);
2378 actualWidth = Integer.parseInt(getTitleOnUiThread(awContents));
2379 assertTrue("Expected: " + displayWidth + ", Actual: " + actualWidth,
2380 Math.abs(displayWidth - actualWidth) <= 1);
2382 awContents, onPageFinishedHelper, pageViewportSpecifiedWidth, "text/html", false);
2383 actualWidth = Integer.parseInt(getTitleOnUiThread(awContents));
2384 assertTrue("Expected: " + displayWidth + ", Actual: " + actualWidth,
2385 Math.abs(displayWidth - actualWidth) <= 1);
2387 settings.setUseWideViewPort(true);
2388 // When UseWideViewPort is on, "meta viewport" tag is used.
2389 // If there is no viewport tag, or width isn't specified,
2390 // then layout width is set to max(980, <device-width-in-DIP-pixels>)
2391 loadDataSync(awContents, onPageFinishedHelper, pageNoViewport, "text/html", false);
2392 actualWidth = Integer.parseInt(getTitleOnUiThread(awContents));
2393 assertTrue("Expected: >= 980 , Actual: " + actualWidth, actualWidth >= 980);
2394 loadDataSync(awContents, onPageFinishedHelper, pageViewportDeviceWidth, "text/html", false);
2395 actualWidth = Integer.parseInt(getTitleOnUiThread(awContents));
2396 assertTrue("Expected: " + displayWidth + ", Actual: " + actualWidth,
2397 Math.abs(displayWidth - actualWidth) <= 1);
2399 awContents, onPageFinishedHelper, pageViewportSpecifiedWidth, "text/html", false);
2400 assertEquals(viewportTagSpecifiedWidth, getTitleOnUiThread(awContents));
2404 @Feature({"AndroidWebView", "Preferences"})
2405 public void testUseWideViewportLayoutWidth() throws Throwable {
2406 TestAwContentsClient contentClient = new TestAwContentsClient();
2407 AwTestContainerView testContainerView =
2408 createAwTestContainerViewOnMainSync(contentClient);
2409 useWideViewportLayoutWidthTest(testContainerView.getAwContents(),
2410 contentClient.getOnPageFinishedHelper());
2414 @Feature({"AndroidWebView", "Preferences"})
2415 public void testUseWideViewportLayoutWidthNoQuirks() throws Throwable {
2416 TestAwContentsClient contentClient = new TestAwContentsClient();
2417 AwTestContainerView testContainerView =
2418 createAwTestContainerViewOnMainSync(contentClient, false);
2419 useWideViewportLayoutWidthTest(testContainerView.getAwContents(),
2420 contentClient.getOnPageFinishedHelper());
2424 @Feature({"AndroidWebView", "Preferences"})
2425 public void testUseWideViewportControlsDoubleTabToZoom() throws Throwable {
2426 final TestAwContentsClient contentClient = new TestAwContentsClient();
2427 final AwTestContainerView testContainerView =
2428 createAwTestContainerViewOnMainSync(contentClient);
2429 final AwContents awContents = testContainerView.getAwContents();
2430 CallbackHelper onPageFinishedHelper = contentClient.getOnPageFinishedHelper();
2431 AwSettings settings = getAwSettingsOnUiThread(awContents);
2432 settings.setBuiltInZoomControls(true);
2434 final String page = "<html><body>Page Text</body></html>";
2435 assertFalse(settings.getUseWideViewPort());
2436 loadDataSync(awContents, onPageFinishedHelper, page, "text/html", false);
2437 final float initialScale = getScaleOnUiThread(awContents);
2438 simulateDoubleTapCenterOfWebViewOnUiThread(testContainerView);
2440 assertEquals(initialScale, getScaleOnUiThread(awContents));
2442 settings.setUseWideViewPort(true);
2443 loadDataSync(awContents, onPageFinishedHelper, page, "text/html", false);
2444 int onScaleChangedCallCount = contentClient.getOnScaleChangedHelper().getCallCount();
2445 simulateDoubleTapCenterOfWebViewOnUiThread(testContainerView);
2446 contentClient.getOnScaleChangedHelper().waitForCallback(onScaleChangedCallCount);
2447 final float zoomedOutScale = getScaleOnUiThread(awContents);
2448 assertTrue("zoomedOut: " + zoomedOutScale + ", initial: " + initialScale,
2449 zoomedOutScale < initialScale);
2453 @Feature({"AndroidWebView", "Preferences"})
2454 public void testLoadWithOverviewModeWithTwoViews() throws Throwable {
2455 ViewPair views = createViews();
2456 runPerViewSettingsTest(
2457 new AwSettingsLoadWithOverviewModeTestHelper(
2458 views.getContents0(), views.getClient0(), false),
2459 new AwSettingsLoadWithOverviewModeTestHelper(
2460 views.getContents1(), views.getClient1(), false));
2464 @Feature({"AndroidWebView", "Preferences"})
2465 public void testLoadWithOverviewModeViewportTagWithTwoViews() throws Throwable {
2466 ViewPair views = createViews();
2467 runPerViewSettingsTest(
2468 new AwSettingsLoadWithOverviewModeTestHelper(
2469 views.getContents0(), views.getClient0(), true),
2470 new AwSettingsLoadWithOverviewModeTestHelper(
2471 views.getContents1(), views.getClient1(), true));
2475 @Feature({"AndroidWebView", "Preferences"})
2476 public void testSetInitialScale() throws Throwable {
2477 final TestAwContentsClient contentClient = new TestAwContentsClient();
2478 final AwTestContainerView testContainerView =
2479 createAwTestContainerViewOnMainSync(contentClient);
2480 final AwContents awContents = testContainerView.getAwContents();
2481 final AwSettings awSettings = getAwSettingsOnUiThread(awContents);
2482 CallbackHelper onPageFinishedHelper = contentClient.getOnPageFinishedHelper();
2484 WindowManager wm = (WindowManager) getInstrumentation().getTargetContext()
2485 .getSystemService(Context.WINDOW_SERVICE);
2486 Point screenSize = new Point();
2487 wm.getDefaultDisplay().getSize(screenSize);
2488 // Make sure after 50% scale, page width still larger than screen.
2489 int height = screenSize.y * 2 + 1;
2490 int width = screenSize.x * 2 + 1;
2491 final String page = "<html><body>" +
2492 "<p style='height:" + height + "px;width:" + width + "px'>" +
2493 "testSetInitialScale</p></body></html>";
2494 final float defaultScale =
2495 getInstrumentation().getTargetContext().getResources().getDisplayMetrics().density;
2497 assertEquals(defaultScale, getPixelScaleOnUiThread(awContents), .01f);
2498 loadDataSync(awContents, onPageFinishedHelper, page, "text/html", false);
2499 assertEquals(defaultScale, getPixelScaleOnUiThread(awContents), .01f);
2501 int onScaleChangedCallCount = contentClient.getOnScaleChangedHelper().getCallCount();
2502 awSettings.setInitialPageScale(50);
2503 loadDataSync(awContents, onPageFinishedHelper, page, "text/html", false);
2504 contentClient.getOnScaleChangedHelper().waitForCallback(onScaleChangedCallCount);
2505 assertEquals(0.5f, getPixelScaleOnUiThread(awContents), .01f);
2507 onScaleChangedCallCount = contentClient.getOnScaleChangedHelper().getCallCount();
2508 awSettings.setInitialPageScale(500);
2509 loadDataSync(awContents, onPageFinishedHelper, page, "text/html", false);
2510 contentClient.getOnScaleChangedHelper().waitForCallback(onScaleChangedCallCount);
2511 assertEquals(5.0f, getPixelScaleOnUiThread(awContents), .01f);
2513 onScaleChangedCallCount = contentClient.getOnScaleChangedHelper().getCallCount();
2514 awSettings.setInitialPageScale(0);
2515 loadDataSync(awContents, onPageFinishedHelper, page, "text/html", false);
2516 contentClient.getOnScaleChangedHelper().waitForCallback(onScaleChangedCallCount);
2517 assertEquals(defaultScale, getPixelScaleOnUiThread(awContents), .01f);
2522 * @param requiredUserGesture the settings of MediaPlaybackRequiresUserGesture.
2523 * @param waitTime time for waiting event happen, -1 means forever.
2524 * @return true if the event happened,
2525 * @throws Throwable throw exception if timeout.
2527 private boolean runVideoTest(final boolean requiredUserGesture, long waitTime)
2529 final JavascriptEventObserver observer = new JavascriptEventObserver();
2530 TestAwContentsClient client = new TestAwContentsClient();
2531 final AwContents awContents = createAwTestContainerViewOnMainSync(client).getAwContents();
2532 getInstrumentation().runOnMainSync(new Runnable() {
2535 AwSettings awSettings = awContents.getSettings();
2536 awSettings.setJavaScriptEnabled(true);
2537 awSettings.setMediaPlaybackRequiresUserGesture(requiredUserGesture);
2538 observer.register(awContents.getContentViewCore(), "javaObserver");
2541 VideoTestWebServer webServer = new VideoTestWebServer(getActivity());
2543 String data = "<html><head><script>" +
2544 "addEventListener('DOMContentLoaded', function() { " +
2545 " document.getElementById('video').addEventListener('play', function() { " +
2546 " javaObserver.notifyJava(); " +
2549 "</script></head><body>" +
2550 "<video id='video' autoplay control src='" +
2551 webServer.getOnePixelOneFrameWebmURL() + "' /> </body></html>";
2552 loadDataAsync(awContents, data, "text/html", false);
2553 if (waitTime == -1) {
2554 observer.waitForEvent();
2557 return observer.waitForEvent(waitTime);
2560 if (webServer != null && webServer.getTestWebServer() != null)
2561 webServer.getTestWebServer().shutdown();
2567 @Feature({"AndroidWebView", "Preferences"})
2568 http://crbug.com/304549
2571 public void testMediaPlaybackWithoutUserGesture() throws Throwable {
2572 assertTrue(runVideoTest(false, -1));
2576 @Feature({"AndroidWebView", "Preferences"})
2577 public void testMediaPlaybackWithUserGesture() throws Throwable {
2578 // Wait for 5 second to see if video played.
2579 assertFalse(runVideoTest(true, 5000));
2583 @Feature({"AndroidWebView", "Preferences"})
2584 public void testDefaultVideoPosterURL() throws Throwable {
2585 final CallbackHelper videoPosterAccessedCallbackHelper = new CallbackHelper();
2586 final String DEFAULT_VIDEO_POSTER_URL = "http://default_video_poster/";
2587 TestAwContentsClient client = new TestAwContentsClient() {
2589 public InterceptedRequestData shouldInterceptRequest(String url) {
2590 if (url.equals(DEFAULT_VIDEO_POSTER_URL)) {
2591 videoPosterAccessedCallbackHelper.notifyCalled();
2596 final AwContents awContents = createAwTestContainerViewOnMainSync(client).getAwContents();
2597 getInstrumentation().runOnMainSync(new Runnable() {
2600 AwSettings awSettings = awContents.getSettings();
2601 awSettings.setDefaultVideoPosterURL(DEFAULT_VIDEO_POSTER_URL);
2604 VideoTestWebServer webServer = new VideoTestWebServer(
2605 getInstrumentation().getTargetContext());
2607 String data = "<html><head><body>" +
2608 "<video id='video' control src='" +
2609 webServer.getOnePixelOneFrameWebmURL() + "' /> </body></html>";
2610 loadDataAsync(awContents, data, "text/html", false);
2611 videoPosterAccessedCallbackHelper.waitForCallback(0, 1, 20, TimeUnit.SECONDS);
2613 if (webServer.getTestWebServer() != null)
2614 webServer.getTestWebServer().shutdown();
2619 @Feature({"AndroidWebView", "Preferences"})
2620 // background shorthand property must not override background-size when
2621 // it's already set.
2622 public void testUseLegacyBackgroundSizeShorthandBehavior() throws Throwable {
2623 final TestAwContentsClient contentClient = new TestAwContentsClient();
2624 final AwTestContainerView testContainerView =
2625 createAwTestContainerViewOnMainSync(contentClient);
2626 final AwContents awContents = testContainerView.getAwContents();
2627 AwSettings settings = getAwSettingsOnUiThread(awContents);
2628 CallbackHelper onPageFinishedHelper = contentClient.getOnPageFinishedHelper();
2629 final String expectedBackgroundSize = "cover";
2630 final String page = "<html><head>" +
2632 "function getBackgroundSize() {" +
2633 " var e = document.getElementById('test'); " +
2634 " e.style.backgroundSize = '" + expectedBackgroundSize + "';" +
2635 " e.style.background = 'center red url(dummy://test.png) no-repeat border-box'; " +
2636 " return e.style.backgroundSize; " +
2638 "</script></head>" +
2639 "<body onload='document.title=getBackgroundSize()'>" +
2640 " <div id='test'> </div>" +
2642 settings.setJavaScriptEnabled(true);
2643 loadDataSync(awContents, onPageFinishedHelper, page, "text/html", false);
2644 String actualBackgroundSize = getTitleOnUiThread(awContents);
2645 assertEquals(expectedBackgroundSize, actualBackgroundSize);
2648 static class ViewPair {
2649 private final AwContents contents0;
2650 private final TestAwContentsClient client0;
2651 private final AwContents contents1;
2652 private final TestAwContentsClient client1;
2654 ViewPair(AwContents contents0, TestAwContentsClient client0,
2655 AwContents contents1, TestAwContentsClient client1) {
2656 this.contents0 = contents0;
2657 this.client0 = client0;
2658 this.contents1 = contents1;
2659 this.client1 = client1;
2662 AwContents getContents0() {
2666 TestAwContentsClient getClient0() {
2670 AwContents getContents1() {
2674 TestAwContentsClient getClient1() {
2680 * Verifies the following statements about a setting:
2681 * - initially, the setting has a default value;
2682 * - the setting can be switched to an alternate value and back;
2683 * - switching a setting in the first WebView doesn't affect the setting
2684 * state in the second WebView and vice versa.
2686 * @param helper0 Test helper for the first ContentView
2687 * @param helper1 Test helper for the second ContentView
2690 private void runPerViewSettingsTest(AwSettingsTestHelper helper0,
2691 AwSettingsTestHelper helper1) throws Throwable {
2692 helper0.ensureSettingHasInitialValue();
2693 helper1.ensureSettingHasInitialValue();
2695 helper1.setAlteredSettingValue();
2696 helper0.ensureSettingHasInitialValue();
2697 helper1.ensureSettingHasAlteredValue();
2699 helper1.setInitialSettingValue();
2700 helper0.ensureSettingHasInitialValue();
2701 helper1.ensureSettingHasInitialValue();
2703 helper0.setAlteredSettingValue();
2704 helper0.ensureSettingHasAlteredValue();
2705 helper1.ensureSettingHasInitialValue();
2707 helper0.setInitialSettingValue();
2708 helper0.ensureSettingHasInitialValue();
2709 helper1.ensureSettingHasInitialValue();
2711 helper0.setAlteredSettingValue();
2712 helper0.ensureSettingHasAlteredValue();
2713 helper1.ensureSettingHasInitialValue();
2715 helper1.setAlteredSettingValue();
2716 helper0.ensureSettingHasAlteredValue();
2717 helper1.ensureSettingHasAlteredValue();
2719 helper0.setInitialSettingValue();
2720 helper0.ensureSettingHasInitialValue();
2721 helper1.ensureSettingHasAlteredValue();
2723 helper1.setInitialSettingValue();
2724 helper0.ensureSettingHasInitialValue();
2725 helper1.ensureSettingHasInitialValue();
2728 private ViewPair createViews() throws Throwable {
2729 return createViews(true);
2732 private ViewPair createViews(boolean supportsLegacyQuirks) throws Throwable {
2733 TestAwContentsClient client0 = new TestAwContentsClient();
2734 TestAwContentsClient client1 = new TestAwContentsClient();
2735 return new ViewPair(
2736 createAwTestContainerViewOnMainSync(client0, supportsLegacyQuirks).getAwContents(),
2738 createAwTestContainerViewOnMainSync(client1, supportsLegacyQuirks).getAwContents(),
2742 static void assertFileIsReadable(String filePath) {
2743 File file = new File(filePath);
2745 assertTrue("Test file \"" + filePath + "\" is not readable." +
2746 "Please make sure that files from android_webview/test/data/device_files/ " +
2747 "has been pushed to the device before testing",
2749 } catch (SecurityException e) {
2750 fail("Got a SecurityException for \"" + filePath + "\": " + e.toString());
2755 * Verifies the number of resource requests made to the content provider.
2756 * @param resource Resource name
2757 * @param expectedCount Expected resource requests count
2759 private void ensureResourceRequestCountInContentProvider(String resource, int expectedCount) {
2760 Context context = getInstrumentation().getTargetContext();
2761 int actualCount = TestContentProvider.getResourceRequestCount(context, resource);
2762 assertEquals(expectedCount, actualCount);
2765 private void resetResourceRequestCountInContentProvider(String resource) {
2766 Context context = getInstrumentation().getTargetContext();
2767 TestContentProvider.resetResourceRequestCount(context, resource);
2770 private String createContentUrl(final String target) {
2771 return TestContentProvider.createContentUrl(target);
2774 private void simulateDoubleTapCenterOfWebViewOnUiThread(final AwTestContainerView webView)
2776 final int x = (webView.getRight() - webView.getLeft()) / 2;
2777 final int y = (webView.getBottom() - webView.getTop()) / 2;
2778 final AwContents awContents = webView.getAwContents();
2779 runTestOnUiThread(new Runnable() {
2782 awContents.getContentViewCore().sendDoubleTapForTest(
2783 SystemClock.uptimeMillis(), x, y, new Bundle());