MDL-69166 pg_paypal: render PayPal buttons and set up transaction
authorShamim Rezaie <shamim@moodle.com>
Fri, 3 Jan 2020 09:07:51 +0000 (20:07 +1100)
committerShamim Rezaie <shamim@moodle.com>
Tue, 27 Oct 2020 04:44:59 +0000 (15:44 +1100)
We truncate brand_name to 127 chars as per PayPal requirement.

payment/gateway/paypal/amd/build/gateways_modal.min.js [new file with mode: 0644]
payment/gateway/paypal/amd/build/gateways_modal.min.js.map [new file with mode: 0644]
payment/gateway/paypal/amd/build/selectors.min.js [new file with mode: 0644]
payment/gateway/paypal/amd/build/selectors.min.js.map [new file with mode: 0644]
payment/gateway/paypal/amd/src/gateways_modal.js [new file with mode: 0644]
payment/gateway/paypal/amd/src/selectors.js [new file with mode: 0644]
payment/gateway/paypal/templates/paypal_button_placeholder.mustache [new file with mode: 0644]

diff --git a/payment/gateway/paypal/amd/build/gateways_modal.min.js b/payment/gateway/paypal/amd/build/gateways_modal.min.js
new file mode 100644 (file)
index 0000000..0199fd2
Binary files /dev/null and b/payment/gateway/paypal/amd/build/gateways_modal.min.js differ
diff --git a/payment/gateway/paypal/amd/build/gateways_modal.min.js.map b/payment/gateway/paypal/amd/build/gateways_modal.min.js.map
new file mode 100644 (file)
index 0000000..bd19358
Binary files /dev/null and b/payment/gateway/paypal/amd/build/gateways_modal.min.js.map differ
diff --git a/payment/gateway/paypal/amd/build/selectors.min.js b/payment/gateway/paypal/amd/build/selectors.min.js
new file mode 100644 (file)
index 0000000..4779204
Binary files /dev/null and b/payment/gateway/paypal/amd/build/selectors.min.js differ
diff --git a/payment/gateway/paypal/amd/build/selectors.min.js.map b/payment/gateway/paypal/amd/build/selectors.min.js.map
new file mode 100644 (file)
index 0000000..41f80eb
Binary files /dev/null and b/payment/gateway/paypal/amd/build/selectors.min.js.map differ
diff --git a/payment/gateway/paypal/amd/src/gateways_modal.js b/payment/gateway/paypal/amd/src/gateways_modal.js
new file mode 100644 (file)
index 0000000..4fa4269
--- /dev/null
@@ -0,0 +1,103 @@
+// This file is part of Moodle - http://moodle.org/
+//
+// Moodle is free software: you can redistribute it and/or modify
+// it under the terms of the GNU General Public License as published by
+// the Free Software Foundation, either version 3 of the License, or
+// (at your option) any later version.
+//
+// Moodle is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
+
+/**
+ * This module is responsible for PayPal content in the gateways modal.
+ *
+ * @module     pg_paypal/gateway_modal
+ * @copyright  2020 Shamim Rezaie <shamim@moodle.com>
+ * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
+ */
+
+import * as Repository from './repository';
+import Templates from 'core/templates';
+import Selectors from './selectors';
+import Truncate from 'core/truncate';
+
+/**
+ * Renders a placeholder in the modal.
+ *
+ * @param rootElement
+ * @returns {Promise<void>}
+ */
+const showPlaceholder = async(rootElement) => {
+    const {html, js} = await Templates.renderForPromise('pg_paypal/paypal_button_placeholder', {});
+    Templates.replaceNodeContents(rootElement.querySelector(Selectors.regions.gatewaysContainer), html, js);
+};
+
+export const process = async(rootElement, amount, currency, component, componentid) => {
+
+    const [
+        ,
+        paypalConfig,
+    ] = await Promise.all([
+        showPlaceholder(rootElement),
+        Repository.getConfigForJs(),
+    ]);
+
+    const paypalScript = `https://www.paypal.com/sdk/js?client-id=${paypalConfig.clientid}&currency=${currency}`;
+
+    callExternalFunction(paypalScript, () => {
+        rootElement.querySelector(Selectors.buttons.save).style.display = 'none';
+        rootElement.querySelector(Selectors.regions.gatewaysContainer).innerHTML = '';
+        paypal.Buttons({ // eslint-disable-line
+            createOrder: function(data, actions) {
+                // This function sets up the details of the transaction, including the amount and line item details.
+                return actions.order.create({
+                    purchase_units: [{ // eslint-disable-line
+                        amount: {
+                            currency_code: currency, // eslint-disable-line
+                            value: amount
+                        }
+                    }],
+                    application_context: { // eslint-disable-line
+                        shipping_preference: 'NO_SHIPPING', // eslint-disable-line
+                        brand_name: Truncate.truncate(paypalConfig.brandname, {length: 127, stripTags: true}), // eslint-disable-line
+                    },
+                });
+            },
+        }).render(Selectors.regions.gatewaysContainer);
+    });
+};
+
+const callExternalFunction = (jsFile, callback) => {
+    // Check to see if this file has already been loaded. If so just go straight to the callback.
+    if (callExternalFunction.currentlyloaded.includes(jsFile)) {
+        callback();
+        return;
+    }
+
+    const script = document.createElement('script');
+
+    if (script.readyState) {
+        script.onreadystatechange = function() {
+            if (this.readyState == 'complete' || this.readyState == 'loaded') {
+                this.onreadystatechange = null;
+                callback();
+            }
+        };
+    } else {
+        script.onload = function() {
+            callback();
+        };
+    }
+
+    script.setAttribute('src', jsFile);
+    document.head.appendChild(script);
+
+    callExternalFunction.currentlyloaded.push(jsFile);
+};
+
+callExternalFunction.currentlyloaded = [];
diff --git a/payment/gateway/paypal/amd/src/selectors.js b/payment/gateway/paypal/amd/src/selectors.js
new file mode 100644 (file)
index 0000000..1515be7
--- /dev/null
@@ -0,0 +1,32 @@
+// This file is part of Moodle - http://moodle.org/
+//
+// Moodle is free software: you can redistribute it and/or modify
+// it under the terms of the GNU General Public License as published by
+// the Free Software Foundation, either version 3 of the License, or
+// (at your option) any later version.
+//
+// Moodle is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+//
+// You should have received a copy of the GNU General Public License
+// along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
+
+/**
+ * Define all of the selectors we will be using on the gateways modal.
+ *
+ * @module     pg_paypal/selectors
+ * @package    pg_paypal
+ * @copyright  2019 Shamim Rezaie <shamim@moodle.com>
+ * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
+ */
+
+export default {
+    regions: {
+        gatewaysContainer: '[data-region="gateways-container"]',
+    },
+    buttons: {
+        save: '[data-action="save"]',
+    },
+};
diff --git a/payment/gateway/paypal/templates/paypal_button_placeholder.mustache b/payment/gateway/paypal/templates/paypal_button_placeholder.mustache
new file mode 100644 (file)
index 0000000..b4118f9
--- /dev/null
@@ -0,0 +1,35 @@
+{{!
+    This file is part of Moodle - http://moodle.org/
+
+    Moodle is free software: you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    Moodle is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
+}}
+{{!
+    @template paygw_paypal/paypal_button_placeholder
+
+    Classes required for JS:
+    * none
+
+    Data attributes required for JS:
+    * none
+
+    Context variables required for this template:
+    * none
+
+    Example context (json):
+    {}
+
+}}
+<div class="bg-pulse-grey rounded" style="width: 100%; height: 45px; margin-bottom: 14px;"></div>
+<div class="bg-pulse-grey rounded" style="width: 100%; height: 45px; margin-bottom: 14px;"></div>
+<div class="bg-pulse-grey" style="width: 110px; height: 16px; margin: 10px auto; position: relative; bottom: 3px;"></div>
\ No newline at end of file