| OLD | NEW |
| 1 // Copyright 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 package org.chromium.android_webview.test; | 5 package org.chromium.android_webview.test; |
| 6 | 6 |
| 7 import android.os.Build; | 7 import android.os.Build; |
| 8 import android.test.suitebuilder.annotation.SmallTest; | 8 import android.test.suitebuilder.annotation.SmallTest; |
| 9 import android.util.Pair; | 9 import android.util.Pair; |
| 10 | 10 |
| (...skipping 19 matching lines...) Expand all Loading... |
| 30 import java.util.concurrent.Callable; | 30 import java.util.concurrent.Callable; |
| 31 import java.util.concurrent.ConcurrentHashMap; | 31 import java.util.concurrent.ConcurrentHashMap; |
| 32 import java.util.concurrent.CountDownLatch; | 32 import java.util.concurrent.CountDownLatch; |
| 33 | 33 |
| 34 /** | 34 /** |
| 35 * Tests for the WebViewClient.shouldInterceptRequest() method. | 35 * Tests for the WebViewClient.shouldInterceptRequest() method. |
| 36 */ | 36 */ |
| 37 @MinAndroidSdkLevel(Build.VERSION_CODES.KITKAT) | 37 @MinAndroidSdkLevel(Build.VERSION_CODES.KITKAT) |
| 38 public class AwContentsClientShouldInterceptRequestTest extends AwTestBase { | 38 public class AwContentsClientShouldInterceptRequestTest extends AwTestBase { |
| 39 | 39 |
| 40 private static class TestAwContentsClient | 40 private static class ShouldInterceptRequestClient extends TestAwContentsClie
nt { |
| 41 extends org.chromium.android_webview.test.TestAwContentsClient { | |
| 42 | 41 |
| 43 public static class ShouldInterceptRequestHelper extends CallbackHelper
{ | 42 public static class ShouldInterceptRequestHelper extends CallbackHelper
{ |
| 44 private List<String> mShouldInterceptRequestUrls = new ArrayList<Str
ing>(); | 43 private List<String> mShouldInterceptRequestUrls = new ArrayList<Str
ing>(); |
| 45 private ConcurrentHashMap<String, AwWebResourceResponse> mReturnValu
esByUrls = | 44 private ConcurrentHashMap<String, AwWebResourceResponse> mReturnValu
esByUrls = |
| 46 new ConcurrentHashMap<String, AwWebResourceResponse>(); | 45 new ConcurrentHashMap<String, AwWebResourceResponse>(); |
| 47 private ConcurrentHashMap<String, AwWebResourceRequest> mRequestsByU
rls = | 46 private ConcurrentHashMap<String, AwWebResourceRequest> mRequestsByU
rls = |
| 48 new ConcurrentHashMap<String, AwWebResourceRequest>(); | 47 new ConcurrentHashMap<String, AwWebResourceRequest>(); |
| 49 // This is read from the IO thread, so needs to be marked volatile. | 48 // This is read on another thread, so needs to be marked volatile. |
| 50 private volatile AwWebResourceResponse mShouldInterceptRequestReturn
Value = null; | 49 private volatile AwWebResourceResponse mShouldInterceptRequestReturn
Value = null; |
| 51 void setReturnValue(AwWebResourceResponse value) { | 50 void setReturnValue(AwWebResourceResponse value) { |
| 52 mShouldInterceptRequestReturnValue = value; | 51 mShouldInterceptRequestReturnValue = value; |
| 53 } | 52 } |
| 54 void setReturnValueForUrl(String url, AwWebResourceResponse value) { | 53 void setReturnValueForUrl(String url, AwWebResourceResponse value) { |
| 55 mReturnValuesByUrls.put(url, value); | 54 mReturnValuesByUrls.put(url, value); |
| 56 } | 55 } |
| 57 public List<String> getUrls() { | 56 public List<String> getUrls() { |
| 58 assert getCallCount() > 0; | 57 assert getCallCount() > 0; |
| 59 return mShouldInterceptRequestUrls; | 58 return mShouldInterceptRequestUrls; |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 99 | 98 |
| 100 @Override | 99 @Override |
| 101 public void onLoadResource(String url) { | 100 public void onLoadResource(String url) { |
| 102 super.onLoadResource(url); | 101 super.onLoadResource(url); |
| 103 mOnLoadResourceHelper.notifyCalled(url); | 102 mOnLoadResourceHelper.notifyCalled(url); |
| 104 } | 103 } |
| 105 | 104 |
| 106 private ShouldInterceptRequestHelper mShouldInterceptRequestHelper; | 105 private ShouldInterceptRequestHelper mShouldInterceptRequestHelper; |
| 107 private OnLoadResourceHelper mOnLoadResourceHelper; | 106 private OnLoadResourceHelper mOnLoadResourceHelper; |
| 108 | 107 |
| 109 public TestAwContentsClient() { | 108 public ShouldInterceptRequestClient() { |
| 110 mShouldInterceptRequestHelper = new ShouldInterceptRequestHelper(); | 109 mShouldInterceptRequestHelper = new ShouldInterceptRequestHelper(); |
| 111 mOnLoadResourceHelper = new OnLoadResourceHelper(); | 110 mOnLoadResourceHelper = new OnLoadResourceHelper(); |
| 112 } | 111 } |
| 113 | 112 |
| 114 public ShouldInterceptRequestHelper getShouldInterceptRequestHelper() { | 113 public ShouldInterceptRequestHelper getShouldInterceptRequestHelper() { |
| 115 return mShouldInterceptRequestHelper; | 114 return mShouldInterceptRequestHelper; |
| 116 } | 115 } |
| 117 | 116 |
| 118 public OnLoadResourceHelper getOnLoadResourceHelper() { | 117 public OnLoadResourceHelper getOnLoadResourceHelper() { |
| 119 return mOnLoadResourceHelper; | 118 return mOnLoadResourceHelper; |
| (...skipping 17 matching lines...) Expand all Loading... |
| 137 | 136 |
| 138 private AwWebResourceResponse stringToAwWebResourceResponse(String input) th
rows Throwable { | 137 private AwWebResourceResponse stringToAwWebResourceResponse(String input) th
rows Throwable { |
| 139 final String mimeType = "text/html"; | 138 final String mimeType = "text/html"; |
| 140 final String encoding = "UTF-8"; | 139 final String encoding = "UTF-8"; |
| 141 | 140 |
| 142 return new AwWebResourceResponse( | 141 return new AwWebResourceResponse( |
| 143 mimeType, encoding, new ByteArrayInputStream(input.getBytes(enco
ding))); | 142 mimeType, encoding, new ByteArrayInputStream(input.getBytes(enco
ding))); |
| 144 } | 143 } |
| 145 | 144 |
| 146 private TestWebServer mWebServer; | 145 private TestWebServer mWebServer; |
| 147 private TestAwContentsClient mContentsClient; | 146 private ShouldInterceptRequestClient mContentsClient; |
| 148 private AwTestContainerView mTestContainerView; | 147 private AwTestContainerView mTestContainerView; |
| 149 private AwContents mAwContents; | 148 private AwContents mAwContents; |
| 150 private TestAwContentsClient.ShouldInterceptRequestHelper mShouldInterceptRe
questHelper; | 149 private ShouldInterceptRequestClient.ShouldInterceptRequestHelper mShouldInt
erceptRequestHelper; |
| 151 | 150 |
| 152 @Override | 151 @Override |
| 153 protected void setUp() throws Exception { | 152 protected void setUp() throws Exception { |
| 154 super.setUp(); | 153 super.setUp(); |
| 155 | 154 |
| 156 mContentsClient = new TestAwContentsClient(); | 155 mContentsClient = new ShouldInterceptRequestClient(); |
| 157 mTestContainerView = createAwTestContainerViewOnMainSync(mContentsClient
); | 156 mTestContainerView = createAwTestContainerViewOnMainSync(mContentsClient
); |
| 158 mAwContents = mTestContainerView.getAwContents(); | 157 mAwContents = mTestContainerView.getAwContents(); |
| 159 mShouldInterceptRequestHelper = mContentsClient.getShouldInterceptReques
tHelper(); | 158 mShouldInterceptRequestHelper = mContentsClient.getShouldInterceptReques
tHelper(); |
| 160 | 159 |
| 161 mWebServer = TestWebServer.start(); | 160 mWebServer = TestWebServer.start(); |
| 162 } | 161 } |
| 163 | 162 |
| 164 @Override | 163 @Override |
| 165 protected void tearDown() throws Exception { | 164 protected void tearDown() throws Exception { |
| 166 mWebServer.shutdown(); | 165 mWebServer.shutdown(); |
| (...skipping 133 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 300 Map<String, String> headers = | 299 Map<String, String> headers = |
| 301 mShouldInterceptRequestHelper.getRequestsForUrl(syncGetUrl).requ
estHeaders; | 300 mShouldInterceptRequestHelper.getRequestsForUrl(syncGetUrl).requ
estHeaders; |
| 302 assertTrue(headers.containsKey(headerName)); | 301 assertTrue(headers.containsKey(headerName)); |
| 303 assertEquals(headerValue, headers.get(headerName)); | 302 assertEquals(headerValue, headers.get(headerName)); |
| 304 } | 303 } |
| 305 | 304 |
| 306 @SmallTest | 305 @SmallTest |
| 307 @Feature({"AndroidWebView"}) | 306 @Feature({"AndroidWebView"}) |
| 308 public void testOnLoadResourceCalledWithCorrectUrl() throws Throwable { | 307 public void testOnLoadResourceCalledWithCorrectUrl() throws Throwable { |
| 309 final String aboutPageUrl = addAboutPageToTestServer(mWebServer); | 308 final String aboutPageUrl = addAboutPageToTestServer(mWebServer); |
| 310 final TestAwContentsClient.OnLoadResourceHelper onLoadResourceHelper = | 309 final ShouldInterceptRequestClient.OnLoadResourceHelper onLoadResourceHe
lper = |
| 311 mContentsClient.getOnLoadResourceHelper(); | 310 mContentsClient.getOnLoadResourceHelper(); |
| 312 | 311 |
| 313 int callCount = onLoadResourceHelper.getCallCount(); | 312 int callCount = onLoadResourceHelper.getCallCount(); |
| 314 | 313 |
| 315 loadUrlAsync(mAwContents, aboutPageUrl); | 314 loadUrlAsync(mAwContents, aboutPageUrl); |
| 316 | 315 |
| 317 onLoadResourceHelper.waitForCallback(callCount); | 316 onLoadResourceHelper.waitForCallback(callCount); |
| 318 assertEquals(aboutPageUrl, onLoadResourceHelper.getUrl()); | 317 assertEquals(aboutPageUrl, onLoadResourceHelper.getUrl()); |
| 319 } | 318 } |
| 320 | 319 |
| (...skipping 508 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 829 int callCount = mShouldInterceptRequestHelper.getCallCount(); | 828 int callCount = mShouldInterceptRequestHelper.getCallCount(); |
| 830 loadDataWithBaseUrlAsync(mAwContents, pageHtml, "text/html", false, base
Url, null); | 829 loadDataWithBaseUrlAsync(mAwContents, pageHtml, "text/html", false, base
Url, null); |
| 831 mShouldInterceptRequestHelper.waitForCallback(callCount, 1); | 830 mShouldInterceptRequestHelper.waitForCallback(callCount, 1); |
| 832 assertEquals(1, mShouldInterceptRequestHelper.getUrls().size()); | 831 assertEquals(1, mShouldInterceptRequestHelper.getUrls().size()); |
| 833 assertEquals(imageUrl, mShouldInterceptRequestHelper.getUrls().get(0)); | 832 assertEquals(imageUrl, mShouldInterceptRequestHelper.getUrls().get(0)); |
| 834 Map<String, String> headers = | 833 Map<String, String> headers = |
| 835 mShouldInterceptRequestHelper.getRequestsForUrl(imageUrl).reques
tHeaders; | 834 mShouldInterceptRequestHelper.getRequestsForUrl(imageUrl).reques
tHeaders; |
| 836 assertTrue(headers.containsKey(refererHeaderName)); | 835 assertTrue(headers.containsKey(refererHeaderName)); |
| 837 assertEquals(baseUrl, headers.get(refererHeaderName)); | 836 assertEquals(baseUrl, headers.get(refererHeaderName)); |
| 838 } | 837 } |
| 838 |
| 839 private static class DeadlockingAwContentsClient extends TestAwContentsClien
t { |
| 840 public DeadlockingAwContentsClient(CountDownLatch ready, CountDownLatch
wait) { |
| 841 mReady = ready; |
| 842 mWait = wait; |
| 843 } |
| 844 |
| 845 @Override |
| 846 public AwWebResourceResponse shouldInterceptRequest(AwWebResourceRequest
request) { |
| 847 mReady.countDown(); |
| 848 try { |
| 849 mWait.await(); |
| 850 } catch (InterruptedException e) { |
| 851 // ignore |
| 852 } |
| 853 return null; |
| 854 } |
| 855 |
| 856 private CountDownLatch mReady; |
| 857 private CountDownLatch mWait; |
| 858 } |
| 859 |
| 860 @SmallTest |
| 861 @Feature({"AndroidWebView"}) |
| 862 public void testDeadlock() throws Throwable { |
| 863 // The client will lock shouldInterceptRequest to wait for the UI thread
. |
| 864 // On the UI thread, we will try engaging the IO thread by executing |
| 865 // an action that causes IPC message sending. If the client callback |
| 866 // is executed on the IO thread, this will cause a deadlock. |
| 867 CountDownLatch waitForShouldInterceptRequest = new CountDownLatch(1); |
| 868 CountDownLatch signalAfterSendingIpc = new CountDownLatch(1); |
| 869 DeadlockingAwContentsClient client = new DeadlockingAwContentsClient( |
| 870 waitForShouldInterceptRequest, signalAfterSendingIpc); |
| 871 mTestContainerView = createAwTestContainerViewOnMainSync(client); |
| 872 mAwContents = mTestContainerView.getAwContents(); |
| 873 loadUrlAsync(mAwContents, "http://www.example.com"); |
| 874 waitForShouldInterceptRequest.await(); |
| 875 // The following call will try to send an IPC and wait for a reply from
renderer. |
| 876 // We do not check the actual result, because it can be bogus. The impor
tant |
| 877 // thing is that the call does not cause a deadlock. |
| 878 executeJavaScriptAndWaitForResult(mAwContents, client, "1+1"); |
| 879 signalAfterSendingIpc.countDown(); |
| 880 } |
| 839 } | 881 } |
| OLD | NEW |