stripe.js
220 lines
| 1 | /* global ppress_stripe_vars */ |
| 2 | /* global ppressCheckoutForm */ |
| 3 | /* global pp_ajax_form */ |
| 4 | |
| 5 | (function ($) { |
| 6 | |
| 7 | function PPressStripe() { |
| 8 | |
| 9 | var _this = this, |
| 10 | stripe = Stripe(ppress_stripe_vars.publishable_key, { |
| 11 | 'locale': ppress_stripe_vars.locale |
| 12 | }); |
| 13 | |
| 14 | this.init = function () { |
| 15 | |
| 16 | window.processCheckoutFlag = false; |
| 17 | window.confirmPaymentFlag = false; |
| 18 | |
| 19 | $(document).on('ppress_updated_checkout', _this.updated_checkout); |
| 20 | |
| 21 | $(document).on('ppress_update_checkout', _this.unmountPaymentElement); |
| 22 | |
| 23 | $(document).on('click', '#ppress-checkout-button', function () { |
| 24 | window.processCheckoutFlag = true; |
| 25 | }); |
| 26 | |
| 27 | _this.updatePaymentElement(); |
| 28 | }; |
| 29 | |
| 30 | this.updated_checkout = function (e, response) { |
| 31 | |
| 32 | _this.checkout_form = $('form#ppress_mb_checkout_form'); |
| 33 | |
| 34 | _this.checkout_form.on('ppress_checkout_place_order_stripe', _this.validateFormSubmission); |
| 35 | _this.checkout_form.on('ppress_process_checkout_stripe', _this.processCheckout); |
| 36 | |
| 37 | _this.mountPaymentElement(response); |
| 38 | }; |
| 39 | |
| 40 | this.fieldValueOrEmpty = function (field) { |
| 41 | if (!field) return ''; |
| 42 | |
| 43 | return field; |
| 44 | }; |
| 45 | |
| 46 | this.getBillingDetails = function () { |
| 47 | var country = $('#stripe_ppress_billing_country').val(), |
| 48 | state = $('#stripe_ppress_billing_state').val(), |
| 49 | val = { |
| 50 | name: _this.fieldValueOrEmpty($('#stripe-card_name').val()), |
| 51 | email: _this.fieldValueOrEmpty($('#ppmb_email').val()), |
| 52 | phone: _this.fieldValueOrEmpty($('#stripe_ppress_billing_phone').val()) |
| 53 | }; |
| 54 | |
| 55 | // only include address to billing details if the billing address fields are in the checkout form |
| 56 | if (country) { |
| 57 | val.address = { |
| 58 | line1: _this.fieldValueOrEmpty($('#stripe_ppress_billing_address').val()), |
| 59 | line2: '', |
| 60 | city: _this.fieldValueOrEmpty($('#stripe_ppress_billing_city').val()), |
| 61 | state: _this.fieldValueOrEmpty(state), |
| 62 | country: _this.fieldValueOrEmpty(country), |
| 63 | postal_code: _this.fieldValueOrEmpty($('#stripe_ppress_billing_postcode').val()), |
| 64 | } |
| 65 | } |
| 66 | |
| 67 | return val; |
| 68 | }; |
| 69 | |
| 70 | this.updatePaymentElement = function () { |
| 71 | |
| 72 | var callback = function () { |
| 73 | |
| 74 | _this.unmountPaymentElement(); |
| 75 | |
| 76 | if (typeof window.elements.create !== 'undefined') { |
| 77 | window.paymentElement = window.elements.create('payment', _this.getPaymentOptions()); |
| 78 | window.paymentElement.mount('#ppress-stripe-card-element'); |
| 79 | } |
| 80 | }; |
| 81 | |
| 82 | // If the email address is changed, re-mount to allow the Link element to show. |
| 83 | $(document).on('change', '#ppmb_email', callback); |
| 84 | }; |
| 85 | |
| 86 | this.getPaymentOptions = function () { |
| 87 | var obj = { |
| 88 | layout: {type: 'tabs'}, |
| 89 | fields: { |
| 90 | billingDetails: ppress_stripe_vars.hideBillingFields === 'true' ? 'never' : 'auto' |
| 91 | }, |
| 92 | terms: { |
| 93 | card: 'never' |
| 94 | } |
| 95 | }; |
| 96 | |
| 97 | // [Fix] Passing "never" for fields.billingDetails in combination with defaultValues.billingDetails is not recommended. |
| 98 | // Instead pass billing_details when creating the payment method or confirming the payment. |
| 99 | if (obj.fields.billingDetails === 'auto') { |
| 100 | obj.defaultValues = { |
| 101 | billingDetails: _this.getBillingDetails() |
| 102 | }; |
| 103 | } |
| 104 | |
| 105 | return obj; |
| 106 | }; |
| 107 | |
| 108 | this.mountPaymentElement = function (response) { |
| 109 | |
| 110 | if ($('#ppress-stripe-card-element').length === 0) return; |
| 111 | |
| 112 | window.elements = stripe.elements(response.data.stripe_args); |
| 113 | |
| 114 | window.paymentElement = window.elements.create('payment', _this.getPaymentOptions()); |
| 115 | |
| 116 | window.paymentElement.mount('#ppress-stripe-card-element'); |
| 117 | }; |
| 118 | |
| 119 | this.unmountPaymentElement = function () { |
| 120 | |
| 121 | if ($('#ppress-stripe-card-element').length === 0) return; |
| 122 | |
| 123 | if (typeof window.paymentElement.destroy !== 'undefined') { |
| 124 | window.paymentElement.destroy(); |
| 125 | } |
| 126 | }; |
| 127 | |
| 128 | this.validateFormSubmission = function () { |
| 129 | |
| 130 | if (window.processCheckoutFlag === true) { |
| 131 | |
| 132 | window.processCheckoutFlag = false; |
| 133 | |
| 134 | window.elements.submit().then(function (result) { |
| 135 | |
| 136 | if ('error' in result && typeof result.error.message !== 'undefined') { |
| 137 | ppressCheckoutForm.createAlertMessage(result.error.message); |
| 138 | } else { |
| 139 | _this.checkout_form.trigger('submit'); |
| 140 | } |
| 141 | }); |
| 142 | |
| 143 | return false; |
| 144 | } |
| 145 | }; |
| 146 | |
| 147 | this.processCheckout = function (e, response, payment_method) { |
| 148 | |
| 149 | if (ppressCheckoutForm.is_var_defined(response.gateway_response) === true) { |
| 150 | |
| 151 | if ( |
| 152 | ppressCheckoutForm.is_var_defined(response.gateway_response.latest_invoice) === true || // for subscription payments |
| 153 | ppressCheckoutForm.is_var_defined(response.gateway_response.status) === true // for one-time payments |
| 154 | ) { |
| 155 | |
| 156 | // ensure the below block of code runs once |
| 157 | if (window.confirmPaymentFlag === false) { |
| 158 | |
| 159 | window.confirmPaymentFlag = true; |
| 160 | |
| 161 | var client_secret, stripeAction = 'confirmPayment', actionResultParam = 'paymentIntent'; |
| 162 | |
| 163 | if (ppressCheckoutForm.is_var_defined(response.gateway_response.client_secret)) { |
| 164 | client_secret = response.gateway_response.client_secret; |
| 165 | } else if ( |
| 166 | ppressCheckoutForm.is_var_defined(response.gateway_response.latest_invoice.payment_intent) && |
| 167 | ppressCheckoutForm.is_var_defined(response.gateway_response.latest_invoice.payment_intent.client_secret) |
| 168 | ) { |
| 169 | client_secret = response.gateway_response.latest_invoice.payment_intent.client_secret; |
| 170 | } else if ( |
| 171 | ppressCheckoutForm.is_var_defined(response.gateway_response.setup_intent_response) && |
| 172 | ppressCheckoutForm.is_var_defined(response.gateway_response.setup_intent_response.client_secret) |
| 173 | ) { |
| 174 | client_secret = response.gateway_response.setup_intent_response.client_secret; |
| 175 | stripeAction = 'confirmSetup'; |
| 176 | actionResultParam = 'setupIntent'; |
| 177 | } |
| 178 | |
| 179 | if (typeof client_secret === 'undefined') { |
| 180 | $(document.body).trigger('ppress_checkout_success', [response, payment_method]); |
| 181 | window.location.assign(response.order_success_url); |
| 182 | } |
| 183 | |
| 184 | var cp_getBillingDetails = _this.getBillingDetails(); |
| 185 | |
| 186 | stripe[stripeAction]({ |
| 187 | elements: window.elements, |
| 188 | clientSecret: client_secret, |
| 189 | confirmParams: { |
| 190 | return_url: response.order_success_url, |
| 191 | payment_method_data: { |
| 192 | billing_details: cp_getBillingDetails |
| 193 | } |
| 194 | }, |
| 195 | redirect: 'if_required' |
| 196 | |
| 197 | }).then(function (result) { |
| 198 | if (result.error) { |
| 199 | window.confirmPaymentFlag = false; |
| 200 | ppressCheckoutForm.createAlertMessage(result.error.message); |
| 201 | } else { |
| 202 | |
| 203 | if (result[actionResultParam]['status'] === 'succeeded') { |
| 204 | $(document.body).trigger('ppress_checkout_success', [response, payment_method]); |
| 205 | } |
| 206 | |
| 207 | window.location.assign(response.order_success_url); |
| 208 | } |
| 209 | }); |
| 210 | } |
| 211 | |
| 212 | return false; |
| 213 | } |
| 214 | } |
| 215 | }; |
| 216 | } |
| 217 | |
| 218 | (new PPressStripe()).init(); |
| 219 | |
| 220 | })(jQuery); |