@superlogic/spree-pay 0.4.12 → 0.5.1
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/README.md +82 -5
- package/build/{CryptoComTab-DAKL7IZF.js → CryptoComTab-ZAWBJUCM.js} +11 -12
- package/build/{CryptoTab-57MMM4AG.js → CryptoTab-632DRL2D.js} +13 -14
- package/build/{chunk-RORSHUSF.js → chunk-4BM6VTMT.js} +6 -7
- package/build/{chunk-JXZZJ7NS.js → chunk-AXNTOSBU.js} +1 -1
- package/build/{chunk-WRFG6YIS.js → chunk-PTEQVWLJ.js} +143 -48
- package/build/index.cjs +635 -507
- package/build/index.css +5 -0
- package/build/index.d.cts +50 -5
- package/build/index.d.ts +50 -5
- package/build/index.js +91 -56
- package/package.json +5 -2
package/build/index.css
CHANGED
package/build/index.d.cts
CHANGED
|
@@ -20,7 +20,9 @@ type SpreePayProps = Partial<{
|
|
|
20
20
|
|
|
21
21
|
declare const SpreePay: (props: SpreePayProps) => react_jsx_runtime.JSX.Element;
|
|
22
22
|
|
|
23
|
-
declare const useCapture3DS: (
|
|
23
|
+
declare const useCapture3DS: ({ paymentIntent }: {
|
|
24
|
+
paymentIntent?: string | null;
|
|
25
|
+
}) => void;
|
|
24
26
|
|
|
25
27
|
type Environment = 'dev' | 'stg' | 'prod';
|
|
26
28
|
type ENV = {
|
|
@@ -114,7 +116,7 @@ declare enum PaymentType {
|
|
|
114
116
|
CREDIT_CARD_SPLIT = "SPLIT",
|
|
115
117
|
POINTS = "POINTS"
|
|
116
118
|
}
|
|
117
|
-
declare enum
|
|
119
|
+
declare enum PaymentStatus {
|
|
118
120
|
NOT_INITIALIZED = "NOT_INITIALIZED",// back-end only
|
|
119
121
|
PENDING = "PENDING",// back-end only
|
|
120
122
|
AUTHORIZED = "AUTHORIZED",// success
|
|
@@ -124,7 +126,7 @@ declare enum SlapiPaymentStatus {
|
|
|
124
126
|
CAPTURE_FAILED = "CAPTURE_FAILED"
|
|
125
127
|
}
|
|
126
128
|
type PaymentMethodResult = {
|
|
127
|
-
status:
|
|
129
|
+
status: PaymentStatus;
|
|
128
130
|
paymentId: string;
|
|
129
131
|
txHash: string | null;
|
|
130
132
|
txId: string | null;
|
|
@@ -133,7 +135,6 @@ type PaymentMethodResult = {
|
|
|
133
135
|
type ProcessFnParams = {
|
|
134
136
|
hash: string;
|
|
135
137
|
capture?: boolean;
|
|
136
|
-
metadata?: Record<string, unknown>;
|
|
137
138
|
};
|
|
138
139
|
type ProcessFn = (data: ProcessFnParams) => Promise<PaymentMethodResult>;
|
|
139
140
|
|
|
@@ -160,6 +161,50 @@ declare global {
|
|
|
160
161
|
}
|
|
161
162
|
}
|
|
162
163
|
|
|
164
|
+
/**
|
|
165
|
+
* Thrown on a non-ok HTTP response. Keeps the status code and raw body on
|
|
166
|
+
* dedicated fields so callers can branch on 401/422/5xx without parsing the
|
|
167
|
+
* message string.
|
|
168
|
+
*/
|
|
169
|
+
declare class SpreePayHttpError extends Error {
|
|
170
|
+
status: number;
|
|
171
|
+
body: string;
|
|
172
|
+
url: string;
|
|
173
|
+
constructor(status: number, body: string, url: string);
|
|
174
|
+
}
|
|
175
|
+
/**
|
|
176
|
+
* Discriminates *why* a payment failed so consumers can show tailored UI
|
|
177
|
+
* (e.g. "your card was declined, try another" vs. a generic "try again").
|
|
178
|
+
*/
|
|
179
|
+
declare enum PaymentErrorCode {
|
|
180
|
+
/** The backend rejected the card (a 4xx decline, or a terminal FAILED status on a card payment). */
|
|
181
|
+
CARD_ERROR = "CARD_ERROR",
|
|
182
|
+
/** Anything else: network/server error, timeout, cancelled flow, crypto failure, … */
|
|
183
|
+
PAYMENT_ERROR = "PAYMENT_ERROR"
|
|
184
|
+
}
|
|
185
|
+
/**
|
|
186
|
+
* Wraps a payment failure with a category `code` and payment `status`; the original
|
|
187
|
+
* error is kept on `cause` (logs only). The widget throws this — detect it with
|
|
188
|
+
* `isPaymentError`. Not meant to be constructed by consumers.
|
|
189
|
+
*/
|
|
190
|
+
declare class PaymentError extends Error {
|
|
191
|
+
status: PaymentStatus;
|
|
192
|
+
code: PaymentErrorCode;
|
|
193
|
+
/**
|
|
194
|
+
* Optional stable code from the backend (e.g. `INSUFFICIENT_FUNDS`) for branching
|
|
195
|
+
* on specific cases without changing the `code` enum. Safe to expose (an
|
|
196
|
+
* identifier, not free-text); absent until the backend supplies one.
|
|
197
|
+
*/
|
|
198
|
+
backendCode?: string;
|
|
199
|
+
constructor(message: string, status: PaymentStatus, options?: {
|
|
200
|
+
code?: PaymentErrorCode;
|
|
201
|
+
backendCode?: string;
|
|
202
|
+
cause?: unknown;
|
|
203
|
+
});
|
|
204
|
+
}
|
|
205
|
+
/** Type guard so consumers can branch on PaymentError without duck-typing `.status`. */
|
|
206
|
+
declare const isPaymentError: (e: unknown) => e is PaymentError;
|
|
207
|
+
|
|
163
208
|
declare enum LogLevel {
|
|
164
209
|
DEBUG = 0,
|
|
165
210
|
INFO = 1,
|
|
@@ -234,4 +279,4 @@ declare const configureLogger: (config: Partial<LoggerConfig> & {
|
|
|
234
279
|
environment?: Environment;
|
|
235
280
|
}) => void;
|
|
236
281
|
|
|
237
|
-
export { type ENV, LogLevel, type PaymentMethodResult, PaymentType, type ProcessFn, type ProcessFnParams, type SelectedPaymentMethod,
|
|
282
|
+
export { type ENV, type Environment, type LogContext, LogLevel, type LoggerConfig, PaymentError, PaymentErrorCode, type PaymentMethodResult, PaymentStatus, PaymentType, type ProcessFn, type ProcessFnParams, type SelectedPaymentMethod, SpreePay, SpreePayHttpError, type SpreePayProps, SpreePayProvider, configureLogger, isPaymentError, logger, useCapture3DS, useSpreePay };
|
package/build/index.d.ts
CHANGED
|
@@ -20,7 +20,9 @@ type SpreePayProps = Partial<{
|
|
|
20
20
|
|
|
21
21
|
declare const SpreePay: (props: SpreePayProps) => react_jsx_runtime.JSX.Element;
|
|
22
22
|
|
|
23
|
-
declare const useCapture3DS: (
|
|
23
|
+
declare const useCapture3DS: ({ paymentIntent }: {
|
|
24
|
+
paymentIntent?: string | null;
|
|
25
|
+
}) => void;
|
|
24
26
|
|
|
25
27
|
type Environment = 'dev' | 'stg' | 'prod';
|
|
26
28
|
type ENV = {
|
|
@@ -114,7 +116,7 @@ declare enum PaymentType {
|
|
|
114
116
|
CREDIT_CARD_SPLIT = "SPLIT",
|
|
115
117
|
POINTS = "POINTS"
|
|
116
118
|
}
|
|
117
|
-
declare enum
|
|
119
|
+
declare enum PaymentStatus {
|
|
118
120
|
NOT_INITIALIZED = "NOT_INITIALIZED",// back-end only
|
|
119
121
|
PENDING = "PENDING",// back-end only
|
|
120
122
|
AUTHORIZED = "AUTHORIZED",// success
|
|
@@ -124,7 +126,7 @@ declare enum SlapiPaymentStatus {
|
|
|
124
126
|
CAPTURE_FAILED = "CAPTURE_FAILED"
|
|
125
127
|
}
|
|
126
128
|
type PaymentMethodResult = {
|
|
127
|
-
status:
|
|
129
|
+
status: PaymentStatus;
|
|
128
130
|
paymentId: string;
|
|
129
131
|
txHash: string | null;
|
|
130
132
|
txId: string | null;
|
|
@@ -133,7 +135,6 @@ type PaymentMethodResult = {
|
|
|
133
135
|
type ProcessFnParams = {
|
|
134
136
|
hash: string;
|
|
135
137
|
capture?: boolean;
|
|
136
|
-
metadata?: Record<string, unknown>;
|
|
137
138
|
};
|
|
138
139
|
type ProcessFn = (data: ProcessFnParams) => Promise<PaymentMethodResult>;
|
|
139
140
|
|
|
@@ -160,6 +161,50 @@ declare global {
|
|
|
160
161
|
}
|
|
161
162
|
}
|
|
162
163
|
|
|
164
|
+
/**
|
|
165
|
+
* Thrown on a non-ok HTTP response. Keeps the status code and raw body on
|
|
166
|
+
* dedicated fields so callers can branch on 401/422/5xx without parsing the
|
|
167
|
+
* message string.
|
|
168
|
+
*/
|
|
169
|
+
declare class SpreePayHttpError extends Error {
|
|
170
|
+
status: number;
|
|
171
|
+
body: string;
|
|
172
|
+
url: string;
|
|
173
|
+
constructor(status: number, body: string, url: string);
|
|
174
|
+
}
|
|
175
|
+
/**
|
|
176
|
+
* Discriminates *why* a payment failed so consumers can show tailored UI
|
|
177
|
+
* (e.g. "your card was declined, try another" vs. a generic "try again").
|
|
178
|
+
*/
|
|
179
|
+
declare enum PaymentErrorCode {
|
|
180
|
+
/** The backend rejected the card (a 4xx decline, or a terminal FAILED status on a card payment). */
|
|
181
|
+
CARD_ERROR = "CARD_ERROR",
|
|
182
|
+
/** Anything else: network/server error, timeout, cancelled flow, crypto failure, … */
|
|
183
|
+
PAYMENT_ERROR = "PAYMENT_ERROR"
|
|
184
|
+
}
|
|
185
|
+
/**
|
|
186
|
+
* Wraps a payment failure with a category `code` and payment `status`; the original
|
|
187
|
+
* error is kept on `cause` (logs only). The widget throws this — detect it with
|
|
188
|
+
* `isPaymentError`. Not meant to be constructed by consumers.
|
|
189
|
+
*/
|
|
190
|
+
declare class PaymentError extends Error {
|
|
191
|
+
status: PaymentStatus;
|
|
192
|
+
code: PaymentErrorCode;
|
|
193
|
+
/**
|
|
194
|
+
* Optional stable code from the backend (e.g. `INSUFFICIENT_FUNDS`) for branching
|
|
195
|
+
* on specific cases without changing the `code` enum. Safe to expose (an
|
|
196
|
+
* identifier, not free-text); absent until the backend supplies one.
|
|
197
|
+
*/
|
|
198
|
+
backendCode?: string;
|
|
199
|
+
constructor(message: string, status: PaymentStatus, options?: {
|
|
200
|
+
code?: PaymentErrorCode;
|
|
201
|
+
backendCode?: string;
|
|
202
|
+
cause?: unknown;
|
|
203
|
+
});
|
|
204
|
+
}
|
|
205
|
+
/** Type guard so consumers can branch on PaymentError without duck-typing `.status`. */
|
|
206
|
+
declare const isPaymentError: (e: unknown) => e is PaymentError;
|
|
207
|
+
|
|
163
208
|
declare enum LogLevel {
|
|
164
209
|
DEBUG = 0,
|
|
165
210
|
INFO = 1,
|
|
@@ -234,4 +279,4 @@ declare const configureLogger: (config: Partial<LoggerConfig> & {
|
|
|
234
279
|
environment?: Environment;
|
|
235
280
|
}) => void;
|
|
236
281
|
|
|
237
|
-
export { type ENV, LogLevel, type PaymentMethodResult, PaymentType, type ProcessFn, type ProcessFnParams, type SelectedPaymentMethod,
|
|
282
|
+
export { type ENV, type Environment, type LogContext, LogLevel, type LoggerConfig, PaymentError, PaymentErrorCode, type PaymentMethodResult, PaymentStatus, PaymentType, type ProcessFn, type ProcessFnParams, type SelectedPaymentMethod, SpreePay, SpreePayHttpError, type SpreePayProps, SpreePayProvider, configureLogger, isPaymentError, logger, useCapture3DS, useSpreePay };
|
package/build/index.js
CHANGED
|
@@ -8,39 +8,49 @@ import {
|
|
|
8
8
|
getSplitAmount,
|
|
9
9
|
getTransactionFee,
|
|
10
10
|
useSlapiBalance
|
|
11
|
-
} from "./chunk-
|
|
11
|
+
} from "./chunk-4BM6VTMT.js";
|
|
12
12
|
import {
|
|
13
13
|
Iframe3ds
|
|
14
|
-
} from "./chunk-
|
|
14
|
+
} from "./chunk-AXNTOSBU.js";
|
|
15
15
|
import {
|
|
16
16
|
InfoBanner,
|
|
17
17
|
LogLevel,
|
|
18
|
+
LoginStatusProvider,
|
|
18
19
|
PaymentError,
|
|
20
|
+
PaymentErrorCode,
|
|
21
|
+
PaymentStatus,
|
|
19
22
|
PaymentType,
|
|
20
23
|
PortalContainerProvider,
|
|
21
24
|
SlapiPaymentService,
|
|
25
|
+
SpreePayHttpError,
|
|
22
26
|
SpreePayProvider,
|
|
23
27
|
StaticConfigProvider,
|
|
24
28
|
cn,
|
|
25
29
|
configureLogger,
|
|
30
|
+
isDeclineStatus,
|
|
26
31
|
isNewCard,
|
|
32
|
+
isPaymentError,
|
|
33
|
+
isSuccessStatus,
|
|
27
34
|
logger,
|
|
28
35
|
registerApi,
|
|
36
|
+
settlePaymentResult,
|
|
37
|
+
toPaymentError,
|
|
38
|
+
useIsLoggedIn,
|
|
29
39
|
useSpreePay,
|
|
30
40
|
useSpreePayConfig,
|
|
31
41
|
useSpreePayEnv,
|
|
32
42
|
useSpreePayRegister,
|
|
33
43
|
useSpreePaymentMethod,
|
|
34
44
|
useStaticConfig
|
|
35
|
-
} from "./chunk-
|
|
45
|
+
} from "./chunk-PTEQVWLJ.js";
|
|
36
46
|
|
|
37
47
|
// src/SpreePay.tsx
|
|
38
|
-
import { useCallback as useCallback8, useEffect as
|
|
48
|
+
import { useCallback as useCallback8, useEffect as useEffect8, useMemo as useMemo9, useState as useState12 } from "react";
|
|
39
49
|
import NiceModal4 from "@ebay/nice-modal-react";
|
|
40
50
|
import { SWRConfig } from "swr";
|
|
41
51
|
|
|
42
52
|
// src/SpreePayContent.tsx
|
|
43
|
-
import { Suspense, lazy } from "react";
|
|
53
|
+
import { Suspense, lazy, useEffect as useEffect6 } from "react";
|
|
44
54
|
|
|
45
55
|
// src/components/CreditCardTab/CreditCardTab.tsx
|
|
46
56
|
import { useCallback as useCallback6, useEffect as useEffect5, useState as useState10 } from "react";
|
|
@@ -61,12 +71,8 @@ var useCardPayment = () => {
|
|
|
61
71
|
});
|
|
62
72
|
throw error;
|
|
63
73
|
}
|
|
64
|
-
const { hash, capture
|
|
65
|
-
cardPaymentLogger.info("Starting card payment", {
|
|
66
|
-
hash,
|
|
67
|
-
capture,
|
|
68
|
-
hasMetadata: Boolean(metadata)
|
|
69
|
-
});
|
|
74
|
+
const { hash, capture } = params;
|
|
75
|
+
cardPaymentLogger.info("Starting card payment", { hash, capture });
|
|
70
76
|
const card = selectedPaymentMethod.method;
|
|
71
77
|
let cardId;
|
|
72
78
|
if ("token" in card) {
|
|
@@ -97,7 +103,6 @@ var useCardPayment = () => {
|
|
|
97
103
|
const { data: paymentResData } = await SlapiPaymentService.createPayment({
|
|
98
104
|
hash,
|
|
99
105
|
capture,
|
|
100
|
-
metadata,
|
|
101
106
|
type: "CREDIT_CARD" /* CREDIT_CARD */,
|
|
102
107
|
card: {
|
|
103
108
|
cardId,
|
|
@@ -260,10 +265,13 @@ async function longPollPoints(paymentId) {
|
|
|
260
265
|
let retries = 0;
|
|
261
266
|
while (retries < MAX_RETRIES) {
|
|
262
267
|
const { detail } = await SlapiPaymentService.getStatus(paymentId);
|
|
263
|
-
if (detail.status
|
|
264
|
-
throw new
|
|
268
|
+
if (isDeclineStatus(detail.status)) {
|
|
269
|
+
throw new PaymentError("Something went wrong with the points payment.", detail.status, {
|
|
270
|
+
code: "PAYMENT_ERROR" /* PAYMENT_ERROR */,
|
|
271
|
+
backendCode: detail.errorCode ?? void 0
|
|
272
|
+
});
|
|
265
273
|
}
|
|
266
|
-
if (
|
|
274
|
+
if (isSuccessStatus(detail.status)) {
|
|
267
275
|
return detail.status;
|
|
268
276
|
}
|
|
269
277
|
await new Promise((res) => setTimeout(res, REFRESH_INTERVAL));
|
|
@@ -276,13 +284,21 @@ async function longPollCardStatus(paymentId) {
|
|
|
276
284
|
let shown3ds = false;
|
|
277
285
|
while (retries < MAX_RETRIES) {
|
|
278
286
|
const { detail } = await SlapiPaymentService.getStatus(paymentId);
|
|
279
|
-
if (detail.status
|
|
280
|
-
|
|
287
|
+
if (isDeclineStatus(detail.status)) {
|
|
288
|
+
const isPointsLeg = detail.validationType === "POINTS";
|
|
289
|
+
throw new PaymentError(
|
|
290
|
+
isPointsLeg ? "Something went wrong with the points payment." : "Your card payment could not be completed.",
|
|
291
|
+
detail.status,
|
|
292
|
+
{
|
|
293
|
+
code: isPointsLeg ? "PAYMENT_ERROR" /* PAYMENT_ERROR */ : "CARD_ERROR" /* CARD_ERROR */,
|
|
294
|
+
backendCode: detail.errorCode ?? void 0
|
|
295
|
+
}
|
|
296
|
+
);
|
|
281
297
|
}
|
|
282
298
|
if (
|
|
283
299
|
// Process to points payment
|
|
284
300
|
detail.validationType === "POINTS" || // early card payment completion
|
|
285
|
-
|
|
301
|
+
isSuccessStatus(detail.status)
|
|
286
302
|
) {
|
|
287
303
|
return detail.status;
|
|
288
304
|
}
|
|
@@ -312,7 +328,7 @@ var usePointsPayment = (mode = "web2") => {
|
|
|
312
328
|
});
|
|
313
329
|
throw error;
|
|
314
330
|
}
|
|
315
|
-
const { hash, capture
|
|
331
|
+
const { hash, capture } = params;
|
|
316
332
|
pointsPaymentLogger.info("Starting points payment", {
|
|
317
333
|
hash,
|
|
318
334
|
capture,
|
|
@@ -327,7 +343,6 @@ var usePointsPayment = (mode = "web2") => {
|
|
|
327
343
|
hash,
|
|
328
344
|
// capture should be always true for web2 points payments
|
|
329
345
|
capture: mode === "web2" ? true : capture,
|
|
330
|
-
metadata,
|
|
331
346
|
type: "POINTS" /* POINTS */
|
|
332
347
|
});
|
|
333
348
|
pointsPaymentLogger.info("Points payment created", {
|
|
@@ -420,7 +435,7 @@ var useSplitCardPayments = (mode = "web2") => {
|
|
|
420
435
|
if (selectedPaymentMethod.type !== "CREDIT_CARD" /* CREDIT_CARD */ || !selectedPaymentMethod.method || !params.points) {
|
|
421
436
|
throw new Error("Unsupported payment method");
|
|
422
437
|
}
|
|
423
|
-
const { hash, capture,
|
|
438
|
+
const { hash, capture, points } = params;
|
|
424
439
|
splitPaymentLogger.info("Starting split card+points payment", { hash, mode, points, capture });
|
|
425
440
|
const card = selectedPaymentMethod.method;
|
|
426
441
|
let cardId;
|
|
@@ -448,7 +463,6 @@ var useSplitCardPayments = (mode = "web2") => {
|
|
|
448
463
|
const { data: paymentResData } = await SlapiPaymentService.createPayment({
|
|
449
464
|
hash,
|
|
450
465
|
capture,
|
|
451
|
-
metadata,
|
|
452
466
|
type: "SPLIT" /* CREDIT_CARD_SPLIT */,
|
|
453
467
|
card: {
|
|
454
468
|
cardId,
|
|
@@ -871,6 +885,7 @@ var StripeWrapper = ({ onCancel, saveNewCard, publicKey }) => {
|
|
|
871
885
|
};
|
|
872
886
|
var CreditCard = ({ newCards, setNewCards }) => {
|
|
873
887
|
const [showForm, setShowForm] = useState3(false);
|
|
888
|
+
const isLoggedIn = useIsLoggedIn();
|
|
874
889
|
const { selectedPaymentMethod, setSelectedPaymentMethod } = useSpreePaymentMethod();
|
|
875
890
|
const { spreePayConfig } = useSpreePayConfig();
|
|
876
891
|
const setCard = (card) => {
|
|
@@ -892,6 +907,14 @@ var CreditCard = ({ newCards, setNewCards }) => {
|
|
|
892
907
|
},
|
|
893
908
|
[setNewCards]
|
|
894
909
|
);
|
|
910
|
+
const handleAddNewCard = () => {
|
|
911
|
+
setSelectedPaymentMethod({
|
|
912
|
+
...selectedPaymentMethod,
|
|
913
|
+
type: "CREDIT_CARD" /* CREDIT_CARD */,
|
|
914
|
+
method: null
|
|
915
|
+
});
|
|
916
|
+
setShowForm(true);
|
|
917
|
+
};
|
|
895
918
|
const handleCancel = () => {
|
|
896
919
|
setShowForm(false);
|
|
897
920
|
};
|
|
@@ -911,14 +934,14 @@ var CreditCard = ({ newCards, setNewCards }) => {
|
|
|
911
934
|
/* @__PURE__ */ jsx5(
|
|
912
935
|
"button",
|
|
913
936
|
{
|
|
914
|
-
onClick:
|
|
915
|
-
disabled: !spreePayConfig?.stripePublicKey,
|
|
937
|
+
onClick: handleAddNewCard,
|
|
938
|
+
disabled: !isLoggedIn || !spreePayConfig?.stripePublicKey,
|
|
916
939
|
className: "text-md text-(--brand-primary) hover:underline disabled:cursor-not-allowed disabled:no-underline disabled:opacity-50",
|
|
917
940
|
children: "Add new card"
|
|
918
941
|
}
|
|
919
942
|
)
|
|
920
943
|
] }),
|
|
921
|
-
spreePayConfig?.stripePublicKey && showForm && /* @__PURE__ */ jsx5(StripeWrapper, { onCancel: handleCancel, saveNewCard, publicKey: spreePayConfig.stripePublicKey })
|
|
944
|
+
isLoggedIn && spreePayConfig?.stripePublicKey && showForm && /* @__PURE__ */ jsx5(StripeWrapper, { onCancel: handleCancel, saveNewCard, publicKey: spreePayConfig.stripePublicKey })
|
|
922
945
|
] });
|
|
923
946
|
};
|
|
924
947
|
|
|
@@ -2081,6 +2104,7 @@ var SplitBlock = (props) => {
|
|
|
2081
2104
|
// src/components/CreditCardTab/Points/Points.tsx
|
|
2082
2105
|
import { Fragment as Fragment3, jsx as jsx15, jsxs as jsxs8 } from "react/jsx-runtime";
|
|
2083
2106
|
var Points = () => {
|
|
2107
|
+
const isLoggedIn = useIsLoggedIn();
|
|
2084
2108
|
const [usePoints, setUsePoints] = useState9(false);
|
|
2085
2109
|
const [selectedPointsType, setSelectedPointsType] = useState9(null);
|
|
2086
2110
|
const { setSelectedPaymentMethod, selectedPaymentMethod } = useSpreePaymentMethod();
|
|
@@ -2100,7 +2124,7 @@ var Points = () => {
|
|
|
2100
2124
|
value: usePoints,
|
|
2101
2125
|
onChange: handleTogglePoints,
|
|
2102
2126
|
message: spreePayConfig?.creditCard.pointsInfoMessage,
|
|
2103
|
-
disabled: !spreePayConfig?.creditCard.enabled || !spreePayConfig?.creditCard.points || appProps.disabledPoints
|
|
2127
|
+
disabled: !isLoggedIn || !spreePayConfig?.creditCard.enabled || !spreePayConfig?.creditCard.points || appProps.disabledPoints
|
|
2104
2128
|
}
|
|
2105
2129
|
),
|
|
2106
2130
|
usePoints && /* @__PURE__ */ jsx15(
|
|
@@ -2116,7 +2140,7 @@ var Points = () => {
|
|
|
2116
2140
|
|
|
2117
2141
|
// src/components/CreditCardTab/CreditCardTab.tsx
|
|
2118
2142
|
import { jsx as jsx16, jsxs as jsxs9 } from "react/jsx-runtime";
|
|
2119
|
-
var CreditCardTab = (
|
|
2143
|
+
var CreditCardTab = () => {
|
|
2120
2144
|
const { selectedPaymentMethod, setSelectedPaymentMethod } = useSpreePaymentMethod();
|
|
2121
2145
|
const { useWeb3Points } = useSpreePayEnv();
|
|
2122
2146
|
const { appProps } = useStaticConfig();
|
|
@@ -2131,23 +2155,23 @@ var CreditCardTab = ({ isLoggedIn }) => {
|
|
|
2131
2155
|
const { pointsPayment } = usePointsPayment(isWeb3Enabled ? "web3" : "web2");
|
|
2132
2156
|
const handlePay = useCallback6(
|
|
2133
2157
|
async (data) => {
|
|
2158
|
+
const pointsAmount = selectedPaymentMethod.pointsAmount ?? 0;
|
|
2159
|
+
const usdAmount = getSplitAmount(appProps.amount ?? 0, pointsAmount, spreePayConfig?.pointsConversionRatio);
|
|
2160
|
+
const isPurePoints = !usdAmount && pointsAmount > 0;
|
|
2161
|
+
const failureMessage = isPurePoints ? "Points payment failed" : "Card payment failed";
|
|
2162
|
+
const failureCode = isPurePoints ? "PAYMENT_ERROR" /* PAYMENT_ERROR */ : "CARD_ERROR" /* CARD_ERROR */;
|
|
2134
2163
|
try {
|
|
2135
|
-
let res
|
|
2136
|
-
const pointsAmount = selectedPaymentMethod.pointsAmount ?? 0;
|
|
2137
|
-
const usdAmount = getSplitAmount(appProps.amount ?? 0, pointsAmount, spreePayConfig?.pointsConversionRatio);
|
|
2164
|
+
let res;
|
|
2138
2165
|
if (usdAmount && pointsAmount) {
|
|
2139
2166
|
res = await splitPayment({ ...data, points: pointsAmount });
|
|
2140
|
-
} else if (
|
|
2167
|
+
} else if (isPurePoints) {
|
|
2141
2168
|
res = await pointsPayment({ ...data, points: pointsAmount });
|
|
2142
2169
|
} else {
|
|
2143
2170
|
res = await cardPayment(data);
|
|
2144
2171
|
}
|
|
2145
|
-
|
|
2146
|
-
|
|
2147
|
-
|
|
2148
|
-
return Promise.reject(new PaymentError("Card payment failed", res.status));
|
|
2149
|
-
} catch (_) {
|
|
2150
|
-
return Promise.reject(new PaymentError("Payment failed", "FAILED" /* FAILED */));
|
|
2172
|
+
return settlePaymentResult(res, failureMessage, failureCode);
|
|
2173
|
+
} catch (e) {
|
|
2174
|
+
return Promise.reject(toPaymentError(e, failureMessage, failureCode));
|
|
2151
2175
|
} finally {
|
|
2152
2176
|
mutateBalance();
|
|
2153
2177
|
if (selectedPaymentMethod.type === "CREDIT_CARD" /* CREDIT_CARD */ && selectedPaymentMethod.method && isNewCard(selectedPaymentMethod.method)) {
|
|
@@ -2184,7 +2208,7 @@ var CreditCardTab = ({ isLoggedIn }) => {
|
|
|
2184
2208
|
return /* @__PURE__ */ jsxs9("div", { children: [
|
|
2185
2209
|
/* @__PURE__ */ jsx16("div", { className: "border-b border-b-(--border-component-specific-card) px-5 py-5 md:px-7 md:py-6", children: /* @__PURE__ */ jsx16(CreditCard, { newCards, setNewCards }) }),
|
|
2186
2210
|
!spreePayConfig?.creditCard.hidePoints && /* @__PURE__ */ jsx16("div", { className: "flex flex-col gap-4 border-b border-b-(--border-component-specific-card) px-5 pt-5 pb-5 md:px-7 md:pt-6 md:pb-7", children: /* @__PURE__ */ jsx16(Points, {}) }),
|
|
2187
|
-
/* @__PURE__ */ jsx16(CheckoutButton, {
|
|
2211
|
+
/* @__PURE__ */ jsx16(CheckoutButton, {})
|
|
2188
2212
|
] });
|
|
2189
2213
|
};
|
|
2190
2214
|
|
|
@@ -2260,24 +2284,30 @@ var TabButtons = (props) => {
|
|
|
2260
2284
|
|
|
2261
2285
|
// src/SpreePayContent.tsx
|
|
2262
2286
|
import { jsx as jsx18, jsxs as jsxs11 } from "react/jsx-runtime";
|
|
2263
|
-
var CryptoTab = lazy(() => import("./CryptoTab-
|
|
2287
|
+
var CryptoTab = lazy(() => import("./CryptoTab-632DRL2D.js").then((module) => ({ default: module.CryptoTab })));
|
|
2264
2288
|
var CryptoComTab = lazy(
|
|
2265
|
-
() => import("./CryptoComTab-
|
|
2289
|
+
() => import("./CryptoComTab-ZAWBJUCM.js").then((module) => ({ default: module.CryptoComTab }))
|
|
2266
2290
|
);
|
|
2267
2291
|
var TabLoadingFallback = () => /* @__PURE__ */ jsx18("div", { className: "flex items-center justify-center px-5 py-8 md:px-7", children: /* @__PURE__ */ jsxs11("div", { className: "flex flex-col items-center gap-3", children: [
|
|
2268
2292
|
/* @__PURE__ */ jsx18("div", { className: "h-8 w-8 animate-spin rounded-full border-4 border-(--border-component-specific-card) border-t-(--brand-primary)" }),
|
|
2269
2293
|
/* @__PURE__ */ jsx18("p", { className: "text-sm text-(--text-tertiary)", children: "Loading payment method..." })
|
|
2270
2294
|
] }) });
|
|
2271
|
-
var SpreePayContent = (
|
|
2295
|
+
var SpreePayContent = () => {
|
|
2296
|
+
const isLoggedIn = useIsLoggedIn();
|
|
2272
2297
|
const { selectedPaymentMethod, setSelectedPaymentMethod } = useSpreePaymentMethod();
|
|
2298
|
+
useEffect6(() => {
|
|
2299
|
+
if (!isLoggedIn) {
|
|
2300
|
+
setSelectedPaymentMethod({ type: "CREDIT_CARD" /* CREDIT_CARD */, method: null });
|
|
2301
|
+
}
|
|
2302
|
+
}, [isLoggedIn, setSelectedPaymentMethod]);
|
|
2273
2303
|
return /* @__PURE__ */ jsxs11("div", { className: "w-full overflow-hidden rounded-3xl border border-(--border-component-specific-card) bg-(--surface-component-specific-card-default-card) shadow-[0_6.25px_25px_0_var(--shadow-component-specific-card)]", children: [
|
|
2274
2304
|
/* @__PURE__ */ jsxs11("div", { className: "flex w-full flex-col gap-2 border-b border-b-(--border-component-specific-card) pt-5 pb-3 md:pt-6 md:pb-5", children: [
|
|
2275
2305
|
/* @__PURE__ */ jsx18("h2", { className: "px-5 text-[28px] leading-8 font-medium text-(--brand-primary) md:px-7", children: "Choose a payment method" }),
|
|
2276
2306
|
/* @__PURE__ */ jsx18(TabButtons, { value: selectedPaymentMethod.type, onChange: setSelectedPaymentMethod })
|
|
2277
2307
|
] }),
|
|
2278
|
-
selectedPaymentMethod.type === "CREDIT_CARD" /* CREDIT_CARD */ && /* @__PURE__ */ jsx18(CreditCardTab, {
|
|
2308
|
+
selectedPaymentMethod.type === "CREDIT_CARD" /* CREDIT_CARD */ && /* @__PURE__ */ jsx18(CreditCardTab, {}),
|
|
2279
2309
|
/* @__PURE__ */ jsxs11(Suspense, { fallback: /* @__PURE__ */ jsx18(TabLoadingFallback, {}), children: [
|
|
2280
|
-
selectedPaymentMethod.type === "CRYPTO" /* CRYPTO */ && /* @__PURE__ */ jsx18(CryptoTab, {
|
|
2310
|
+
selectedPaymentMethod.type === "CRYPTO" /* CRYPTO */ && /* @__PURE__ */ jsx18(CryptoTab, {}),
|
|
2281
2311
|
selectedPaymentMethod.type === "CDC" /* CDC */ && /* @__PURE__ */ jsx18(CryptoComTab, {})
|
|
2282
2312
|
] })
|
|
2283
2313
|
] });
|
|
@@ -2332,7 +2362,7 @@ var ErrorBoundary = class extends Component {
|
|
|
2332
2362
|
};
|
|
2333
2363
|
|
|
2334
2364
|
// src/hooks/useKeycloakSSO.ts
|
|
2335
|
-
import { useCallback as useCallback7, useEffect as
|
|
2365
|
+
import { useCallback as useCallback7, useEffect as useEffect7, useRef as useRef6, useState as useState11 } from "react";
|
|
2336
2366
|
import Keycloak from "keycloak-js";
|
|
2337
2367
|
var refreshAheadSeconds = 60;
|
|
2338
2368
|
var keycloakLogger = logger.child("keycloak");
|
|
@@ -2370,10 +2400,10 @@ function useKeycloakSSO(config) {
|
|
|
2370
2400
|
});
|
|
2371
2401
|
}, delayMs);
|
|
2372
2402
|
}, []);
|
|
2373
|
-
|
|
2403
|
+
useEffect7(() => {
|
|
2374
2404
|
scheduleRefreshRef.current = scheduleRefresh;
|
|
2375
2405
|
}, [scheduleRefresh]);
|
|
2376
|
-
|
|
2406
|
+
useEffect7(() => {
|
|
2377
2407
|
if (initRef.current || !enabled) return;
|
|
2378
2408
|
initRef.current = true;
|
|
2379
2409
|
const kc = new Keycloak({ url, realm, clientId });
|
|
@@ -2419,6 +2449,7 @@ var isTokenExpired = (token) => {
|
|
|
2419
2449
|
|
|
2420
2450
|
// src/SpreePay.tsx
|
|
2421
2451
|
import { jsx as jsx20, jsxs as jsxs13 } from "react/jsx-runtime";
|
|
2452
|
+
var unauthenticatedFetcher = () => Promise.resolve(null);
|
|
2422
2453
|
var SpreePayInner = () => {
|
|
2423
2454
|
const [portalEl, setPortalEl] = useState12(null);
|
|
2424
2455
|
const rootRef = useCallback8((node) => {
|
|
@@ -2427,7 +2458,7 @@ var SpreePayInner = () => {
|
|
|
2427
2458
|
setPortalEl(el ?? null);
|
|
2428
2459
|
}, []);
|
|
2429
2460
|
const { environment, tenantId, keycloakClientId, accessToken: envAccessToken, ssoPageURI } = useSpreePayEnv();
|
|
2430
|
-
|
|
2461
|
+
useEffect8(() => {
|
|
2431
2462
|
configureLogger({ environment });
|
|
2432
2463
|
logger.logVersion();
|
|
2433
2464
|
}, [environment]);
|
|
@@ -2441,7 +2472,6 @@ var SpreePayInner = () => {
|
|
|
2441
2472
|
enabled: !envTokenValid
|
|
2442
2473
|
});
|
|
2443
2474
|
const _accessToken = envTokenValid ? envAccessToken : accessToken;
|
|
2444
|
-
const unauthenticatedFetcher = useCallback8(() => Promise.resolve(null), []);
|
|
2445
2475
|
const slapiFetcher = useMemo9(() => {
|
|
2446
2476
|
if (_accessToken) {
|
|
2447
2477
|
return registerApi({
|
|
@@ -2451,7 +2481,7 @@ var SpreePayInner = () => {
|
|
|
2451
2481
|
});
|
|
2452
2482
|
}
|
|
2453
2483
|
return unauthenticatedFetcher;
|
|
2454
|
-
}, [_accessToken, staticConfig, tenantId
|
|
2484
|
+
}, [_accessToken, staticConfig, tenantId]);
|
|
2455
2485
|
const getContent = () => {
|
|
2456
2486
|
if (isChecking) {
|
|
2457
2487
|
return /* @__PURE__ */ jsxs13("div", { className: "flex w-full flex-col", children: [
|
|
@@ -2468,7 +2498,7 @@ var SpreePayInner = () => {
|
|
|
2468
2498
|
revalidateOnFocus: false,
|
|
2469
2499
|
revalidateIfStale: false
|
|
2470
2500
|
},
|
|
2471
|
-
children: /* @__PURE__ */ jsx20(PortalContainerProvider, { container: portalEl, children: /* @__PURE__ */ jsx20(NiceModal4.Provider, { children: /* @__PURE__ */ jsx20(
|
|
2501
|
+
children: /* @__PURE__ */ jsx20(PortalContainerProvider, { container: portalEl, children: /* @__PURE__ */ jsx20(NiceModal4.Provider, { children: /* @__PURE__ */ jsx20(LoginStatusProvider, { isLoggedIn: Boolean(_accessToken), children: /* @__PURE__ */ jsx20(SpreePayContent, {}) }) }) })
|
|
2472
2502
|
}
|
|
2473
2503
|
);
|
|
2474
2504
|
};
|
|
@@ -2482,20 +2512,25 @@ var SpreePay = (props) => {
|
|
|
2482
2512
|
};
|
|
2483
2513
|
|
|
2484
2514
|
// src/hooks/useCapture3DS.ts
|
|
2485
|
-
import { useEffect as
|
|
2486
|
-
var useCapture3DS = (
|
|
2487
|
-
|
|
2488
|
-
if (typeof window !== "undefined" && window.parent &&
|
|
2489
|
-
window.parent.SP_EVENT_BUS?.emit("paymentIntent", { paymentIntent
|
|
2515
|
+
import { useEffect as useEffect9 } from "react";
|
|
2516
|
+
var useCapture3DS = ({ paymentIntent }) => {
|
|
2517
|
+
useEffect9(() => {
|
|
2518
|
+
if (typeof window !== "undefined" && window.parent && paymentIntent) {
|
|
2519
|
+
window.parent.SP_EVENT_BUS?.emit("paymentIntent", { paymentIntent });
|
|
2490
2520
|
}
|
|
2491
|
-
}, [
|
|
2521
|
+
}, [paymentIntent]);
|
|
2492
2522
|
};
|
|
2493
2523
|
export {
|
|
2494
2524
|
LogLevel,
|
|
2525
|
+
PaymentError,
|
|
2526
|
+
PaymentErrorCode,
|
|
2527
|
+
PaymentStatus,
|
|
2495
2528
|
PaymentType,
|
|
2496
2529
|
SpreePay,
|
|
2530
|
+
SpreePayHttpError,
|
|
2497
2531
|
SpreePayProvider,
|
|
2498
2532
|
configureLogger,
|
|
2533
|
+
isPaymentError,
|
|
2499
2534
|
logger,
|
|
2500
2535
|
useCapture3DS,
|
|
2501
2536
|
useSpreePay
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@superlogic/spree-pay",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.5.1",
|
|
4
4
|
"description": "Spree-pay React component and utilities",
|
|
5
5
|
"private": false,
|
|
6
6
|
"type": "module",
|
|
@@ -30,6 +30,8 @@
|
|
|
30
30
|
"dev": "tsup --watch",
|
|
31
31
|
"lint": "eslint . --max-warnings 0",
|
|
32
32
|
"check-ts": "tsc --noEmit",
|
|
33
|
+
"test": "vitest run",
|
|
34
|
+
"test:watch": "vitest",
|
|
33
35
|
"publish": "npm run build"
|
|
34
36
|
},
|
|
35
37
|
"publishConfig": {
|
|
@@ -71,7 +73,8 @@
|
|
|
71
73
|
"tailwindcss": "^4.3.0",
|
|
72
74
|
"tsup": "^8.5.1",
|
|
73
75
|
"tw-animate-css": "^1.4.0",
|
|
74
|
-
"typescript": "^6.0.3"
|
|
76
|
+
"typescript": "^6.0.3",
|
|
77
|
+
"vitest": "^4.1.6"
|
|
75
78
|
},
|
|
76
79
|
"tsup": {
|
|
77
80
|
"entry": [
|