@easypayment/medusa-paypal-ui 1.1.1 → 1.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +97 -61
- package/README.md +781 -759
- package/dist/index.cjs +143 -142
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +64 -2
- package/dist/index.d.ts +64 -2
- package/dist/index.mjs +133 -136
- package/dist/index.mjs.map +1 -1
- package/dist/order.cjs +14 -3
- package/dist/order.cjs.map +1 -1
- package/dist/order.d.cts +13 -4
- package/dist/order.d.ts +13 -4
- package/dist/order.mjs +13 -4
- package/dist/order.mjs.map +1 -1
- package/package.json +76 -75
- package/src/adapters/MedusaNextPayPalAdapter.tsx +34 -5
- package/src/client/http.ts +9 -1
- package/src/client/paypal.ts +27 -1
- package/src/components/PayPalAdvancedCard.tsx +24 -0
- package/src/components/PayPalPaymentSection.tsx +95 -202
- package/src/components/PayPalSmartButtons.tsx +24 -0
- package/src/constants.ts +22 -0
- package/src/hooks/usePayPalPaymentMethods.ts +15 -1
- package/src/index.ts +5 -0
- package/src/order.ts +7 -10
- package/src/utils/captured-state.ts +44 -0
package/dist/index.cjs
CHANGED
|
@@ -39,13 +39,17 @@ __export(index_exports, {
|
|
|
39
39
|
PayPalPaymentSection: () => PayPalPaymentSection,
|
|
40
40
|
PayPalProvider: () => PayPalProvider,
|
|
41
41
|
PayPalSmartButtons: () => PayPalSmartButtons,
|
|
42
|
+
clearCartCaptured: () => clearCartCaptured,
|
|
42
43
|
createPayPalStoreApi: () => createPayPalStoreApi,
|
|
44
|
+
generateIdempotencyKey: () => generateIdempotencyKey,
|
|
43
45
|
hideProcessingOverlay: () => hideProcessingOverlay,
|
|
44
46
|
isPayPalProviderId: () => isPayPalProviderId,
|
|
47
|
+
markCartCaptured: () => markCartCaptured,
|
|
45
48
|
markPaymentComplete: () => markPaymentComplete,
|
|
46
49
|
showProcessingOverlay: () => showProcessingOverlay,
|
|
47
50
|
usePayPalConfig: () => usePayPalConfig,
|
|
48
|
-
usePayPalPaymentMethods: () => usePayPalPaymentMethods
|
|
51
|
+
usePayPalPaymentMethods: () => usePayPalPaymentMethods,
|
|
52
|
+
wasCartCaptured: () => wasCartCaptured
|
|
49
53
|
});
|
|
50
54
|
module.exports = __toCommonJS(index_exports);
|
|
51
55
|
|
|
@@ -115,7 +119,7 @@ function createHttpClient(opts) {
|
|
|
115
119
|
res = await fetch(url, {
|
|
116
120
|
...init,
|
|
117
121
|
headers,
|
|
118
|
-
credentials: "include",
|
|
122
|
+
credentials: opts.credentials ?? "include",
|
|
119
123
|
signal: controller.signal
|
|
120
124
|
});
|
|
121
125
|
text = await res.text().catch(() => "");
|
|
@@ -184,6 +188,14 @@ function createHttpClient(opts) {
|
|
|
184
188
|
}
|
|
185
189
|
|
|
186
190
|
// src/client/paypal.ts
|
|
191
|
+
function generateIdempotencyKey() {
|
|
192
|
+
try {
|
|
193
|
+
const c = globalThis.crypto;
|
|
194
|
+
if (c?.randomUUID) return c.randomUUID();
|
|
195
|
+
} catch {
|
|
196
|
+
}
|
|
197
|
+
return `pp-${Date.now().toString(36)}-${Math.random().toString(36).slice(2, 12)}`;
|
|
198
|
+
}
|
|
187
199
|
async function markPaymentComplete(baseUrl, cartId, publishableApiKey) {
|
|
188
200
|
const http = createHttpClient({ baseUrl, publishableApiKey });
|
|
189
201
|
return http.request(
|
|
@@ -209,7 +221,13 @@ function createPayPalStoreApi(opts) {
|
|
|
209
221
|
createOrder(cartId, isCardPayment = false) {
|
|
210
222
|
return http.request(`/store/paypal/create-order`, {
|
|
211
223
|
method: "POST",
|
|
212
|
-
headers: {
|
|
224
|
+
headers: {
|
|
225
|
+
"Content-Type": "application/json",
|
|
226
|
+
// One key per attempt — see generateIdempotencyKey. Deliberately NOT
|
|
227
|
+
// sent for capture-order: there the server's deterministic
|
|
228
|
+
// per-order-id fallback is the correct idempotency scope.
|
|
229
|
+
"Idempotency-Key": generateIdempotencyKey()
|
|
230
|
+
},
|
|
213
231
|
body: JSON.stringify({ cart_id: cartId, is_card_payment: isCardPayment })
|
|
214
232
|
});
|
|
215
233
|
},
|
|
@@ -342,6 +360,31 @@ function PayPalCurrencyNotice({ config }) {
|
|
|
342
360
|
var import_react3 = require("react");
|
|
343
361
|
var import_react_paypal_js2 = require("@paypal/react-paypal-js");
|
|
344
362
|
|
|
363
|
+
// src/utils/captured-state.ts
|
|
364
|
+
var KEY_PREFIX = "__pp_captured::";
|
|
365
|
+
function markCartCaptured(cartId) {
|
|
366
|
+
if (!cartId) return;
|
|
367
|
+
try {
|
|
368
|
+
window.sessionStorage.setItem(`${KEY_PREFIX}${cartId}`, String(Date.now()));
|
|
369
|
+
} catch {
|
|
370
|
+
}
|
|
371
|
+
}
|
|
372
|
+
function wasCartCaptured(cartId) {
|
|
373
|
+
if (!cartId) return false;
|
|
374
|
+
try {
|
|
375
|
+
return window.sessionStorage.getItem(`${KEY_PREFIX}${cartId}`) !== null;
|
|
376
|
+
} catch {
|
|
377
|
+
return false;
|
|
378
|
+
}
|
|
379
|
+
}
|
|
380
|
+
function clearCartCaptured(cartId) {
|
|
381
|
+
if (!cartId) return;
|
|
382
|
+
try {
|
|
383
|
+
window.sessionStorage.removeItem(`${KEY_PREFIX}${cartId}`);
|
|
384
|
+
} catch {
|
|
385
|
+
}
|
|
386
|
+
}
|
|
387
|
+
|
|
345
388
|
// src/utils/next-errors.ts
|
|
346
389
|
function isNextRouterError(e) {
|
|
347
390
|
if (typeof e !== "object" || e === null || !("digest" in e)) return false;
|
|
@@ -465,6 +508,13 @@ function PayPalSmartButtons(props) {
|
|
|
465
508
|
window.addEventListener("pageshow", onPageShow);
|
|
466
509
|
return () => window.removeEventListener("pageshow", onPageShow);
|
|
467
510
|
}, []);
|
|
511
|
+
(0, import_react3.useEffect)(() => {
|
|
512
|
+
if (capturedRef.current || !wasCartCaptured(cartId)) return;
|
|
513
|
+
capturedRef.current = {};
|
|
514
|
+
setCompletionPending(true);
|
|
515
|
+
const msg = "Your payment was already received for this cart. Please use the button below to finish placing your order \u2014 do not pay again.";
|
|
516
|
+
setError(msg);
|
|
517
|
+
}, [cartId]);
|
|
468
518
|
(0, import_react3.useEffect)(() => {
|
|
469
519
|
if (!isResolved || buttonsReady) {
|
|
470
520
|
return;
|
|
@@ -480,6 +530,7 @@ function PayPalSmartButtons(props) {
|
|
|
480
530
|
setError(null);
|
|
481
531
|
try {
|
|
482
532
|
const completeResult = await markPaymentComplete(baseUrl, cartId, publishableApiKey);
|
|
533
|
+
clearCartCaptured(cartId);
|
|
483
534
|
await onPaid?.({ ...captured, ...completeResult });
|
|
484
535
|
setCompletionPending(false);
|
|
485
536
|
} catch (e) {
|
|
@@ -750,6 +801,7 @@ function PayPalSmartButtons(props) {
|
|
|
750
801
|
if (!orderId) throw new Error("PayPal order ID is missing from approval response");
|
|
751
802
|
const result = await api.captureOrder(cartId, orderId);
|
|
752
803
|
capturedRef.current = result || {};
|
|
804
|
+
markCartCaptured(cartId);
|
|
753
805
|
} catch (e) {
|
|
754
806
|
if (isNextRouterError(e)) return;
|
|
755
807
|
hideProcessingOverlay();
|
|
@@ -958,6 +1010,14 @@ function PayPalAdvancedCard(props) {
|
|
|
958
1010
|
window.addEventListener("pageshow", onPageShow);
|
|
959
1011
|
return () => window.removeEventListener("pageshow", onPageShow);
|
|
960
1012
|
}, []);
|
|
1013
|
+
import_react4.default.useEffect(() => {
|
|
1014
|
+
if (capturedRef.current || !wasCartCaptured(cartId)) return;
|
|
1015
|
+
capturedRef.current = {};
|
|
1016
|
+
setCompletionPending(true);
|
|
1017
|
+
setError(
|
|
1018
|
+
"Your payment was already received for this cart. Please use the button below to finish placing your order \u2014 do not pay again."
|
|
1019
|
+
);
|
|
1020
|
+
}, [cartId]);
|
|
961
1021
|
const finalizeCapturedPayment = import_react4.default.useCallback(async () => {
|
|
962
1022
|
const captured = capturedRef.current;
|
|
963
1023
|
if (!captured) return;
|
|
@@ -966,6 +1026,7 @@ function PayPalAdvancedCard(props) {
|
|
|
966
1026
|
setError(null);
|
|
967
1027
|
try {
|
|
968
1028
|
const completeResult = await markPaymentComplete(baseUrl, cartId, publishableApiKey);
|
|
1029
|
+
clearCartCaptured(cartId);
|
|
969
1030
|
await onPaid?.({ ...captured, ...completeResult });
|
|
970
1031
|
setCompletionPending(false);
|
|
971
1032
|
} catch (e) {
|
|
@@ -1187,6 +1248,7 @@ function PayPalAdvancedCard(props) {
|
|
|
1187
1248
|
if (!orderId) throw new Error("PayPal order ID is missing from approval response");
|
|
1188
1249
|
const result = await api.captureOrder(cartId, orderId);
|
|
1189
1250
|
capturedRef.current = result || {};
|
|
1251
|
+
markCartCaptured(cartId);
|
|
1190
1252
|
} catch (e) {
|
|
1191
1253
|
if (isNextRouterError(e)) return;
|
|
1192
1254
|
resetSubmitState();
|
|
@@ -1375,9 +1437,23 @@ function PayPalAdvancedCard(props) {
|
|
|
1375
1437
|
|
|
1376
1438
|
// src/adapters/MedusaNextPayPalAdapter.tsx
|
|
1377
1439
|
var import_react5 = require("react");
|
|
1440
|
+
|
|
1441
|
+
// src/constants.ts
|
|
1442
|
+
var PAYPAL_WALLET_PROVIDER_ID = "pp_paypal_paypal";
|
|
1443
|
+
var PAYPAL_CARD_PROVIDER_ID = "pp_paypal_card_paypal_card";
|
|
1444
|
+
var PAYPAL_PROVIDER_IDS = [
|
|
1445
|
+
PAYPAL_WALLET_PROVIDER_ID,
|
|
1446
|
+
PAYPAL_CARD_PROVIDER_ID
|
|
1447
|
+
];
|
|
1448
|
+
function isPayPalProviderId(providerId) {
|
|
1449
|
+
if (!providerId) return false;
|
|
1450
|
+
return PAYPAL_PROVIDER_IDS.includes(
|
|
1451
|
+
providerId
|
|
1452
|
+
);
|
|
1453
|
+
}
|
|
1454
|
+
|
|
1455
|
+
// src/adapters/MedusaNextPayPalAdapter.tsx
|
|
1378
1456
|
var import_jsx_runtime5 = require("react/jsx-runtime");
|
|
1379
|
-
var DEFAULT_PAYPAL_PROVIDER_ID = "pp_paypal_paypal";
|
|
1380
|
-
var DEFAULT_PAYPAL_CARD_PROVIDER_ID = "pp_paypal_card_paypal_card";
|
|
1381
1457
|
var SPIN_STYLE3 = `@keyframes _pp_spin { to { transform: rotate(360deg) } }`;
|
|
1382
1458
|
function PayPalLoadingCard() {
|
|
1383
1459
|
return /* @__PURE__ */ (0, import_jsx_runtime5.jsxs)(
|
|
@@ -1435,6 +1511,26 @@ function PayPalErrorCard({ message }) {
|
|
|
1435
1511
|
}
|
|
1436
1512
|
);
|
|
1437
1513
|
}
|
|
1514
|
+
function PayPalUnavailableCard({ label }) {
|
|
1515
|
+
return /* @__PURE__ */ (0, import_jsx_runtime5.jsxs)(
|
|
1516
|
+
"div",
|
|
1517
|
+
{
|
|
1518
|
+
role: "status",
|
|
1519
|
+
style: {
|
|
1520
|
+
padding: "12px 16px",
|
|
1521
|
+
background: "#f9fafb",
|
|
1522
|
+
border: "1px solid #e5e7eb",
|
|
1523
|
+
borderRadius: 10,
|
|
1524
|
+
fontSize: 13,
|
|
1525
|
+
color: "#6b7280"
|
|
1526
|
+
},
|
|
1527
|
+
children: [
|
|
1528
|
+
label,
|
|
1529
|
+
" is currently unavailable. Please choose a different payment method."
|
|
1530
|
+
]
|
|
1531
|
+
}
|
|
1532
|
+
);
|
|
1533
|
+
}
|
|
1438
1534
|
function MedusaNextPayPalAdapter(props) {
|
|
1439
1535
|
const {
|
|
1440
1536
|
cartId,
|
|
@@ -1446,8 +1542,8 @@ function MedusaNextPayPalAdapter(props) {
|
|
|
1446
1542
|
onError,
|
|
1447
1543
|
onPaid
|
|
1448
1544
|
} = props;
|
|
1449
|
-
const paypalProviderId = providerIds?.paypal ||
|
|
1450
|
-
const paypalCardProviderId = providerIds?.paypalCard ||
|
|
1545
|
+
const paypalProviderId = providerIds?.paypal || PAYPAL_WALLET_PROVIDER_ID;
|
|
1546
|
+
const paypalCardProviderId = providerIds?.paypalCard || PAYPAL_CARD_PROVIDER_ID;
|
|
1451
1547
|
const shouldRender = selectedProviderId === paypalProviderId || selectedProviderId === paypalCardProviderId;
|
|
1452
1548
|
const { config, loading, error } = usePayPalConfig({
|
|
1453
1549
|
baseUrl,
|
|
@@ -1467,8 +1563,12 @@ function MedusaNextPayPalAdapter(props) {
|
|
|
1467
1563
|
if (error) return /* @__PURE__ */ (0, import_jsx_runtime5.jsx)(PayPalErrorCard, { message: error });
|
|
1468
1564
|
if (!config) return null;
|
|
1469
1565
|
const isCardProvider = selectedProviderId === paypalCardProviderId;
|
|
1470
|
-
if (config.paypal_enabled === false && !isCardProvider)
|
|
1471
|
-
|
|
1566
|
+
if (config.paypal_enabled === false && !isCardProvider) {
|
|
1567
|
+
return /* @__PURE__ */ (0, import_jsx_runtime5.jsx)(PayPalUnavailableCard, { label: config.paypal_title || "PayPal" });
|
|
1568
|
+
}
|
|
1569
|
+
if (isCardProvider && config.card_enabled === false) {
|
|
1570
|
+
return /* @__PURE__ */ (0, import_jsx_runtime5.jsx)(PayPalUnavailableCard, { label: config.card_title || "Card payment" });
|
|
1571
|
+
}
|
|
1472
1572
|
const disableFunding = Array.isArray(config.disable_buttons) ? config.disable_buttons.join(",") : void 0;
|
|
1473
1573
|
return /* @__PURE__ */ (0, import_jsx_runtime5.jsxs)("div", { style: { display: "grid", gap: 12 }, children: [
|
|
1474
1574
|
/* @__PURE__ */ (0, import_jsx_runtime5.jsx)(PayPalCurrencyNotice, { config }),
|
|
@@ -1505,18 +1605,7 @@ function MedusaNextPayPalAdapter(props) {
|
|
|
1505
1605
|
}
|
|
1506
1606
|
|
|
1507
1607
|
// src/components/PayPalPaymentSection.tsx
|
|
1508
|
-
var import_react6 = require("react");
|
|
1509
1608
|
var import_jsx_runtime6 = require("react/jsx-runtime");
|
|
1510
|
-
var PAYPAL_WALLET_PROVIDER_ID = "pp_paypal_paypal";
|
|
1511
|
-
var PAYPAL_CARD_PROVIDER_ID = "pp_paypal_card_paypal_card";
|
|
1512
|
-
var PAYPAL_PROVIDER_IDS = [
|
|
1513
|
-
PAYPAL_WALLET_PROVIDER_ID,
|
|
1514
|
-
PAYPAL_CARD_PROVIDER_ID
|
|
1515
|
-
];
|
|
1516
|
-
function isPayPalProviderId(id) {
|
|
1517
|
-
if (!id) return false;
|
|
1518
|
-
return PAYPAL_PROVIDER_IDS.includes(id);
|
|
1519
|
-
}
|
|
1520
1609
|
var SPIN_STYLE4 = `@keyframes _pp_section_spin { to { transform: rotate(360deg) } }`;
|
|
1521
1610
|
function SessionInitCard() {
|
|
1522
1611
|
return /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)(
|
|
@@ -1555,62 +1644,6 @@ function SessionInitCard() {
|
|
|
1555
1644
|
}
|
|
1556
1645
|
);
|
|
1557
1646
|
}
|
|
1558
|
-
function ConfigLoadingCard() {
|
|
1559
|
-
return /* @__PURE__ */ (0, import_jsx_runtime6.jsxs)(
|
|
1560
|
-
"div",
|
|
1561
|
-
{
|
|
1562
|
-
role: "status",
|
|
1563
|
-
"aria-label": "Connecting to PayPal",
|
|
1564
|
-
style: {
|
|
1565
|
-
display: "flex",
|
|
1566
|
-
alignItems: "center",
|
|
1567
|
-
gap: 12,
|
|
1568
|
-
padding: "14px 16px",
|
|
1569
|
-
background: "#f9fafb",
|
|
1570
|
-
border: "1px solid #e5e7eb",
|
|
1571
|
-
borderRadius: 10
|
|
1572
|
-
},
|
|
1573
|
-
children: [
|
|
1574
|
-
/* @__PURE__ */ (0, import_jsx_runtime6.jsx)("style", { children: SPIN_STYLE4 }),
|
|
1575
|
-
/* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
|
|
1576
|
-
"div",
|
|
1577
|
-
{
|
|
1578
|
-
style: {
|
|
1579
|
-
width: 22,
|
|
1580
|
-
height: 22,
|
|
1581
|
-
borderRadius: "50%",
|
|
1582
|
-
border: "2.5px solid #e5e7eb",
|
|
1583
|
-
borderTopColor: "#0070ba",
|
|
1584
|
-
animation: "_pp_section_spin .7s linear infinite",
|
|
1585
|
-
flexShrink: 0
|
|
1586
|
-
}
|
|
1587
|
-
}
|
|
1588
|
-
),
|
|
1589
|
-
/* @__PURE__ */ (0, import_jsx_runtime6.jsxs)("div", { children: [
|
|
1590
|
-
/* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { style: { fontSize: 13, fontWeight: 500, color: "#111827" }, children: "Connecting to PayPal\u2026" }),
|
|
1591
|
-
/* @__PURE__ */ (0, import_jsx_runtime6.jsx)("div", { style: { fontSize: 12, color: "#6b7280", marginTop: 2 }, children: "Setting up secure payment" })
|
|
1592
|
-
] })
|
|
1593
|
-
]
|
|
1594
|
-
}
|
|
1595
|
-
);
|
|
1596
|
-
}
|
|
1597
|
-
function ErrorCard({ message }) {
|
|
1598
|
-
return /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
|
|
1599
|
-
"div",
|
|
1600
|
-
{
|
|
1601
|
-
role: "alert",
|
|
1602
|
-
style: {
|
|
1603
|
-
padding: "12px 16px",
|
|
1604
|
-
background: "#fef2f2",
|
|
1605
|
-
border: "1px solid #fecaca",
|
|
1606
|
-
borderRadius: 10,
|
|
1607
|
-
fontSize: 13,
|
|
1608
|
-
color: "#b91c1c"
|
|
1609
|
-
},
|
|
1610
|
-
children: message
|
|
1611
|
-
}
|
|
1612
|
-
);
|
|
1613
|
-
}
|
|
1614
1647
|
function PayPalPaymentSection({
|
|
1615
1648
|
cartId,
|
|
1616
1649
|
selectedProviderId,
|
|
@@ -1621,67 +1654,24 @@ function PayPalPaymentSection({
|
|
|
1621
1654
|
onError,
|
|
1622
1655
|
onPaid
|
|
1623
1656
|
}) {
|
|
1624
|
-
|
|
1625
|
-
const { config, loading, error } = usePayPalConfig({
|
|
1626
|
-
baseUrl,
|
|
1627
|
-
publishableApiKey,
|
|
1628
|
-
cartId,
|
|
1629
|
-
enabled: shouldRender
|
|
1630
|
-
});
|
|
1631
|
-
const handlePaid = (0, import_react6.useCallback)(
|
|
1632
|
-
async (captureResult) => {
|
|
1633
|
-
onPaid?.(captureResult);
|
|
1634
|
-
await onSuccess?.(cartId);
|
|
1635
|
-
},
|
|
1636
|
-
[cartId, onPaid, onSuccess]
|
|
1637
|
-
);
|
|
1638
|
-
if (!shouldRender) return null;
|
|
1657
|
+
if (!isPayPalProviderId(selectedProviderId)) return null;
|
|
1639
1658
|
if (sessionLoading) return /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(SessionInitCard, {});
|
|
1640
|
-
|
|
1641
|
-
|
|
1642
|
-
|
|
1643
|
-
|
|
1644
|
-
|
|
1645
|
-
|
|
1646
|
-
|
|
1647
|
-
|
|
1648
|
-
|
|
1649
|
-
|
|
1650
|
-
|
|
1651
|
-
|
|
1652
|
-
PayPalProvider,
|
|
1653
|
-
{
|
|
1654
|
-
config,
|
|
1655
|
-
intent: config.intent === "authorize" ? "authorize" : "capture",
|
|
1656
|
-
disableFunding,
|
|
1657
|
-
children: isCardProvider ? /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
|
|
1658
|
-
PayPalAdvancedCard,
|
|
1659
|
-
{
|
|
1660
|
-
baseUrl,
|
|
1661
|
-
publishableApiKey,
|
|
1662
|
-
cartId,
|
|
1663
|
-
config,
|
|
1664
|
-
onPaid: handlePaid,
|
|
1665
|
-
onError
|
|
1666
|
-
}
|
|
1667
|
-
) : /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
|
|
1668
|
-
PayPalSmartButtons,
|
|
1669
|
-
{
|
|
1670
|
-
baseUrl,
|
|
1671
|
-
publishableApiKey,
|
|
1672
|
-
cartId,
|
|
1673
|
-
config,
|
|
1674
|
-
onPaid: handlePaid,
|
|
1675
|
-
onError
|
|
1676
|
-
}
|
|
1677
|
-
)
|
|
1678
|
-
}
|
|
1679
|
-
)
|
|
1680
|
-
] }, selectedProviderId);
|
|
1659
|
+
return /* @__PURE__ */ (0, import_jsx_runtime6.jsx)(
|
|
1660
|
+
MedusaNextPayPalAdapter,
|
|
1661
|
+
{
|
|
1662
|
+
cartId,
|
|
1663
|
+
selectedProviderId,
|
|
1664
|
+
baseUrl,
|
|
1665
|
+
publishableApiKey,
|
|
1666
|
+
onSuccess,
|
|
1667
|
+
onError,
|
|
1668
|
+
onPaid
|
|
1669
|
+
}
|
|
1670
|
+
);
|
|
1681
1671
|
}
|
|
1682
1672
|
|
|
1683
1673
|
// src/hooks/usePayPalPaymentMethods.ts
|
|
1684
|
-
var
|
|
1674
|
+
var import_react6 = require("react");
|
|
1685
1675
|
var MAX_CACHE_ENTRIES2 = 50;
|
|
1686
1676
|
var _cache2 = /* @__PURE__ */ new Map();
|
|
1687
1677
|
var CACHE_TTL2 = 5 * 60 * 1e3;
|
|
@@ -1700,7 +1690,8 @@ var DEFAULT_RESULT = {
|
|
|
1700
1690
|
paypalTitle: "PayPal",
|
|
1701
1691
|
cardEnabled: true,
|
|
1702
1692
|
cardTitle: "Credit or Debit Card",
|
|
1703
|
-
loading: false
|
|
1693
|
+
loading: false,
|
|
1694
|
+
error: null
|
|
1704
1695
|
};
|
|
1705
1696
|
function usePayPalPaymentMethods({
|
|
1706
1697
|
baseUrl,
|
|
@@ -1708,16 +1699,16 @@ function usePayPalPaymentMethods({
|
|
|
1708
1699
|
cartId,
|
|
1709
1700
|
enabled = true
|
|
1710
1701
|
}) {
|
|
1711
|
-
const api = (0,
|
|
1702
|
+
const api = (0, import_react6.useMemo)(
|
|
1712
1703
|
() => createPayPalStoreApi({ baseUrl, publishableApiKey }),
|
|
1713
1704
|
[baseUrl, publishableApiKey]
|
|
1714
1705
|
);
|
|
1715
1706
|
const key = cacheKey2(baseUrl, cartId);
|
|
1716
1707
|
const hit = _cache2.get(key);
|
|
1717
1708
|
const seed = hit && Date.now() - hit.at < CACHE_TTL2 ? hit.result : null;
|
|
1718
|
-
const [result, setResult] = (0,
|
|
1719
|
-
const fetchIdRef = (0,
|
|
1720
|
-
(0,
|
|
1709
|
+
const [result, setResult] = (0, import_react6.useState)(seed ?? { ...DEFAULT_RESULT, loading: enabled });
|
|
1710
|
+
const fetchIdRef = (0, import_react6.useRef)(0);
|
|
1711
|
+
(0, import_react6.useEffect)(() => {
|
|
1721
1712
|
if (!enabled) {
|
|
1722
1713
|
setResult((prev) => ({ ...prev, loading: false }));
|
|
1723
1714
|
return;
|
|
@@ -1741,7 +1732,8 @@ function usePayPalPaymentMethods({
|
|
|
1741
1732
|
paypalTitle: typeof cfg.paypal_title === "string" && cfg.paypal_title ? cfg.paypal_title : "PayPal",
|
|
1742
1733
|
cardEnabled: cfg.card_enabled !== false,
|
|
1743
1734
|
cardTitle: typeof cfg.card_title === "string" && cfg.card_title ? cfg.card_title : "Credit or Debit Card",
|
|
1744
|
-
loading: false
|
|
1735
|
+
loading: false,
|
|
1736
|
+
error: null
|
|
1745
1737
|
};
|
|
1746
1738
|
cacheSet2(k, { result: next, at: Date.now() });
|
|
1747
1739
|
setResult(next);
|
|
@@ -1754,12 +1746,17 @@ function usePayPalPaymentMethods({
|
|
|
1754
1746
|
...DEFAULT_RESULT,
|
|
1755
1747
|
paypalEnabled: false,
|
|
1756
1748
|
cardEnabled: false,
|
|
1757
|
-
loading: false
|
|
1749
|
+
loading: false,
|
|
1750
|
+
error: msg || "PayPal is disabled"
|
|
1758
1751
|
};
|
|
1759
1752
|
setResult(disabled);
|
|
1760
1753
|
return;
|
|
1761
1754
|
}
|
|
1762
|
-
setResult({
|
|
1755
|
+
setResult({
|
|
1756
|
+
...DEFAULT_RESULT,
|
|
1757
|
+
loading: false,
|
|
1758
|
+
error: msg || "Failed to load PayPal payment methods"
|
|
1759
|
+
});
|
|
1763
1760
|
}
|
|
1764
1761
|
})();
|
|
1765
1762
|
return () => {
|
|
@@ -1779,12 +1776,16 @@ function usePayPalPaymentMethods({
|
|
|
1779
1776
|
PayPalPaymentSection,
|
|
1780
1777
|
PayPalProvider,
|
|
1781
1778
|
PayPalSmartButtons,
|
|
1779
|
+
clearCartCaptured,
|
|
1782
1780
|
createPayPalStoreApi,
|
|
1781
|
+
generateIdempotencyKey,
|
|
1783
1782
|
hideProcessingOverlay,
|
|
1784
1783
|
isPayPalProviderId,
|
|
1784
|
+
markCartCaptured,
|
|
1785
1785
|
markPaymentComplete,
|
|
1786
1786
|
showProcessingOverlay,
|
|
1787
1787
|
usePayPalConfig,
|
|
1788
|
-
usePayPalPaymentMethods
|
|
1788
|
+
usePayPalPaymentMethods,
|
|
1789
|
+
wasCartCaptured
|
|
1789
1790
|
});
|
|
1790
1791
|
//# sourceMappingURL=index.cjs.map
|