| 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 #include "modules/payments/PaymentRequest.h" | 5 #include "modules/payments/PaymentRequest.h" |
| 6 | 6 |
| 7 #include "bindings/core/v8/ExceptionState.h" | 7 #include "bindings/core/v8/ExceptionState.h" |
| 8 #include "bindings/core/v8/ScriptPromiseResolver.h" | 8 #include "bindings/core/v8/ScriptPromiseResolver.h" |
| 9 #include "bindings/core/v8/ScriptState.h" | 9 #include "bindings/core/v8/ScriptState.h" |
| 10 #include "bindings/core/v8/V8StringResource.h" | 10 #include "bindings/core/v8/V8StringResource.h" |
| (...skipping 17 matching lines...) Expand all Loading... |
| 28 #include "mojo/public/cpp/bindings/wtf_array.h" | 28 #include "mojo/public/cpp/bindings/wtf_array.h" |
| 29 #include "platform/mojo/MojoHelper.h" | 29 #include "platform/mojo/MojoHelper.h" |
| 30 #include "public/platform/InterfaceProvider.h" | 30 #include "public/platform/InterfaceProvider.h" |
| 31 #include "public/platform/Platform.h" | 31 #include "public/platform/Platform.h" |
| 32 #include "public/platform/WebTraceLocation.h" | 32 #include "public/platform/WebTraceLocation.h" |
| 33 #include "wtf/HashSet.h" | 33 #include "wtf/HashSet.h" |
| 34 #include <utility> | 34 #include <utility> |
| 35 | 35 |
| 36 namespace mojo { | 36 namespace mojo { |
| 37 | 37 |
| 38 using payments::mojom::blink::PaymentCurrencyAmount; | 38 using blink::mojom::blink::PaymentCurrencyAmount; |
| 39 using payments::mojom::blink::PaymentCurrencyAmountPtr; | 39 using blink::mojom::blink::PaymentCurrencyAmountPtr; |
| 40 using payments::mojom::blink::PaymentDetails; | 40 using blink::mojom::blink::PaymentDetails; |
| 41 using payments::mojom::blink::PaymentDetailsModifier; | 41 using blink::mojom::blink::PaymentDetailsModifier; |
| 42 using payments::mojom::blink::PaymentDetailsModifierPtr; | 42 using blink::mojom::blink::PaymentDetailsModifierPtr; |
| 43 using payments::mojom::blink::PaymentDetailsPtr; | 43 using blink::mojom::blink::PaymentDetailsPtr; |
| 44 using payments::mojom::blink::PaymentErrorReason; | 44 using blink::mojom::blink::PaymentErrorReason; |
| 45 using payments::mojom::blink::PaymentItem; | 45 using blink::mojom::blink::PaymentItem; |
| 46 using payments::mojom::blink::PaymentItemPtr; | 46 using blink::mojom::blink::PaymentItemPtr; |
| 47 using payments::mojom::blink::PaymentMethodData; | 47 using blink::mojom::blink::PaymentMethodData; |
| 48 using payments::mojom::blink::PaymentMethodDataPtr; | 48 using blink::mojom::blink::PaymentMethodDataPtr; |
| 49 using payments::mojom::blink::PaymentOptions; | 49 using blink::mojom::blink::PaymentOptions; |
| 50 using payments::mojom::blink::PaymentOptionsPtr; | 50 using blink::mojom::blink::PaymentOptionsPtr; |
| 51 using payments::mojom::blink::PaymentShippingOption; | 51 using blink::mojom::blink::PaymentShippingOption; |
| 52 using payments::mojom::blink::PaymentShippingOptionPtr; | 52 using blink::mojom::blink::PaymentShippingOptionPtr; |
| 53 using payments::mojom::blink::PaymentShippingType; | 53 using blink::mojom::blink::PaymentShippingType; |
| 54 | 54 |
| 55 template <> | 55 template <> |
| 56 struct TypeConverter<PaymentCurrencyAmountPtr, blink::PaymentCurrencyAmount> { | 56 struct TypeConverter<PaymentCurrencyAmountPtr, blink::PaymentCurrencyAmount> { |
| 57 static PaymentCurrencyAmountPtr Convert( | 57 static PaymentCurrencyAmountPtr Convert( |
| 58 const blink::PaymentCurrencyAmount& input) { | 58 const blink::PaymentCurrencyAmount& input) { |
| 59 PaymentCurrencyAmountPtr output = PaymentCurrencyAmount::New(); | 59 PaymentCurrencyAmountPtr output = PaymentCurrencyAmount::New(); |
| 60 output->currency = input.currency(); | 60 output->currency = input.currency(); |
| 61 output->value = input.value(); | 61 output->value = input.value(); |
| 62 if (input.hasCurrencySystem()) | 62 if (input.hasCurrencySystem()) |
| 63 output->currencySystem = input.currencySystem(); | 63 output->currencySystem = input.currencySystem(); |
| (...skipping 347 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 411 static const char* const validValues[] = { | 411 static const char* const validValues[] = { |
| 412 "shipping", "delivery", "pickup", | 412 "shipping", "delivery", "pickup", |
| 413 }; | 413 }; |
| 414 for (size_t i = 0; i < WTF_ARRAY_LENGTH(validValues); i++) { | 414 for (size_t i = 0; i < WTF_ARRAY_LENGTH(validValues); i++) { |
| 415 if (shippingType == validValues[i]) | 415 if (shippingType == validValues[i]) |
| 416 return shippingType; | 416 return shippingType; |
| 417 } | 417 } |
| 418 return validValues[0]; | 418 return validValues[0]; |
| 419 } | 419 } |
| 420 | 420 |
| 421 payments::mojom::blink::PaymentDetailsPtr maybeKeepShippingOptions( | 421 mojom::blink::PaymentDetailsPtr maybeKeepShippingOptions( |
| 422 payments::mojom::blink::PaymentDetailsPtr details, | 422 mojom::blink::PaymentDetailsPtr details, |
| 423 bool keep) { | 423 bool keep) { |
| 424 if (!keep) | 424 if (!keep) |
| 425 details->shipping_options.resize(0); | 425 details->shipping_options.resize(0); |
| 426 | 426 |
| 427 return details; | 427 return details; |
| 428 } | 428 } |
| 429 | 429 |
| 430 bool allowedToUsePaymentRequest(const Frame* frame) { | 430 bool allowedToUsePaymentRequest(const Frame* frame) { |
| 431 // To determine whether a Document object |document| is allowed to use the | 431 // To determine whether a Document object |document| is allowed to use the |
| 432 // feature indicated by attribute name |allowpaymentrequest|, run these steps: | 432 // feature indicated by attribute name |allowpaymentrequest|, run these steps: |
| (...skipping 15 matching lines...) Expand all Loading... |
| 448 if (ownerElement && isHTMLIFrameElement(ownerElement)) { | 448 if (ownerElement && isHTMLIFrameElement(ownerElement)) { |
| 449 HTMLIFrameElement* iframe = toHTMLIFrameElement(ownerElement); | 449 HTMLIFrameElement* iframe = toHTMLIFrameElement(ownerElement); |
| 450 if (HTMLIFrameElementPayments::from(*iframe).allowPaymentRequest(*iframe)) | 450 if (HTMLIFrameElementPayments::from(*iframe).allowPaymentRequest(*iframe)) |
| 451 return allowedToUsePaymentRequest(frame->tree().parent()); | 451 return allowedToUsePaymentRequest(frame->tree().parent()); |
| 452 } | 452 } |
| 453 | 453 |
| 454 // 4. Return false. | 454 // 4. Return false. |
| 455 return false; | 455 return false; |
| 456 } | 456 } |
| 457 | 457 |
| 458 WTF::Vector<payments::mojom::blink::PaymentMethodDataPtr> | 458 WTF::Vector<mojom::blink::PaymentMethodDataPtr> ConvertPaymentMethodData( |
| 459 ConvertPaymentMethodData( | |
| 460 const Vector<PaymentRequest::MethodData>& blinkMethods) { | 459 const Vector<PaymentRequest::MethodData>& blinkMethods) { |
| 461 WTF::Vector<payments::mojom::blink::PaymentMethodDataPtr> mojoMethods( | 460 WTF::Vector<mojom::blink::PaymentMethodDataPtr> mojoMethods( |
| 462 blinkMethods.size()); | 461 blinkMethods.size()); |
| 463 for (size_t i = 0; i < blinkMethods.size(); ++i) { | 462 for (size_t i = 0; i < blinkMethods.size(); ++i) { |
| 464 mojoMethods[i] = payments::mojom::blink::PaymentMethodData::New(); | 463 mojoMethods[i] = mojom::blink::PaymentMethodData::New(); |
| 465 mojoMethods[i]->supported_methods = | 464 mojoMethods[i]->supported_methods = |
| 466 WTF::Vector<WTF::String>(blinkMethods[i].supportedMethods); | 465 WTF::Vector<WTF::String>(blinkMethods[i].supportedMethods); |
| 467 mojoMethods[i]->stringified_data = blinkMethods[i].stringifiedData; | 466 mojoMethods[i]->stringified_data = blinkMethods[i].stringifiedData; |
| 468 } | 467 } |
| 469 return mojoMethods; | 468 return mojoMethods; |
| 470 } | 469 } |
| 471 | 470 |
| 472 } // namespace | 471 } // namespace |
| 473 | 472 |
| 474 PaymentRequest* PaymentRequest::create( | 473 PaymentRequest* PaymentRequest::create( |
| (...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 556 | 555 |
| 557 // User has cancelled the transaction while the website was processing it. | 556 // User has cancelled the transaction while the website was processing it. |
| 558 if (!m_paymentProvider) | 557 if (!m_paymentProvider) |
| 559 return ScriptPromise::rejectWithDOMException( | 558 return ScriptPromise::rejectWithDOMException( |
| 560 scriptState, | 559 scriptState, |
| 561 DOMException::create(InvalidStateError, "Request cancelled")); | 560 DOMException::create(InvalidStateError, "Request cancelled")); |
| 562 | 561 |
| 563 m_completeTimer.stop(); | 562 m_completeTimer.stop(); |
| 564 | 563 |
| 565 // The payment provider should respond in PaymentRequest::OnComplete(). | 564 // The payment provider should respond in PaymentRequest::OnComplete(). |
| 566 m_paymentProvider->Complete(payments::mojom::blink::PaymentComplete(result)); | 565 m_paymentProvider->Complete(mojom::blink::PaymentComplete(result)); |
| 567 | 566 |
| 568 m_completeResolver = ScriptPromiseResolver::create(scriptState); | 567 m_completeResolver = ScriptPromiseResolver::create(scriptState); |
| 569 return m_completeResolver->promise(); | 568 return m_completeResolver->promise(); |
| 570 } | 569 } |
| 571 | 570 |
| 572 void PaymentRequest::onUpdatePaymentDetails( | 571 void PaymentRequest::onUpdatePaymentDetails( |
| 573 const ScriptValue& detailsScriptValue) { | 572 const ScriptValue& detailsScriptValue) { |
| 574 if (!m_showResolver || !m_paymentProvider) | 573 if (!m_showResolver || !m_paymentProvider) |
| 575 return; | 574 return; |
| 576 | 575 |
| (...skipping 18 matching lines...) Expand all Loading... |
| 595 } | 594 } |
| 596 | 595 |
| 597 if (m_options.requestShipping()) { | 596 if (m_options.requestShipping()) { |
| 598 if (keepShippingOptions) | 597 if (keepShippingOptions) |
| 599 m_shippingOption = getSelectedShippingOption(details); | 598 m_shippingOption = getSelectedShippingOption(details); |
| 600 else | 599 else |
| 601 m_shippingOption = String(); | 600 m_shippingOption = String(); |
| 602 } | 601 } |
| 603 | 602 |
| 604 m_paymentProvider->UpdateWith(maybeKeepShippingOptions( | 603 m_paymentProvider->UpdateWith(maybeKeepShippingOptions( |
| 605 payments::mojom::blink::PaymentDetails::From(details), | 604 mojom::blink::PaymentDetails::From(details), keepShippingOptions)); |
| 606 keepShippingOptions)); | |
| 607 } | 605 } |
| 608 | 606 |
| 609 void PaymentRequest::onUpdatePaymentDetailsFailure(const String& error) { | 607 void PaymentRequest::onUpdatePaymentDetailsFailure(const String& error) { |
| 610 if (m_showResolver) | 608 if (m_showResolver) |
| 611 m_showResolver->reject(DOMException::create(AbortError, error)); | 609 m_showResolver->reject(DOMException::create(AbortError, error)); |
| 612 if (m_completeResolver) | 610 if (m_completeResolver) |
| 613 m_completeResolver->reject(DOMException::create(AbortError, error)); | 611 m_completeResolver->reject(DOMException::create(AbortError, error)); |
| 614 clearResolversAndCloseMojoConnection(); | 612 clearResolversAndCloseMojoConnection(); |
| 615 } | 613 } |
| 616 | 614 |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 669 if (m_options.requestShipping()) { | 667 if (m_options.requestShipping()) { |
| 670 if (keepShippingOptions) | 668 if (keepShippingOptions) |
| 671 m_shippingOption = getSelectedShippingOption(details); | 669 m_shippingOption = getSelectedShippingOption(details); |
| 672 m_shippingType = getValidShippingType(m_options.shippingType()); | 670 m_shippingType = getValidShippingType(m_options.shippingType()); |
| 673 } | 671 } |
| 674 | 672 |
| 675 scriptState->domWindow()->frame()->interfaceProvider()->getInterface( | 673 scriptState->domWindow()->frame()->interfaceProvider()->getInterface( |
| 676 mojo::GetProxy(&m_paymentProvider)); | 674 mojo::GetProxy(&m_paymentProvider)); |
| 677 m_paymentProvider.set_connection_error_handler(convertToBaseCallback( | 675 m_paymentProvider.set_connection_error_handler(convertToBaseCallback( |
| 678 WTF::bind(&PaymentRequest::OnError, wrapWeakPersistent(this), | 676 WTF::bind(&PaymentRequest::OnError, wrapWeakPersistent(this), |
| 679 payments::mojom::blink::PaymentErrorReason::UNKNOWN))); | 677 mojom::blink::PaymentErrorReason::UNKNOWN))); |
| 680 m_paymentProvider->Init( | 678 m_paymentProvider->Init( |
| 681 m_clientBinding.CreateInterfacePtrAndBind(), | 679 m_clientBinding.CreateInterfacePtrAndBind(), |
| 682 ConvertPaymentMethodData(validatedMethodData), | 680 ConvertPaymentMethodData(validatedMethodData), |
| 683 maybeKeepShippingOptions( | 681 maybeKeepShippingOptions( |
| 684 payments::mojom::blink::PaymentDetails::From(details), | 682 mojom::blink::PaymentDetails::From(details), |
| 685 keepShippingOptions && m_options.requestShipping()), | 683 keepShippingOptions && m_options.requestShipping()), |
| 686 payments::mojom::blink::PaymentOptions::From(m_options)); | 684 mojom::blink::PaymentOptions::From(m_options)); |
| 687 } | 685 } |
| 688 | 686 |
| 689 void PaymentRequest::contextDestroyed() { | 687 void PaymentRequest::contextDestroyed() { |
| 690 clearResolversAndCloseMojoConnection(); | 688 clearResolversAndCloseMojoConnection(); |
| 691 } | 689 } |
| 692 | 690 |
| 693 void PaymentRequest::OnShippingAddressChange( | 691 void PaymentRequest::OnShippingAddressChange( |
| 694 payments::mojom::blink::PaymentAddressPtr address) { | 692 mojom::blink::PaymentAddressPtr address) { |
| 695 DCHECK(m_showResolver); | 693 DCHECK(m_showResolver); |
| 696 DCHECK(!m_completeResolver); | 694 DCHECK(!m_completeResolver); |
| 697 | 695 |
| 698 String errorMessage; | 696 String errorMessage; |
| 699 if (!PaymentsValidators::isValidShippingAddress(address, &errorMessage)) { | 697 if (!PaymentsValidators::isValidShippingAddress(address, &errorMessage)) { |
| 700 m_showResolver->reject(DOMException::create(SyntaxError, errorMessage)); | 698 m_showResolver->reject(DOMException::create(SyntaxError, errorMessage)); |
| 701 clearResolversAndCloseMojoConnection(); | 699 clearResolversAndCloseMojoConnection(); |
| 702 return; | 700 return; |
| 703 } | 701 } |
| 704 | 702 |
| (...skipping 14 matching lines...) Expand all Loading... |
| 719 PaymentRequestUpdateEvent* event = | 717 PaymentRequestUpdateEvent* event = |
| 720 PaymentRequestUpdateEvent::create(EventTypeNames::shippingoptionchange); | 718 PaymentRequestUpdateEvent::create(EventTypeNames::shippingoptionchange); |
| 721 event->setTarget(this); | 719 event->setTarget(this); |
| 722 event->setPaymentDetailsUpdater(this); | 720 event->setPaymentDetailsUpdater(this); |
| 723 bool success = getExecutionContext()->getEventQueue()->enqueueEvent(event); | 721 bool success = getExecutionContext()->getEventQueue()->enqueueEvent(event); |
| 724 DCHECK(success); | 722 DCHECK(success); |
| 725 ALLOW_UNUSED_LOCAL(success); | 723 ALLOW_UNUSED_LOCAL(success); |
| 726 } | 724 } |
| 727 | 725 |
| 728 void PaymentRequest::OnPaymentResponse( | 726 void PaymentRequest::OnPaymentResponse( |
| 729 payments::mojom::blink::PaymentResponsePtr response) { | 727 mojom::blink::PaymentResponsePtr response) { |
| 730 DCHECK(m_showResolver); | 728 DCHECK(m_showResolver); |
| 731 DCHECK(!m_completeResolver); | 729 DCHECK(!m_completeResolver); |
| 732 DCHECK(!m_completeTimer.isActive()); | 730 DCHECK(!m_completeTimer.isActive()); |
| 733 | 731 |
| 734 if (m_options.requestShipping()) { | 732 if (m_options.requestShipping()) { |
| 735 if (!response->shipping_address || response->shipping_option.isEmpty()) { | 733 if (!response->shipping_address || response->shipping_option.isEmpty()) { |
| 736 m_showResolver->reject(DOMException::create(SyntaxError)); | 734 m_showResolver->reject(DOMException::create(SyntaxError)); |
| 737 clearResolversAndCloseMojoConnection(); | 735 clearResolversAndCloseMojoConnection(); |
| 738 return; | 736 return; |
| 739 } | 737 } |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 781 if (!Platform::current()) { | 779 if (!Platform::current()) { |
| 782 // TODO(rockot): Clean this up once renderer shutdown sequence is fixed. | 780 // TODO(rockot): Clean this up once renderer shutdown sequence is fixed. |
| 783 return; | 781 return; |
| 784 } | 782 } |
| 785 | 783 |
| 786 bool isError = false; | 784 bool isError = false; |
| 787 ExceptionCode ec = UnknownError; | 785 ExceptionCode ec = UnknownError; |
| 788 String message; | 786 String message; |
| 789 | 787 |
| 790 switch (error) { | 788 switch (error) { |
| 791 case payments::mojom::blink::PaymentErrorReason::USER_CANCEL: | 789 case mojom::blink::PaymentErrorReason::USER_CANCEL: |
| 792 message = "Request cancelled"; | 790 message = "Request cancelled"; |
| 793 break; | 791 break; |
| 794 case payments::mojom::blink::PaymentErrorReason::NOT_SUPPORTED: | 792 case mojom::blink::PaymentErrorReason::NOT_SUPPORTED: |
| 795 isError = true; | 793 isError = true; |
| 796 ec = NotSupportedError; | 794 ec = NotSupportedError; |
| 797 message = "The payment method is not supported"; | 795 message = "The payment method is not supported"; |
| 798 break; | 796 break; |
| 799 case payments::mojom::blink::PaymentErrorReason::UNKNOWN: | 797 case mojom::blink::PaymentErrorReason::UNKNOWN: |
| 800 isError = true; | 798 isError = true; |
| 801 ec = UnknownError; | 799 ec = UnknownError; |
| 802 message = "Request failed"; | 800 message = "Request failed"; |
| 803 break; | 801 break; |
| 804 } | 802 } |
| 805 | 803 |
| 806 DCHECK(!message.isEmpty()); | 804 DCHECK(!message.isEmpty()); |
| 807 | 805 |
| 808 if (isError) { | 806 if (isError) { |
| 809 if (m_completeResolver) | 807 if (m_completeResolver) |
| (...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 843 m_abortResolver.clear(); | 841 m_abortResolver.clear(); |
| 844 return; | 842 return; |
| 845 } | 843 } |
| 846 | 844 |
| 847 m_showResolver->reject(DOMException::create(AbortError)); | 845 m_showResolver->reject(DOMException::create(AbortError)); |
| 848 m_abortResolver->resolve(); | 846 m_abortResolver->resolve(); |
| 849 clearResolversAndCloseMojoConnection(); | 847 clearResolversAndCloseMojoConnection(); |
| 850 } | 848 } |
| 851 | 849 |
| 852 void PaymentRequest::onCompleteTimeout(TimerBase*) { | 850 void PaymentRequest::onCompleteTimeout(TimerBase*) { |
| 853 m_paymentProvider->Complete(payments::mojom::blink::PaymentComplete(Fail)); | 851 m_paymentProvider->Complete(mojom::blink::PaymentComplete(Fail)); |
| 854 clearResolversAndCloseMojoConnection(); | 852 clearResolversAndCloseMojoConnection(); |
| 855 } | 853 } |
| 856 | 854 |
| 857 void PaymentRequest::clearResolversAndCloseMojoConnection() { | 855 void PaymentRequest::clearResolversAndCloseMojoConnection() { |
| 858 m_completeTimer.stop(); | 856 m_completeTimer.stop(); |
| 859 m_completeResolver.clear(); | 857 m_completeResolver.clear(); |
| 860 m_showResolver.clear(); | 858 m_showResolver.clear(); |
| 861 m_abortResolver.clear(); | 859 m_abortResolver.clear(); |
| 862 if (m_clientBinding.is_bound()) | 860 if (m_clientBinding.is_bound()) |
| 863 m_clientBinding.Close(); | 861 m_clientBinding.Close(); |
| 864 m_paymentProvider.reset(); | 862 m_paymentProvider.reset(); |
| 865 } | 863 } |
| 866 | 864 |
| 867 } // namespace blink | 865 } // namespace blink |
| OLD | NEW |