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. 4 5 package org.chromium.content.browser.test.util; 6 7 8 import org.chromium.base.ThreadUtils; 9 import org.chromium.content.browser.ContentViewCore; 10 import org.chromium.content_public.browser.JavaScriptCallback; 11 12 import java.util.concurrent.TimeUnit; 13 import java.util.concurrent.TimeoutException; 14 15 /** 16 * This class is used to provide callback hooks for tests and related classes. 17 */ 18 public class TestCallbackHelperContainer { 19 private final TestContentViewClient mTestContentViewClient; 20 private TestWebContentsObserver mTestWebContentsObserver; 21 22 public TestCallbackHelperContainer(final ContentViewCore contentViewCore) { 23 mTestContentViewClient = new TestContentViewClient(); 24 contentViewCore.setContentViewClient(mTestContentViewClient); 25 // TODO(yfriedman): Change callers to be executed on the UI thread. Unfortunately this is 26 // super convenient as the caller is nearly always on the test thread which is fine to block 27 // and it's cumbersome to keep bouncing to the UI thread. 28 ThreadUtils.runOnUiThreadBlocking(new Runnable() { 29 @Override 30 public void run() { 31 mTestWebContentsObserver = new TestWebContentsObserver(contentViewCore); 32 } 33 }); 34 } 35 36 protected TestCallbackHelperContainer( 37 TestContentViewClient viewClient, TestWebContentsObserver contentsObserver) { 38 mTestContentViewClient = viewClient; 39 mTestWebContentsObserver = contentsObserver; 40 } 41 42 /** 43 * CallbackHelper for OnPageFinished. 44 */ 45 public static class OnPageFinishedHelper extends CallbackHelper { 46 private String mUrl; 47 public void notifyCalled(String url) { 48 mUrl = url; 49 notifyCalled(); 50 } 51 public String getUrl() { 52 assert getCallCount() > 0; 53 return mUrl; 54 } 55 } 56 57 /** 58 * CallbackHelper for OnPageStarted. 59 */ 60 public static class OnPageStartedHelper extends CallbackHelper { 61 private String mUrl; 62 public void notifyCalled(String url) { 63 mUrl = url; 64 notifyCalled(); 65 } 66 public String getUrl() { 67 assert getCallCount() > 0; 68 return mUrl; 69 } 70 } 71 72 /** 73 * CallbackHelper for OnReceivedError. 74 */ 75 public static class OnReceivedErrorHelper extends CallbackHelper { 76 private int mErrorCode; 77 private String mDescription; 78 private String mFailingUrl; 79 public void notifyCalled(int errorCode, String description, String failingUrl) { 80 mErrorCode = errorCode; 81 mDescription = description; 82 mFailingUrl = failingUrl; 83 notifyCalled(); 84 } 85 public int getErrorCode() { 86 assert getCallCount() > 0; 87 return mErrorCode; 88 } 89 public String getDescription() { 90 assert getCallCount() > 0; 91 return mDescription; 92 } 93 public String getFailingUrl() { 94 assert getCallCount() > 0; 95 return mFailingUrl; 96 } 97 } 98 99 /** 100 * CallbackHelper for OnEvaluateJavaScriptResult. 101 * This class wraps the evaluation of JavaScript code allowing test code to 102 * synchronously evaluate JavaScript and then test the result. 103 */ 104 public static class OnEvaluateJavaScriptResultHelper extends CallbackHelper { 105 private String mJsonResult; 106 107 /** 108 * Starts evaluation of a given JavaScript code on a given contentViewCore. 109 * @param contentViewCore A ContentViewCore instance to be used. 110 * @param code A JavaScript code to be evaluated. 111 */ 112 public void evaluateJavaScript(ContentViewCore contentViewCore, String code) { 113 JavaScriptCallback callback = 114 new JavaScriptCallback() { 115 @Override 116 public void handleJavaScriptResult(String jsonResult) { 117 notifyCalled(jsonResult); 118 } 119 }; 120 contentViewCore.evaluateJavaScript(code, callback); 121 mJsonResult = null; 122 } 123 124 /** 125 * Returns true if the evaluation started by evaluateJavaScript() has completed. 126 */ 127 public boolean hasValue() { 128 return mJsonResult != null; 129 } 130 131 /** 132 * Returns the JSON result of a previously completed JavaScript evaluation and 133 * resets the helper to accept new evaluations. 134 * @return String JSON result of a previously completed JavaScript evaluation. 135 */ 136 public String getJsonResultAndClear() { 137 assert hasValue(); 138 String result = mJsonResult; 139 mJsonResult = null; 140 return result; 141 } 142 143 144 /** 145 * Returns a criteria that checks that the evaluation has finished. 146 */ 147 public Criteria getHasValueCriteria() { 148 return new Criteria() { 149 @Override 150 public boolean isSatisfied() { 151 return hasValue(); 152 } 153 }; 154 } 155 156 /** 157 * Waits till the JavaScript evaluation finishes and returns true if a value was returned, 158 * false if it timed-out. 159 */ 160 public boolean waitUntilHasValue(long timeout, TimeUnit timeoutUnits) 161 throws InterruptedException, TimeoutException { 162 waitUntilCriteria(getHasValueCriteria(), timeout, timeoutUnits); 163 return hasValue(); 164 } 165 166 public boolean waitUntilHasValue() throws InterruptedException, TimeoutException { 167 waitUntilCriteria(getHasValueCriteria()); 168 return hasValue(); 169 } 170 171 public void notifyCalled(String jsonResult) { 172 assert !hasValue(); 173 mJsonResult = jsonResult; 174 notifyCalled(); 175 } 176 } 177 178 /** 179 * CallbackHelper for OnStartContentIntent. 180 */ 181 public static class OnStartContentIntentHelper extends CallbackHelper { 182 private String mIntentUrl; 183 public void notifyCalled(String intentUrl) { 184 mIntentUrl = intentUrl; 185 notifyCalled(); 186 } 187 public String getIntentUrl() { 188 assert getCallCount() > 0; 189 return mIntentUrl; 190 } 191 } 192 193 public OnPageStartedHelper getOnPageStartedHelper() { 194 return mTestWebContentsObserver.getOnPageStartedHelper(); 195 } 196 197 public OnPageFinishedHelper getOnPageFinishedHelper() { 198 return mTestWebContentsObserver.getOnPageFinishedHelper(); 199 } 200 201 public OnReceivedErrorHelper getOnReceivedErrorHelper() { 202 return mTestWebContentsObserver.getOnReceivedErrorHelper(); 203 } 204 205 public OnStartContentIntentHelper getOnStartContentIntentHelper() { 206 return mTestContentViewClient.getOnStartContentIntentHelper(); 207 } 208 } 209