diff --git a/app/code/Magento/Paypal/Model/Express.php b/app/code/Magento/Paypal/Model/Express.php index 8ba8adcede511..accb22b265335 100644 --- a/app/code/Magento/Paypal/Model/Express.php +++ b/app/code/Magento/Paypal/Model/Express.php @@ -669,7 +669,7 @@ public function getApi() public function assignData(\Magento\Framework\DataObject $data) { parent::assignData($data); - + $additionalData = $data->getData(PaymentInterface::KEY_ADDITIONAL_DATA); if (!is_array($additionalData)) { @@ -677,6 +677,11 @@ public function assignData(\Magento\Framework\DataObject $data) } foreach ($additionalData as $key => $value) { + // Skip extension attributes + if ($key === \Magento\Framework\Api\ExtensibleDataInterface::EXTENSION_ATTRIBUTES_KEY) { + continue; + } + $this->getInfoInstance()->setAdditionalInformation($key, $value); } return $this; diff --git a/app/code/Magento/Paypal/Test/Unit/Model/ExpressTest.php b/app/code/Magento/Paypal/Test/Unit/Model/ExpressTest.php index 6a2d33d010190..1b8c33622e784 100644 --- a/app/code/Magento/Paypal/Test/Unit/Model/ExpressTest.php +++ b/app/code/Magento/Paypal/Test/Unit/Model/ExpressTest.php @@ -161,12 +161,21 @@ public function testAssignData() { $transportValue = 'something'; + $extensionAttribute = $this->getMockForAbstractClass( + \Magento\Quote\Api\Data\PaymentExtensionInterface::class, + [], + '', + false, + false + ); + $data = new DataObject( [ PaymentInterface::KEY_ADDITIONAL_DATA => [ Express\Checkout::PAYMENT_INFO_TRANSPORT_BILLING_AGREEMENT => $transportValue, Express\Checkout::PAYMENT_INFO_TRANSPORT_PAYER_ID => $transportValue, - Express\Checkout::PAYMENT_INFO_TRANSPORT_TOKEN => $transportValue + Express\Checkout::PAYMENT_INFO_TRANSPORT_TOKEN => $transportValue, + \Magento\Framework\Api\ExtensibleDataInterface::EXTENSION_ATTRIBUTES_KEY => $extensionAttribute ] ] ); diff --git a/app/code/Magento/Paypal/view/frontend/web/js/action/set-payment-method.js b/app/code/Magento/Paypal/view/frontend/web/js/action/set-payment-method.js index a994f9defd583..63e34437c6f90 100644 --- a/app/code/Magento/Paypal/view/frontend/web/js/action/set-payment-method.js +++ b/app/code/Magento/Paypal/view/frontend/web/js/action/set-payment-method.js @@ -4,48 +4,12 @@ */ define([ - 'jquery', 'Magento_Checkout/js/model/quote', - 'Magento_Checkout/js/model/url-builder', - 'mage/storage', - 'Magento_Checkout/js/model/error-processor', - 'Magento_Customer/js/model/customer', - 'Magento_Checkout/js/model/full-screen-loader' -], function ($, quote, urlBuilder, storage, errorProcessor, customer, fullScreenLoader) { + 'Magento_Checkout/js/action/set-payment-information' +], function (quote, setPaymentInformation) { 'use strict'; return function (messageContainer) { - var serviceUrl, - payload, - paymentData = quote.paymentMethod(); - - /** - * Checkout for guest and registered customer. - */ - if (!customer.isLoggedIn()) { - serviceUrl = urlBuilder.createUrl('/guest-carts/:cartId/set-payment-information', { - cartId: quote.getQuoteId() - }); - payload = { - cartId: quote.getQuoteId(), - email: quote.guestEmail, - paymentMethod: paymentData - }; - } else { - serviceUrl = urlBuilder.createUrl('/carts/mine/set-payment-information', {}); - payload = { - cartId: quote.getQuoteId(), - paymentMethod: paymentData - }; - } - fullScreenLoader.startLoader(); - - return storage.post( - serviceUrl, JSON.stringify(payload) - ).fail(function (response) { - errorProcessor.process(response, messageContainer); - }).always(function () { - fullScreenLoader.stopLoader(); - }); + return setPaymentInformation(messageContainer, quote.paymentMethod()); }; }); diff --git a/dev/tests/js/jasmine/tests/app/code/Magento/CheckoutAgreements/frontend/js/model/place-order-mixin.test.js b/dev/tests/js/jasmine/tests/app/code/Magento/CheckoutAgreements/frontend/js/model/place-order-mixin.test.js new file mode 100644 index 0000000000000..545daf0a330c9 --- /dev/null +++ b/dev/tests/js/jasmine/tests/app/code/Magento/CheckoutAgreements/frontend/js/model/place-order-mixin.test.js @@ -0,0 +1,55 @@ +/** + * Copyright © Magento, Inc. All rights reserved. + * See COPYING.txt for license details. + */ + +define([ + 'squire' +], function (Squire) { + 'use strict'; + + var injector = new Squire(), + mocks = { + 'Magento_Checkout/js/action/place-order': jasmine.createSpy('placeOrderAction'), + 'Magento_CheckoutAgreements/js/model/agreements-assigner': jasmine.createSpy('agreementsAssigner') + }, + defaultContext = require.s.contexts._, + mixin, + placeOrderAction; + + beforeEach(function (done) { + window.checkoutConfig = { + checkoutAgreements: { + isEnabled: true + } + }; + injector.mock(mocks); + injector.require([ + 'Magento_CheckoutAgreements/js/model/place-order-mixin', + 'Magento_Checkout/js/action/place-order' + ], function (Mixin, placeOrder) { + mixin = Mixin; + placeOrderAction = placeOrder; + done(); + }); + }); + + describe('Magento_CheckoutAgreements/js/model/place-order-mixin', function () { + it('mixin is applied to Magento_Checkout/js/action/place-order', function () { + var placeOrderMixins = defaultContext.config.config.mixins['Magento_Checkout/js/action/place-order']; + + expect(placeOrderMixins['Magento_CheckoutAgreements/js/model/place-order-mixin']).toBe(true); + }); + + it('Magento_CheckoutAgreements/js/model/agreements-assigner is called', function () { + var messageContainer = jasmine.createSpy('messageContainer'), + paymentData = {}; + + mixin(placeOrderAction)(paymentData, messageContainer); + expect(mocks['Magento_CheckoutAgreements/js/model/agreements-assigner']) + .toHaveBeenCalledWith(paymentData); + expect(mocks['Magento_Checkout/js/action/place-order']) + .toHaveBeenCalledWith(paymentData, messageContainer); + }); + }); +}); diff --git a/dev/tests/js/jasmine/tests/app/code/Magento/CheckoutAgreements/frontend/js/model/set-payment-information-mixin.test.js b/dev/tests/js/jasmine/tests/app/code/Magento/CheckoutAgreements/frontend/js/model/set-payment-information-mixin.test.js new file mode 100644 index 0000000000000..ed525bfd96a6c --- /dev/null +++ b/dev/tests/js/jasmine/tests/app/code/Magento/CheckoutAgreements/frontend/js/model/set-payment-information-mixin.test.js @@ -0,0 +1,56 @@ +/** + * Copyright © Magento, Inc. All rights reserved. + * See COPYING.txt for license details. + */ + +define([ + 'squire' +], function (Squire) { + 'use strict'; + + var injector = new Squire(), + mocks = { + 'Magento_Checkout/js/action/set-payment-information': jasmine.createSpy('placeOrderAction'), + 'Magento_CheckoutAgreements/js/model/agreements-assigner': jasmine.createSpy('agreementsAssigner') + }, + defaultContext = require.s.contexts._, + mixin, + placeOrderAction; + + beforeEach(function (done) { + window.checkoutConfig = { + checkoutAgreements: { + isEnabled: true + } + }; + injector.mock(mocks); + injector.require([ + 'Magento_CheckoutAgreements/js/model/set-payment-information-mixin', + 'Magento_Checkout/js/action/set-payment-information' + ], function (Mixin, setPaymentInformation) { + mixin = Mixin; + placeOrderAction = setPaymentInformation; + done(); + }); + }); + + describe('Magento_CheckoutAgreements/js/model/set-payment-information-mixin', function () { + it('mixin is applied to Magento_Checkout/js/action/set-payment-information', function () { + var placeOrderMixins = defaultContext + .config.config.mixins['Magento_Checkout/js/action/set-payment-information']; + + expect(placeOrderMixins['Magento_CheckoutAgreements/js/model/set-payment-information-mixin']).toBe(true); + }); + + it('Magento_CheckoutAgreements/js/model/agreements-assigner is called', function () { + var messageContainer = jasmine.createSpy('messageContainer'), + paymentData = {}; + + mixin(placeOrderAction)(messageContainer, paymentData); + expect(mocks['Magento_CheckoutAgreements/js/model/agreements-assigner']) + .toHaveBeenCalledWith(paymentData); + expect(mocks['Magento_Checkout/js/action/set-payment-information']) + .toHaveBeenCalledWith(messageContainer, paymentData); + }); + }); +}); diff --git a/dev/tests/js/jasmine/tests/app/code/Magento/Paypal/frontend/js/view/payment/method-renderer/paypal-express-abstract.test.js b/dev/tests/js/jasmine/tests/app/code/Magento/Paypal/frontend/js/view/payment/method-renderer/paypal-express-abstract.test.js index dc520c5238568..47e3507ea1321 100644 --- a/dev/tests/js/jasmine/tests/app/code/Magento/Paypal/frontend/js/view/payment/method-renderer/paypal-express-abstract.test.js +++ b/dev/tests/js/jasmine/tests/app/code/Magento/Paypal/frontend/js/view/payment/method-renderer/paypal-express-abstract.test.js @@ -16,6 +16,13 @@ define([ describe('paypal/js/view/payment/method-renderer/paypal-express-abstract', function () { var injector = new Squire(), + successPromise = jasmine.createSpyObj('successPromise', ['done']), + setPaymentMock = jasmine.createSpy('set-payment-information', function () { + return successPromise; + }).and.callThrough(), + validateMock = jasmine.createSpy('validate', function () { + return true; + }).and.callThrough(), mocks = { 'Magento_Checkout/js/model/quote': { billingAddress: ko.observable(), @@ -23,6 +30,10 @@ define([ paymentMethod: ko.observable(), totals: ko.observable({}) + }, + 'Magento_Checkout/js/action/set-payment-information': setPaymentMock, + 'Magento_Checkout/js/model/payment/additional-validators': { + validate: validateMock } }, paypalExpressAbstract, @@ -85,6 +96,23 @@ define([ }, 500); }); + it('setPaymentMethodAction is called before redirect to paypal', function () { + spyOn(paypalExpressAbstract, 'selectPaymentMethod'); + paypalExpressAbstract.continueToPayPal(); + expect(paypalExpressAbstract.selectPaymentMethod).toHaveBeenCalled(); + expect(validateMock).toHaveBeenCalled(); + expect(validateMock.calls.mostRecent()).toEqual(jasmine.objectContaining({ + object: mocks['Magento_Checkout/js/model/payment/additional-validators'], + args: [], + returnValue: true + })); + expect(setPaymentMock).toHaveBeenCalled(); + expect(setPaymentMock.calls.mostRecent()).toEqual(jasmine.objectContaining({ + returnValue: successPromise + })); + expect(successPromise.done).toHaveBeenCalledWith(jasmine.any(Function)); + }); + afterAll(function (done) { tplElement.remove(); done();