@blocklet/payment-react 1.18.28 → 1.18.30
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/es/components/over-due-invoice-payment.js +15 -16
- package/es/history/invoice/list.js +3 -1
- package/es/libs/util.d.ts +1 -0
- package/es/libs/util.js +10 -0
- package/es/payment/form/index.js +4 -2
- package/es/payment/product-donation.js +4 -3
- package/lib/components/over-due-invoice-payment.js +15 -15
- package/lib/history/invoice/list.js +1 -0
- package/lib/libs/util.d.ts +1 -0
- package/lib/libs/util.js +11 -0
- package/lib/payment/form/index.js +2 -1
- package/lib/payment/product-donation.js +4 -3
- package/package.json +8 -8
- package/src/components/over-due-invoice-payment.tsx +24 -18
- package/src/history/invoice/list.tsx +2 -0
- package/src/libs/util.ts +11 -0
- package/src/payment/form/index.tsx +3 -1
- package/src/payment/product-donation.tsx +4 -3
|
@@ -9,7 +9,7 @@ import { Dialog } from "@arcblock/ux";
|
|
|
9
9
|
import { CheckCircle as CheckCircleIcon } from "@mui/icons-material";
|
|
10
10
|
import debounce from "lodash/debounce";
|
|
11
11
|
import { usePaymentContext } from "../contexts/payment.js";
|
|
12
|
-
import { formatAmount, formatError, getPrefix } from "../libs/util.js";
|
|
12
|
+
import { formatAmount, formatError, getPrefix, isCrossOrigin } from "../libs/util.js";
|
|
13
13
|
import { useSubscription } from "../hooks/subscription.js";
|
|
14
14
|
import api from "../libs/api.js";
|
|
15
15
|
import LoadingButton from "./loading-button.js";
|
|
@@ -40,14 +40,15 @@ function OverdueInvoicePayment({
|
|
|
40
40
|
authToken
|
|
41
41
|
}) {
|
|
42
42
|
const { t } = useLocaleContext();
|
|
43
|
-
const { connect } = usePaymentContext();
|
|
43
|
+
const { connect, session } = usePaymentContext();
|
|
44
44
|
const [selectCurrencyId, setSelectCurrencyId] = useState("");
|
|
45
45
|
const [payLoading, setPayLoading] = useState(false);
|
|
46
46
|
const [dialogOpen, setDialogOpen] = useState(dialogProps.open || false);
|
|
47
47
|
const [processedCurrencies, setProcessedCurrencies] = useState({});
|
|
48
48
|
const [paymentStatus, setPaymentStatus] = useState({});
|
|
49
49
|
const sourceType = subscriptionId ? "subscription" : "customer";
|
|
50
|
-
const
|
|
50
|
+
const effectiveCustomerId = customerId || session?.user?.did;
|
|
51
|
+
const sourceId = subscriptionId || effectiveCustomerId;
|
|
51
52
|
const {
|
|
52
53
|
data = {
|
|
53
54
|
summary: {},
|
|
@@ -56,18 +57,18 @@ function OverdueInvoicePayment({
|
|
|
56
57
|
error,
|
|
57
58
|
loading,
|
|
58
59
|
runAsync: refresh
|
|
59
|
-
} = useRequest(() => fetchOverdueInvoices({ subscriptionId, customerId, authToken }), {
|
|
60
|
-
ready: !!subscriptionId || !!
|
|
60
|
+
} = useRequest(() => fetchOverdueInvoices({ subscriptionId, customerId: effectiveCustomerId, authToken }), {
|
|
61
|
+
ready: !!subscriptionId || !!effectiveCustomerId
|
|
61
62
|
});
|
|
62
63
|
const detailUrl = useMemo(() => {
|
|
63
64
|
if (subscriptionId) {
|
|
64
65
|
return joinURL(getPrefix(), `/customer/subscription/${subscriptionId}`);
|
|
65
66
|
}
|
|
66
|
-
if (
|
|
67
|
+
if (effectiveCustomerId) {
|
|
67
68
|
return joinURL(getPrefix(), "/customer/invoice/past-due");
|
|
68
69
|
}
|
|
69
70
|
return "";
|
|
70
|
-
}, [subscriptionId,
|
|
71
|
+
}, [subscriptionId, effectiveCustomerId]);
|
|
71
72
|
const summaryList = useMemo(() => {
|
|
72
73
|
if (!data?.summary) {
|
|
73
74
|
return [];
|
|
@@ -100,7 +101,7 @@ function OverdueInvoicePayment({
|
|
|
100
101
|
subscription.on("invoice.paid", ({ response }) => {
|
|
101
102
|
const relevantId = subscriptionId || response.customer_id;
|
|
102
103
|
const uniqueKey = `${relevantId}-${response.currency_id}`;
|
|
103
|
-
if (subscriptionId && response.subscription_id === subscriptionId ||
|
|
104
|
+
if (subscriptionId && response.subscription_id === subscriptionId || effectiveCustomerId && [data.customer?.id, effectiveCustomerId].includes(response.customer_id)) {
|
|
104
105
|
if (!processedCurrencies[uniqueKey]) {
|
|
105
106
|
setProcessedCurrencies((prev) => ({ ...prev, [uniqueKey]: 1 }));
|
|
106
107
|
debouncedHandleInvoicePaid(response.currency_id);
|
|
@@ -108,7 +109,7 @@ function OverdueInvoicePayment({
|
|
|
108
109
|
}
|
|
109
110
|
});
|
|
110
111
|
}
|
|
111
|
-
}, [subscription, subscriptionId,
|
|
112
|
+
}, [subscription, subscriptionId, effectiveCustomerId]);
|
|
112
113
|
const handlePay = (item) => {
|
|
113
114
|
const { currency, method } = item;
|
|
114
115
|
if (method.type === "stripe") {
|
|
@@ -128,14 +129,15 @@ function OverdueInvoicePayment({
|
|
|
128
129
|
const extraParams = { currencyId: currency.id };
|
|
129
130
|
if (subscriptionId) {
|
|
130
131
|
extraParams.subscriptionId = subscriptionId;
|
|
131
|
-
} else if (
|
|
132
|
-
extraParams.customerId =
|
|
132
|
+
} else if (effectiveCustomerId) {
|
|
133
|
+
extraParams.customerId = effectiveCustomerId;
|
|
133
134
|
}
|
|
134
135
|
connect.open({
|
|
135
136
|
containerEl: void 0,
|
|
136
137
|
saveConnect: false,
|
|
137
138
|
action: "collect-batch",
|
|
138
139
|
prefix: joinURL(getPrefix(), "/api/did"),
|
|
140
|
+
useSocket: isCrossOrigin() === false,
|
|
139
141
|
extraParams,
|
|
140
142
|
onSuccess: () => {
|
|
141
143
|
connect.close();
|
|
@@ -246,7 +248,7 @@ function OverdueInvoicePayment({
|
|
|
246
248
|
count: data.invoices?.length
|
|
247
249
|
});
|
|
248
250
|
}
|
|
249
|
-
if (
|
|
251
|
+
if (effectiveCustomerId) {
|
|
250
252
|
let title = "";
|
|
251
253
|
if (summaryList.length === 1) {
|
|
252
254
|
title = t("payment.customer.overdue.title", {
|
|
@@ -275,10 +277,7 @@ function OverdueInvoicePayment({
|
|
|
275
277
|
name: data.subscription?.description
|
|
276
278
|
});
|
|
277
279
|
}
|
|
278
|
-
|
|
279
|
-
return t("payment.customer.overdue.empty");
|
|
280
|
-
}
|
|
281
|
-
return "";
|
|
280
|
+
return t("payment.customer.overdue.empty");
|
|
282
281
|
};
|
|
283
282
|
if (mode === "custom" && children && typeof children === "function") {
|
|
284
283
|
return /* @__PURE__ */ jsx(Stack, { children: children(handlePay, {
|
|
@@ -19,7 +19,8 @@ import {
|
|
|
19
19
|
formatToDatetime,
|
|
20
20
|
getInvoiceDescriptionAndReason,
|
|
21
21
|
getInvoiceStatusColor,
|
|
22
|
-
getTxLink
|
|
22
|
+
getTxLink,
|
|
23
|
+
isCrossOrigin
|
|
23
24
|
} from "../../libs/util.js";
|
|
24
25
|
import Table from "../../components/table.js";
|
|
25
26
|
import { createLink, handleNavigation } from "../../libs/navigation.js";
|
|
@@ -479,6 +480,7 @@ export default function CustomerInvoiceList(props) {
|
|
|
479
480
|
connect.open({
|
|
480
481
|
action: "collect",
|
|
481
482
|
saveConnect: false,
|
|
483
|
+
useSocket: isCrossOrigin() === false,
|
|
482
484
|
messages: {
|
|
483
485
|
scan: "",
|
|
484
486
|
title: t(`payment.customer.invoice.${action || "pay"}`),
|
package/es/libs/util.d.ts
CHANGED
|
@@ -3,6 +3,7 @@ import type { ActionProps, PricingRenderProps } from '../types';
|
|
|
3
3
|
export declare const PAYMENT_KIT_DID = "z2qaCNvKMv5GjouKdcDWexv6WqtHbpNPQDnAk";
|
|
4
4
|
export declare const isPaymentKitMounted: () => any;
|
|
5
5
|
export declare const getPrefix: () => string;
|
|
6
|
+
export declare function isCrossOrigin(): boolean;
|
|
6
7
|
export declare function formatToDate(date: Date | string | number, locale?: string, format?: string): any;
|
|
7
8
|
export declare function formatToDatetime(date: Date | string | number, locale?: string): any;
|
|
8
9
|
export declare function formatTime(date: Date | string | number, format?: string, locale?: string): any;
|
package/es/libs/util.js
CHANGED
|
@@ -36,6 +36,16 @@ export const getPrefix = () => {
|
|
|
36
36
|
}
|
|
37
37
|
return joinURL(baseUrl, prefix);
|
|
38
38
|
};
|
|
39
|
+
export function isCrossOrigin() {
|
|
40
|
+
try {
|
|
41
|
+
const prefix = getPrefix();
|
|
42
|
+
const prefixOrigin = new URL(prefix).origin;
|
|
43
|
+
const currentOrigin = window.location.origin;
|
|
44
|
+
return prefixOrigin !== currentOrigin;
|
|
45
|
+
} catch (error) {
|
|
46
|
+
return false;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
39
49
|
export function formatToDate(date, locale = "en", format = "YYYY-MM-DD HH:mm:ss") {
|
|
40
50
|
if (!date) {
|
|
41
51
|
return "-";
|
package/es/payment/form/index.js
CHANGED
|
@@ -21,7 +21,8 @@ import {
|
|
|
21
21
|
formatQuantityInventory,
|
|
22
22
|
getPrefix,
|
|
23
23
|
getQueryParams,
|
|
24
|
-
getStatementDescriptor
|
|
24
|
+
getStatementDescriptor,
|
|
25
|
+
isCrossOrigin
|
|
25
26
|
} from "../../libs/util.js";
|
|
26
27
|
import AddressForm from "./address.js";
|
|
27
28
|
import CurrencySelector from "./currency.js";
|
|
@@ -311,6 +312,7 @@ export default function PaymentForm({
|
|
|
311
312
|
action: checkoutSession.mode,
|
|
312
313
|
prefix: joinURL(getPrefix(), "/api/did"),
|
|
313
314
|
saveConnect: false,
|
|
315
|
+
useSocket: isCrossOrigin() === false,
|
|
314
316
|
extraParams: { checkoutSessionId: checkoutSession.id, sessionUserDid: session?.user?.did },
|
|
315
317
|
onSuccess: async () => {
|
|
316
318
|
connect.close();
|
|
@@ -602,7 +604,7 @@ export default function PaymentForm({
|
|
|
602
604
|
state.customerLimited && /* @__PURE__ */ jsx(
|
|
603
605
|
OverdueInvoicePayment,
|
|
604
606
|
{
|
|
605
|
-
customerId: customer?.id || session?.user?.
|
|
607
|
+
customerId: customer?.id || session?.user?.did,
|
|
606
608
|
onPaid: () => {
|
|
607
609
|
setState({ customerLimited: false });
|
|
608
610
|
onAction();
|
|
@@ -85,9 +85,10 @@ export default function ProductDonation({
|
|
|
85
85
|
if (hasPresets) {
|
|
86
86
|
sortedPresets = [...presets].map((p) => parseFloat(p)).sort((a, b) => a - b);
|
|
87
87
|
}
|
|
88
|
-
const minPreset = hasPresets ? sortedPresets[
|
|
89
|
-
|
|
90
|
-
const
|
|
88
|
+
const minPreset = hasPresets ? sortedPresets[sortedPresets.length - 1] : 1;
|
|
89
|
+
let maxPreset = hasPresets ? sortedPresets[sortedPresets.length - 1] * 5 : 100;
|
|
90
|
+
const systemMax = settings.amount.maximum ? parseFloat(settings.amount.maximum) : Infinity;
|
|
91
|
+
maxPreset = Math.min(maxPreset, systemMax);
|
|
91
92
|
const detectPrecision = () => {
|
|
92
93
|
let maxPrecision = 2;
|
|
93
94
|
if (!hasPresets)
|
|
@@ -51,7 +51,8 @@ function OverdueInvoicePayment({
|
|
|
51
51
|
t
|
|
52
52
|
} = (0, _context.useLocaleContext)();
|
|
53
53
|
const {
|
|
54
|
-
connect
|
|
54
|
+
connect,
|
|
55
|
+
session
|
|
55
56
|
} = (0, _payment.usePaymentContext)();
|
|
56
57
|
const [selectCurrencyId, setSelectCurrencyId] = (0, _react.useState)("");
|
|
57
58
|
const [payLoading, setPayLoading] = (0, _react.useState)(false);
|
|
@@ -59,7 +60,8 @@ function OverdueInvoicePayment({
|
|
|
59
60
|
const [processedCurrencies, setProcessedCurrencies] = (0, _react.useState)({});
|
|
60
61
|
const [paymentStatus, setPaymentStatus] = (0, _react.useState)({});
|
|
61
62
|
const sourceType = subscriptionId ? "subscription" : "customer";
|
|
62
|
-
const
|
|
63
|
+
const effectiveCustomerId = customerId || session?.user?.did;
|
|
64
|
+
const sourceId = subscriptionId || effectiveCustomerId;
|
|
63
65
|
const {
|
|
64
66
|
data = {
|
|
65
67
|
summary: {},
|
|
@@ -70,20 +72,20 @@ function OverdueInvoicePayment({
|
|
|
70
72
|
runAsync: refresh
|
|
71
73
|
} = (0, _ahooks.useRequest)(() => fetchOverdueInvoices({
|
|
72
74
|
subscriptionId,
|
|
73
|
-
customerId,
|
|
75
|
+
customerId: effectiveCustomerId,
|
|
74
76
|
authToken
|
|
75
77
|
}), {
|
|
76
|
-
ready: !!subscriptionId || !!
|
|
78
|
+
ready: !!subscriptionId || !!effectiveCustomerId
|
|
77
79
|
});
|
|
78
80
|
const detailUrl = (0, _react.useMemo)(() => {
|
|
79
81
|
if (subscriptionId) {
|
|
80
82
|
return (0, _ufo.joinURL)((0, _util.getPrefix)(), `/customer/subscription/${subscriptionId}`);
|
|
81
83
|
}
|
|
82
|
-
if (
|
|
84
|
+
if (effectiveCustomerId) {
|
|
83
85
|
return (0, _ufo.joinURL)((0, _util.getPrefix)(), "/customer/invoice/past-due");
|
|
84
86
|
}
|
|
85
87
|
return "";
|
|
86
|
-
}, [subscriptionId,
|
|
88
|
+
}, [subscriptionId, effectiveCustomerId]);
|
|
87
89
|
const summaryList = (0, _react.useMemo)(() => {
|
|
88
90
|
if (!data?.summary) {
|
|
89
91
|
return [];
|
|
@@ -114,7 +116,7 @@ function OverdueInvoicePayment({
|
|
|
114
116
|
}) => {
|
|
115
117
|
const relevantId = subscriptionId || response.customer_id;
|
|
116
118
|
const uniqueKey = `${relevantId}-${response.currency_id}`;
|
|
117
|
-
if (subscriptionId && response.subscription_id === subscriptionId ||
|
|
119
|
+
if (subscriptionId && response.subscription_id === subscriptionId || effectiveCustomerId && [data.customer?.id, effectiveCustomerId].includes(response.customer_id)) {
|
|
118
120
|
if (!processedCurrencies[uniqueKey]) {
|
|
119
121
|
setProcessedCurrencies(prev => ({
|
|
120
122
|
...prev,
|
|
@@ -125,7 +127,7 @@ function OverdueInvoicePayment({
|
|
|
125
127
|
}
|
|
126
128
|
});
|
|
127
129
|
}
|
|
128
|
-
}, [subscription, subscriptionId,
|
|
130
|
+
}, [subscription, subscriptionId, effectiveCustomerId]);
|
|
129
131
|
const handlePay = item => {
|
|
130
132
|
const {
|
|
131
133
|
currency,
|
|
@@ -150,14 +152,15 @@ function OverdueInvoicePayment({
|
|
|
150
152
|
};
|
|
151
153
|
if (subscriptionId) {
|
|
152
154
|
extraParams.subscriptionId = subscriptionId;
|
|
153
|
-
} else if (
|
|
154
|
-
extraParams.customerId =
|
|
155
|
+
} else if (effectiveCustomerId) {
|
|
156
|
+
extraParams.customerId = effectiveCustomerId;
|
|
155
157
|
}
|
|
156
158
|
connect.open({
|
|
157
159
|
containerEl: void 0,
|
|
158
160
|
saveConnect: false,
|
|
159
161
|
action: "collect-batch",
|
|
160
162
|
prefix: (0, _ufo.joinURL)((0, _util.getPrefix)(), "/api/did"),
|
|
163
|
+
useSocket: (0, _util.isCrossOrigin)() === false,
|
|
161
164
|
extraParams,
|
|
162
165
|
onSuccess: () => {
|
|
163
166
|
connect.close();
|
|
@@ -276,7 +279,7 @@ function OverdueInvoicePayment({
|
|
|
276
279
|
count: data.invoices?.length
|
|
277
280
|
});
|
|
278
281
|
}
|
|
279
|
-
if (
|
|
282
|
+
if (effectiveCustomerId) {
|
|
280
283
|
let title = "";
|
|
281
284
|
if (summaryList.length === 1) {
|
|
282
285
|
title = t("payment.customer.overdue.title", {
|
|
@@ -305,10 +308,7 @@ function OverdueInvoicePayment({
|
|
|
305
308
|
name: data.subscription?.description
|
|
306
309
|
});
|
|
307
310
|
}
|
|
308
|
-
|
|
309
|
-
return t("payment.customer.overdue.empty");
|
|
310
|
-
}
|
|
311
|
-
return "";
|
|
311
|
+
return t("payment.customer.overdue.empty");
|
|
312
312
|
};
|
|
313
313
|
if (mode === "custom" && children && typeof children === "function") {
|
|
314
314
|
return /* @__PURE__ */(0, _jsxRuntime.jsx)(_material.Stack, {
|
package/lib/libs/util.d.ts
CHANGED
|
@@ -3,6 +3,7 @@ import type { ActionProps, PricingRenderProps } from '../types';
|
|
|
3
3
|
export declare const PAYMENT_KIT_DID = "z2qaCNvKMv5GjouKdcDWexv6WqtHbpNPQDnAk";
|
|
4
4
|
export declare const isPaymentKitMounted: () => any;
|
|
5
5
|
export declare const getPrefix: () => string;
|
|
6
|
+
export declare function isCrossOrigin(): boolean;
|
|
6
7
|
export declare function formatToDate(date: Date | string | number, locale?: string, format?: string): any;
|
|
7
8
|
export declare function formatToDatetime(date: Date | string | number, locale?: string): any;
|
|
8
9
|
export declare function formatTime(date: Date | string | number, format?: string, locale?: string): any;
|
package/lib/libs/util.js
CHANGED
|
@@ -49,6 +49,7 @@ exports.getUserProfileLink = getUserProfileLink;
|
|
|
49
49
|
exports.getWebhookStatusColor = getWebhookStatusColor;
|
|
50
50
|
exports.getWordBreakStyle = getWordBreakStyle;
|
|
51
51
|
exports.hasDelegateTxHash = hasDelegateTxHash;
|
|
52
|
+
exports.isCrossOrigin = isCrossOrigin;
|
|
52
53
|
exports.isMobileSafari = isMobileSafari;
|
|
53
54
|
exports.isPaymentKitMounted = void 0;
|
|
54
55
|
exports.isValidCountry = isValidCountry;
|
|
@@ -100,6 +101,16 @@ const getPrefix = () => {
|
|
|
100
101
|
return (0, _ufo.joinURL)(baseUrl, prefix);
|
|
101
102
|
};
|
|
102
103
|
exports.getPrefix = getPrefix;
|
|
104
|
+
function isCrossOrigin() {
|
|
105
|
+
try {
|
|
106
|
+
const prefix = getPrefix();
|
|
107
|
+
const prefixOrigin = new URL(prefix).origin;
|
|
108
|
+
const currentOrigin = window.location.origin;
|
|
109
|
+
return prefixOrigin !== currentOrigin;
|
|
110
|
+
} catch (error) {
|
|
111
|
+
return false;
|
|
112
|
+
}
|
|
113
|
+
}
|
|
103
114
|
function formatToDate(date, locale = "en", format = "YYYY-MM-DD HH:mm:ss") {
|
|
104
115
|
if (!date) {
|
|
105
116
|
return "-";
|
|
@@ -355,6 +355,7 @@ function PaymentForm({
|
|
|
355
355
|
action: checkoutSession.mode,
|
|
356
356
|
prefix: (0, _ufo.joinURL)((0, _util.getPrefix)(), "/api/did"),
|
|
357
357
|
saveConnect: false,
|
|
358
|
+
useSocket: (0, _util.isCrossOrigin)() === false,
|
|
358
359
|
extraParams: {
|
|
359
360
|
checkoutSessionId: checkoutSession.id,
|
|
360
361
|
sessionUserDid: session?.user?.did
|
|
@@ -681,7 +682,7 @@ function PaymentForm({
|
|
|
681
682
|
})]
|
|
682
683
|
})
|
|
683
684
|
}), state.customerLimited && /* @__PURE__ */(0, _jsxRuntime.jsx)(_overDueInvoicePayment.default, {
|
|
684
|
-
customerId: customer?.id || session?.user?.
|
|
685
|
+
customerId: customer?.id || session?.user?.did,
|
|
685
686
|
onPaid: () => {
|
|
686
687
|
setState({
|
|
687
688
|
customerLimited: false
|
|
@@ -105,9 +105,10 @@ function ProductDonation({
|
|
|
105
105
|
if (hasPresets) {
|
|
106
106
|
sortedPresets = [...presets].map(p => parseFloat(p)).sort((a, b) => a - b);
|
|
107
107
|
}
|
|
108
|
-
const minPreset = hasPresets ? sortedPresets[
|
|
109
|
-
|
|
110
|
-
const
|
|
108
|
+
const minPreset = hasPresets ? sortedPresets[sortedPresets.length - 1] : 1;
|
|
109
|
+
let maxPreset = hasPresets ? sortedPresets[sortedPresets.length - 1] * 5 : 100;
|
|
110
|
+
const systemMax = settings.amount.maximum ? parseFloat(settings.amount.maximum) : Infinity;
|
|
111
|
+
maxPreset = Math.min(maxPreset, systemMax);
|
|
111
112
|
const detectPrecision = () => {
|
|
112
113
|
let maxPrecision = 2;
|
|
113
114
|
if (!hasPresets) return 0;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@blocklet/payment-react",
|
|
3
|
-
"version": "1.18.
|
|
3
|
+
"version": "1.18.30",
|
|
4
4
|
"description": "Reusable react components for payment kit v2",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"react",
|
|
@@ -54,15 +54,15 @@
|
|
|
54
54
|
}
|
|
55
55
|
},
|
|
56
56
|
"dependencies": {
|
|
57
|
-
"@arcblock/did-connect": "^2.
|
|
58
|
-
"@arcblock/ux": "^2.
|
|
59
|
-
"@arcblock/ws": "^1.
|
|
60
|
-
"@blocklet/ui-react": "^2.
|
|
57
|
+
"@arcblock/did-connect": "^2.13.1",
|
|
58
|
+
"@arcblock/ux": "^2.13.1",
|
|
59
|
+
"@arcblock/ws": "^1.20.0",
|
|
60
|
+
"@blocklet/ui-react": "^2.13.1",
|
|
61
61
|
"@mui/icons-material": "^5.16.6",
|
|
62
62
|
"@mui/lab": "^5.0.0-alpha.173",
|
|
63
63
|
"@mui/material": "^5.16.6",
|
|
64
64
|
"@mui/system": "^5.16.6",
|
|
65
|
-
"@ocap/util": "^1.
|
|
65
|
+
"@ocap/util": "^1.20.0",
|
|
66
66
|
"@stripe/react-stripe-js": "^2.7.3",
|
|
67
67
|
"@stripe/stripe-js": "^2.4.0",
|
|
68
68
|
"@vitejs/plugin-legacy": "^5.4.1",
|
|
@@ -93,7 +93,7 @@
|
|
|
93
93
|
"@babel/core": "^7.25.2",
|
|
94
94
|
"@babel/preset-env": "^7.25.2",
|
|
95
95
|
"@babel/preset-react": "^7.24.7",
|
|
96
|
-
"@blocklet/payment-types": "1.18.
|
|
96
|
+
"@blocklet/payment-types": "1.18.30",
|
|
97
97
|
"@storybook/addon-essentials": "^7.6.20",
|
|
98
98
|
"@storybook/addon-interactions": "^7.6.20",
|
|
99
99
|
"@storybook/addon-links": "^7.6.20",
|
|
@@ -124,5 +124,5 @@
|
|
|
124
124
|
"vite-plugin-babel": "^1.2.0",
|
|
125
125
|
"vite-plugin-node-polyfills": "^0.21.0"
|
|
126
126
|
},
|
|
127
|
-
"gitHead": "
|
|
127
|
+
"gitHead": "ed1753c48ee405a104cd2a0cab87cccb21e70ba8"
|
|
128
128
|
}
|
|
@@ -4,13 +4,20 @@ import { Button, Typography, Stack, Alert, SxProps } from '@mui/material';
|
|
|
4
4
|
import { useLocaleContext } from '@arcblock/ux/lib/Locale/context';
|
|
5
5
|
import Toast from '@arcblock/ux/lib/Toast';
|
|
6
6
|
import { joinURL } from 'ufo';
|
|
7
|
-
import type {
|
|
7
|
+
import type {
|
|
8
|
+
Customer,
|
|
9
|
+
Invoice,
|
|
10
|
+
PaymentCurrency,
|
|
11
|
+
PaymentMethod,
|
|
12
|
+
Subscription,
|
|
13
|
+
TInvoiceExpanded,
|
|
14
|
+
} from '@blocklet/payment-types';
|
|
8
15
|
import { useRequest } from 'ahooks';
|
|
9
16
|
import { Dialog } from '@arcblock/ux';
|
|
10
17
|
import { CheckCircle as CheckCircleIcon } from '@mui/icons-material';
|
|
11
18
|
import debounce from 'lodash/debounce';
|
|
12
19
|
import { usePaymentContext } from '../contexts/payment';
|
|
13
|
-
import { formatAmount, formatError, getPrefix } from '../libs/util';
|
|
20
|
+
import { formatAmount, formatError, getPrefix, isCrossOrigin } from '../libs/util';
|
|
14
21
|
import { useSubscription } from '../hooks/subscription';
|
|
15
22
|
import api from '../libs/api';
|
|
16
23
|
import LoadingButton from './loading-button';
|
|
@@ -60,6 +67,7 @@ type OverdueInvoicesResult = {
|
|
|
60
67
|
summary: { [key: string]: SummaryItem };
|
|
61
68
|
invoices: Invoice[];
|
|
62
69
|
subscriptionCount?: number;
|
|
70
|
+
customer?: Customer;
|
|
63
71
|
};
|
|
64
72
|
|
|
65
73
|
const fetchOverdueInvoices = async (params: {
|
|
@@ -95,7 +103,7 @@ function OverdueInvoicePayment({
|
|
|
95
103
|
authToken,
|
|
96
104
|
}: Props) {
|
|
97
105
|
const { t } = useLocaleContext();
|
|
98
|
-
const { connect } = usePaymentContext();
|
|
106
|
+
const { connect, session } = usePaymentContext();
|
|
99
107
|
const [selectCurrencyId, setSelectCurrencyId] = useState('');
|
|
100
108
|
const [payLoading, setPayLoading] = useState(false);
|
|
101
109
|
const [dialogOpen, setDialogOpen] = useState(dialogProps.open || false);
|
|
@@ -103,7 +111,8 @@ function OverdueInvoicePayment({
|
|
|
103
111
|
const [paymentStatus, setPaymentStatus] = useState<{ [key: string]: 'success' | 'error' | 'idle' }>({});
|
|
104
112
|
|
|
105
113
|
const sourceType = subscriptionId ? 'subscription' : 'customer';
|
|
106
|
-
const
|
|
114
|
+
const effectiveCustomerId = customerId || session?.user?.did;
|
|
115
|
+
const sourceId = subscriptionId || effectiveCustomerId;
|
|
107
116
|
const {
|
|
108
117
|
data = {
|
|
109
118
|
summary: {},
|
|
@@ -112,19 +121,19 @@ function OverdueInvoicePayment({
|
|
|
112
121
|
error,
|
|
113
122
|
loading,
|
|
114
123
|
runAsync: refresh,
|
|
115
|
-
} = useRequest(() => fetchOverdueInvoices({ subscriptionId, customerId, authToken }), {
|
|
116
|
-
ready: !!subscriptionId || !!
|
|
124
|
+
} = useRequest(() => fetchOverdueInvoices({ subscriptionId, customerId: effectiveCustomerId, authToken }), {
|
|
125
|
+
ready: !!subscriptionId || !!effectiveCustomerId,
|
|
117
126
|
});
|
|
118
127
|
|
|
119
128
|
const detailUrl = useMemo(() => {
|
|
120
129
|
if (subscriptionId) {
|
|
121
130
|
return joinURL(getPrefix(), `/customer/subscription/${subscriptionId}`);
|
|
122
131
|
}
|
|
123
|
-
if (
|
|
132
|
+
if (effectiveCustomerId) {
|
|
124
133
|
return joinURL(getPrefix(), '/customer/invoice/past-due');
|
|
125
134
|
}
|
|
126
135
|
return '';
|
|
127
|
-
}, [subscriptionId,
|
|
136
|
+
}, [subscriptionId, effectiveCustomerId]);
|
|
128
137
|
|
|
129
138
|
const summaryList = useMemo(() => {
|
|
130
139
|
if (!data?.summary) {
|
|
@@ -163,7 +172,7 @@ function OverdueInvoicePayment({
|
|
|
163
172
|
|
|
164
173
|
if (
|
|
165
174
|
(subscriptionId && response.subscription_id === subscriptionId) ||
|
|
166
|
-
(
|
|
175
|
+
(effectiveCustomerId && [data.customer?.id, effectiveCustomerId].includes(response.customer_id))
|
|
167
176
|
) {
|
|
168
177
|
if (!processedCurrencies[uniqueKey]) {
|
|
169
178
|
setProcessedCurrencies((prev) => ({ ...prev, [uniqueKey]: 1 }));
|
|
@@ -173,7 +182,7 @@ function OverdueInvoicePayment({
|
|
|
173
182
|
});
|
|
174
183
|
}
|
|
175
184
|
// eslint-disable-next-line react-hooks/exhaustive-deps
|
|
176
|
-
}, [subscription, subscriptionId,
|
|
185
|
+
}, [subscription, subscriptionId, effectiveCustomerId]);
|
|
177
186
|
|
|
178
187
|
const handlePay = (item: SummaryItem) => {
|
|
179
188
|
const { currency, method } = item;
|
|
@@ -196,8 +205,8 @@ function OverdueInvoicePayment({
|
|
|
196
205
|
|
|
197
206
|
if (subscriptionId) {
|
|
198
207
|
extraParams.subscriptionId = subscriptionId;
|
|
199
|
-
} else if (
|
|
200
|
-
extraParams.customerId =
|
|
208
|
+
} else if (effectiveCustomerId) {
|
|
209
|
+
extraParams.customerId = effectiveCustomerId;
|
|
201
210
|
}
|
|
202
211
|
|
|
203
212
|
connect.open({
|
|
@@ -205,6 +214,7 @@ function OverdueInvoicePayment({
|
|
|
205
214
|
saveConnect: false,
|
|
206
215
|
action: 'collect-batch',
|
|
207
216
|
prefix: joinURL(getPrefix(), '/api/did'),
|
|
217
|
+
useSocket: isCrossOrigin() === false,
|
|
208
218
|
extraParams,
|
|
209
219
|
onSuccess: () => {
|
|
210
220
|
connect.close();
|
|
@@ -343,7 +353,7 @@ function OverdueInvoicePayment({
|
|
|
343
353
|
count: data.invoices?.length,
|
|
344
354
|
});
|
|
345
355
|
}
|
|
346
|
-
if (
|
|
356
|
+
if (effectiveCustomerId) {
|
|
347
357
|
let title = '';
|
|
348
358
|
if (summaryList.length === 1) {
|
|
349
359
|
title = t('payment.customer.overdue.title', {
|
|
@@ -374,11 +384,7 @@ function OverdueInvoicePayment({
|
|
|
374
384
|
name: data.subscription?.description,
|
|
375
385
|
});
|
|
376
386
|
}
|
|
377
|
-
|
|
378
|
-
return t('payment.customer.overdue.empty');
|
|
379
|
-
}
|
|
380
|
-
|
|
381
|
-
return '';
|
|
387
|
+
return t('payment.customer.overdue.empty');
|
|
382
388
|
};
|
|
383
389
|
|
|
384
390
|
if (mode === 'custom' && children && typeof children === 'function') {
|
|
@@ -28,6 +28,7 @@ import {
|
|
|
28
28
|
getInvoiceDescriptionAndReason,
|
|
29
29
|
getInvoiceStatusColor,
|
|
30
30
|
getTxLink,
|
|
31
|
+
isCrossOrigin,
|
|
31
32
|
} from '../../libs/util';
|
|
32
33
|
import Table from '../../components/table';
|
|
33
34
|
import { createLink, handleNavigation, LinkInfo } from '../../libs/navigation';
|
|
@@ -617,6 +618,7 @@ export default function CustomerInvoiceList(props: Props) {
|
|
|
617
618
|
connect.open({
|
|
618
619
|
action: 'collect',
|
|
619
620
|
saveConnect: false,
|
|
621
|
+
useSocket: isCrossOrigin() === false,
|
|
620
622
|
messages: {
|
|
621
623
|
scan: '',
|
|
622
624
|
title: t(`payment.customer.invoice.${action || 'pay'}`),
|
package/src/libs/util.ts
CHANGED
|
@@ -61,6 +61,17 @@ export const getPrefix = (): string => {
|
|
|
61
61
|
return joinURL(baseUrl, prefix);
|
|
62
62
|
};
|
|
63
63
|
|
|
64
|
+
export function isCrossOrigin() {
|
|
65
|
+
try {
|
|
66
|
+
const prefix = getPrefix();
|
|
67
|
+
const prefixOrigin = new URL(prefix).origin;
|
|
68
|
+
const currentOrigin = window.location.origin;
|
|
69
|
+
return prefixOrigin !== currentOrigin;
|
|
70
|
+
} catch (error) {
|
|
71
|
+
return false;
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
|
|
64
75
|
export function formatToDate(date: Date | string | number, locale = 'en', format = 'YYYY-MM-DD HH:mm:ss') {
|
|
65
76
|
if (!date) {
|
|
66
77
|
return '-';
|
|
@@ -32,6 +32,7 @@ import {
|
|
|
32
32
|
getPrefix,
|
|
33
33
|
getQueryParams,
|
|
34
34
|
getStatementDescriptor,
|
|
35
|
+
isCrossOrigin,
|
|
35
36
|
} from '../../libs/util';
|
|
36
37
|
import type { CheckoutCallbacks, CheckoutContext } from '../../types';
|
|
37
38
|
import AddressForm from './address';
|
|
@@ -426,6 +427,7 @@ export default function PaymentForm({
|
|
|
426
427
|
action: checkoutSession.mode,
|
|
427
428
|
prefix: joinURL(getPrefix(), '/api/did'),
|
|
428
429
|
saveConnect: false,
|
|
430
|
+
useSocket: isCrossOrigin() === false,
|
|
429
431
|
extraParams: { checkoutSessionId: checkoutSession.id, sessionUserDid: session?.user?.did },
|
|
430
432
|
onSuccess: async () => {
|
|
431
433
|
connect.close();
|
|
@@ -726,7 +728,7 @@ export default function PaymentForm({
|
|
|
726
728
|
</Fade>
|
|
727
729
|
{state.customerLimited && (
|
|
728
730
|
<OverdueInvoicePayment
|
|
729
|
-
customerId={customer?.id || session?.user?.
|
|
731
|
+
customerId={customer?.id || session?.user?.did}
|
|
730
732
|
onPaid={() => {
|
|
731
733
|
setState({ customerLimited: false });
|
|
732
734
|
onAction();
|
|
@@ -108,9 +108,10 @@ export default function ProductDonation({
|
|
|
108
108
|
}
|
|
109
109
|
|
|
110
110
|
// Get min and max values for random amount
|
|
111
|
-
const minPreset = hasPresets ? sortedPresets[
|
|
112
|
-
|
|
113
|
-
const
|
|
111
|
+
const minPreset = hasPresets ? sortedPresets[sortedPresets.length - 1] : 1;
|
|
112
|
+
let maxPreset = hasPresets ? sortedPresets[sortedPresets.length - 1] * 5 : 100;
|
|
113
|
+
const systemMax = settings.amount.maximum ? parseFloat(settings.amount.maximum) : Infinity;
|
|
114
|
+
maxPreset = Math.min(maxPreset, systemMax);
|
|
114
115
|
|
|
115
116
|
// Detect precision from existing presets
|
|
116
117
|
const detectPrecision = () => {
|