Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(64)

Unified Diff: ios/chrome/browser/payments/payment_request_manager.mm

Issue 2632463003: Add a timeout if the page doesn't call complete() in a timely fashion. (Closed)
Patch Set: Created 3 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: ios/chrome/browser/payments/payment_request_manager.mm
diff --git a/ios/chrome/browser/payments/payment_request_manager.mm b/ios/chrome/browser/payments/payment_request_manager.mm
index 657183145f2098c5333df7c8a8daa4518e4d0ad9..5aa3e0634fb2cf3d10ee80063b3be89dddf333aa 100644
--- a/ios/chrome/browser/payments/payment_request_manager.mm
+++ b/ios/chrome/browser/payments/payment_request_manager.mm
@@ -32,6 +32,14 @@
namespace {
// Command prefix for injected JavaScript.
const std::string kCommandPrefix = "paymentRequest";
+
+// Time interval between attempts to unblock the webview's JS event queue.
+const NSTimeInterval kNoopInterval = 0.1;
+
+// Time interval before closing the UI if the page has not yet called
+// PaymentResponse.complete().
+const NSTimeInterval kTimeoutInterval = 60.0;
+
} // namespace
@interface PaymentRequestManager ()<PaymentRequestCoordinatorDelegate,
@@ -65,6 +73,13 @@ const std::string kCommandPrefix = "paymentRequest";
// Coordinator used to create and present the PaymentRequest view controller.
base::scoped_nsobject<PaymentRequestCoordinator> _paymentRequestCoordinator;
+
+ // Timer used to periodically unblock the webview's JS event queue.
+ base::scoped_nsobject<NSTimer> _unblockEventQueueTimer;
+
+ // Timer used to close the UI if the page does not call
+ // PaymentResponse.complete() in a timely fashion.
+ base::scoped_nsobject<NSTimer> _paymentResponseTimeoutTimer;
}
// Synchronous method executed by -asynchronouslyEnablePaymentRequest:
@@ -282,9 +297,11 @@ const std::string kCommandPrefix = "paymentRequest";
// TODO(crbug.com/602666): Check that there *is* a pending response here.
// TODO(crbug.com/602666): Indicate success or failure in the UI.
+ [_unblockEventQueueTimer invalidate];
+ [_paymentResponseTimeoutTimer invalidate];
+
[self dismissUI];
- // TODO(crbug.com/602666): Reject the promise on failure.
[_paymentRequestJsManager resolveResponsePromise:nil];
return YES;
@@ -322,6 +339,26 @@ const std::string kCommandPrefix = "paymentRequest";
(web::PaymentResponse)paymentResponse {
[_paymentRequestJsManager resolveRequestPromise:paymentResponse
completionHandler:nil];
+
+ // Establish a timer that periodically prompts the JS manager to execute a
+ // noop. This works around an issue where the JS event queue is blocked while
+ // presenting the Payment Request UI.
+ _unblockEventQueueTimer.reset(
+ [[NSTimer scheduledTimerWithTimeInterval:kNoopInterval
+ target:_paymentRequestJsManager
+ selector:@selector(executeNoop)
+ userInfo:nil
+ repeats:YES] retain]);
Moe 2017/01/16 21:52:58 is executeNoop what fixes the landscape issue? Why
Justin Donnelly 2017/01/18 19:36:21 Correct, this fixes the landscape issue. Switching
+
+ // Per the spec, if the page does not call PaymentResponse.complete() within
+ // some timeout period, user agents may behave as if the complete() method was
+ // called with no arguments.
+ _paymentResponseTimeoutTimer.reset(
+ [[NSTimer scheduledTimerWithTimeInterval:kTimeoutInterval
+ target:self
+ selector:@selector(handleResponseComplete)
+ userInfo:nil
+ repeats:NO] retain]);
}
#pragma mark - PaymentRequestWebStateDelegate methods

Powered by Google App Engine
This is Rietveld 408576698