OLD | NEW |
---|---|
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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 #import "ios/web/public/test/earl_grey/web_view_actions.h" | 5 #import "ios/web/public/test/earl_grey/web_view_actions.h" |
6 | 6 |
7 #include "base/callback_helpers.h" | 7 #include "base/callback_helpers.h" |
8 #include "base/logging.h" | 8 #include "base/logging.h" |
9 #include "base/mac/bind_objc_block.h" | 9 #include "base/mac/bind_objc_block.h" |
10 #include "base/strings/stringprintf.h" | 10 #include "base/strings/stringprintf.h" |
11 #include "base/test/ios/wait_util.h" | 11 #include "base/test/ios/wait_util.h" |
12 #include "base/values.h" | 12 #include "base/values.h" |
13 #import "ios/testing/earl_grey/wait_util.h" | 13 #import "ios/testing/wait_util.h" |
14 #import "ios/web/public/test/earl_grey/web_view_matchers.h" | 14 #import "ios/web/public/test/earl_grey/web_view_matchers.h" |
15 #import "ios/web/public/test/web_view_interaction_test_util.h" | 15 #import "ios/web/public/test/web_view_interaction_test_util.h" |
16 #import "ios/web/web_state/web_state_impl.h" | 16 #import "ios/web/web_state/web_state_impl.h" |
17 | 17 |
18 using web::test::ExecuteJavaScript; | 18 using web::test::ExecuteJavaScript; |
19 | 19 |
20 namespace { | 20 namespace { |
21 | 21 |
22 // Long press duration to trigger context menu. | 22 // Long press duration to trigger context menu. |
23 const NSTimeInterval kContextMenuLongPressDuration = 0.3; | 23 const NSTimeInterval kContextMenuLongPressDuration = 0.3; |
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
55 " __gCrWeb.message.invokeOnHost(" | 55 " __gCrWeb.message.invokeOnHost(" |
56 // Second template param: callback command. | 56 // Second template param: callback command. |
57 " {'command' : '%2$s' });" | 57 " {'command' : '%2$s' });" |
58 " }, options);" | 58 " }, options);" |
59 " return true;" | 59 " return true;" |
60 "})();"; | 60 "})();"; |
61 | 61 |
62 const std::string kAddVerifierScript = | 62 const std::string kAddVerifierScript = |
63 base::StringPrintf(kAddInteractionVerifierScriptTemplate, | 63 base::StringPrintf(kAddInteractionVerifierScriptTemplate, |
64 element_id.c_str(), kCallbackInvocation.c_str()); | 64 element_id.c_str(), kCallbackInvocation.c_str()); |
65 NSDate* deadline = | |
66 [NSDate dateWithTimeIntervalSinceNow:testing::kWaitForUIElementTimeout]; | |
67 bool verifier_added = false; | |
68 while (([[NSDate date] compare:deadline] != NSOrderedDescending) && | |
69 !verifier_added) { | |
70 std::unique_ptr<base::Value> value = | |
71 web::test::ExecuteJavaScript(web_state, kAddVerifierScript); | |
72 if (value) { | |
73 std::string error; | |
74 if (value->GetAsString(&error)) { | |
75 DLOG(ERROR) << "Verifier injection failed: " << error << ", retrying."; | |
76 } else if (value->GetAsBoolean(&verifier_added)) { | |
77 verifier_added = true; | |
78 } | |
79 } | |
80 base::test::ios::SpinRunLoopWithMaxDelay( | |
81 base::TimeDelta::FromSecondsD(testing::kSpinDelaySeconds)); | |
82 } | |
83 | 65 |
84 if (!verifier_added) | 66 bool success = testing::WaitUntilConditionOrTimeout( |
67 testing::kWaitForUIElementTimeout, ^bool() { | |
Eugene But (OOO till 7-30)
2016/10/25 14:43:39
Optional nit: You don't need |bool() |
baxley
2016/10/25 18:50:05
Done.
| |
68 bool verifier_added = false; | |
69 std::unique_ptr<base::Value> value = | |
70 web::test::ExecuteJavaScript(web_state, kAddVerifierScript); | |
71 if (value) { | |
72 std::string error; | |
73 if (value->GetAsString(&error)) { | |
74 DLOG(ERROR) << "Verifier injection failed: " << error | |
75 << ", retrying."; | |
76 } else if (value->GetAsBoolean(&verifier_added)) { | |
77 return true; | |
78 } | |
79 } | |
80 return false; | |
81 }); | |
82 | |
83 if (!success) | |
85 return false; | 84 return false; |
86 | 85 |
87 // The callback doesn't care about any of the parameters, just whether it is | 86 // The callback doesn't care about any of the parameters, just whether it is |
88 // called or not. | 87 // called or not. |
89 auto callback = base::BindBlock(^bool(const base::DictionaryValue& /* json */, | 88 auto callback = base::BindBlock(^bool(const base::DictionaryValue& /* json */, |
90 const GURL& /* origin_url */, | 89 const GURL& /* origin_url */, |
91 bool /* user_is_interacting */) { | 90 bool /* user_is_interacting */) { |
92 *verified = true; | 91 *verified = true; |
93 return true; | 92 return true; |
94 }); | 93 }); |
(...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
168 | 167 |
169 if (*error) { | 168 if (*error) { |
170 return NO; | 169 return NO; |
171 } | 170 } |
172 | 171 |
173 // Wait for the verified to trigger and set |verified|. | 172 // Wait for the verified to trigger and set |verified|. |
174 NSString* verification_timeout_message = | 173 NSString* verification_timeout_message = |
175 [NSString stringWithFormat:@"The action (%@) on element_id %s wasn't " | 174 [NSString stringWithFormat:@"The action (%@) on element_id %s wasn't " |
176 @"verified before timing out.", | 175 @"verified before timing out.", |
177 action.name, element_id.c_str()]; | 176 action.name, element_id.c_str()]; |
178 testing::WaitUntilCondition(testing::kWaitForJSCompletionTimeout, | 177 GREYAssert(testing::WaitUntilConditionOrTimeout( |
179 verification_timeout_message, ^{ | 178 testing::kWaitForJSCompletionTimeout, |
180 return verified; | 179 ^{ |
181 }); | 180 return verified; |
181 }), | |
182 verification_timeout_message); | |
182 | 183 |
183 // If |verified| is not true, the wait condition should have already exited | 184 // If |verified| is not true, the wait condition should have already exited |
184 // this control flow, so sanity check that it has in fact been set to | 185 // this control flow, so sanity check that it has in fact been set to |
185 // true by this point. | 186 // true by this point. |
186 DCHECK(verified); | 187 DCHECK(verified); |
187 return YES; | 188 return YES; |
188 }; | 189 }; |
189 | 190 |
190 return [GREYActionBlock actionWithName:action_name | 191 return [GREYActionBlock actionWithName:action_name |
191 constraints:webViewInWebState(state) | 192 constraints:webViewInWebState(state) |
(...skipping 20 matching lines...) Expand all Loading... | |
212 id<GREYAction> webViewTapElement(WebState* state, | 213 id<GREYAction> webViewTapElement(WebState* state, |
213 const std::string& element_id) { | 214 const std::string& element_id) { |
214 CGRect rect = web::test::GetBoundingRectOfElementWithId(state, element_id); | 215 CGRect rect = web::test::GetBoundingRectOfElementWithId(state, element_id); |
215 CGPoint point = CGPointMake(CGRectGetMidX(rect), CGRectGetMidY(rect)); | 216 CGPoint point = CGPointMake(CGRectGetMidX(rect), CGRectGetMidY(rect)); |
216 return CGRectIsEmpty(rect) ? webViewElementNotFound(element_id) | 217 return CGRectIsEmpty(rect) ? webViewElementNotFound(element_id) |
217 : webViewVerifiedActionOnElement( | 218 : webViewVerifiedActionOnElement( |
218 state, grey_tapAtPoint(point), element_id); | 219 state, grey_tapAtPoint(point), element_id); |
219 } | 220 } |
220 | 221 |
221 } // namespace web | 222 } // namespace web |
OLD | NEW |