@solvapay/react 1.3.0 → 1.4.0-preview-ecd61384a4e849717e13d47ab2daa086cdcd91c5
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 +28 -0
- package/dist/adapters/auth.js +1 -0
- package/dist/adapters/auth0.js +1 -0
- package/dist/adapters/session-auth.js +1 -0
- package/dist/{chunk-DW5FJUUG.js → chunk-6RR4J74H.js} +214 -24
- package/dist/chunk-GFWMLRR3.js +3224 -0
- package/dist/chunk-MLKGABMK.js +9 -0
- package/dist/{chunk-4ISNB3JU.js → chunk-SUHDOG7Q.js} +1 -1
- package/dist/{index-BwwdMBdt.d.ts → index-CDvQcobx.d.cts} +21 -2
- package/dist/{index-kXLvp7EU.d.cts → index-w_VMlKm5.d.ts} +21 -2
- package/dist/index.cjs +2216 -363
- package/dist/index.d.cts +34 -5
- package/dist/index.d.ts +34 -5
- package/dist/index.js +66 -3
- package/dist/mcp/index.cjs +216 -29
- package/dist/mcp/index.d.cts +1 -1
- package/dist/mcp/index.d.ts +1 -1
- package/dist/mcp/index.js +3 -2
- package/dist/primitives/index.cjs +2101 -362
- package/dist/primitives/index.d.cts +180 -5
- package/dist/primitives/index.d.ts +180 -5
- package/dist/primitives/index.js +73 -2
- package/dist/{shared-lIhc8DS3.d.ts → shared-D8raw1Nv.d.ts} +143 -12
- package/dist/{shared-BNZAIWkU.d.cts → shared-LcjvX4fD.d.cts} +143 -12
- package/dist/styles.css +513 -0
- package/dist/webapi-K5XBCEO6.js +3775 -0
- package/package.json +5 -5
- package/dist/chunk-K7ZUJI26.js +0 -1527
|
@@ -45,6 +45,40 @@ __export(primitives_exports, {
|
|
|
45
45
|
AmountPickerCustom: () => AmountPickerCustom2,
|
|
46
46
|
AmountPickerOption: () => AmountPickerOption2,
|
|
47
47
|
AmountPickerRoot: () => AmountPickerRoot2,
|
|
48
|
+
AutoRecharge: () => AutoRecharge,
|
|
49
|
+
AutoRechargeActions: () => AutoRechargeActions2,
|
|
50
|
+
AutoRechargeAmountField: () => AutoRechargeAmountField2,
|
|
51
|
+
AutoRechargeBody: () => AutoRechargeBody2,
|
|
52
|
+
AutoRechargeCancelButton: () => AutoRechargeCancelButton2,
|
|
53
|
+
AutoRechargeCard: () => AutoRechargeCard2,
|
|
54
|
+
AutoRechargeCardHeading: () => AutoRechargeCardHeading2,
|
|
55
|
+
AutoRechargeCardSetup: () => AutoRechargeCardSetup,
|
|
56
|
+
AutoRechargeCardSummary: () => AutoRechargeCardSummary2,
|
|
57
|
+
AutoRechargeContent: () => AutoRechargeContent2,
|
|
58
|
+
AutoRechargeDescription: () => AutoRechargeDescription2,
|
|
59
|
+
AutoRechargeDisableButton: () => AutoRechargeDisableButton2,
|
|
60
|
+
AutoRechargeEnableQuestion: () => AutoRechargeEnableQuestion2,
|
|
61
|
+
AutoRechargeEnableRow: () => AutoRechargeEnableRow2,
|
|
62
|
+
AutoRechargeEnableSentence: () => AutoRechargeEnableSentence2,
|
|
63
|
+
AutoRechargeEnableSwitch: () => AutoRechargeEnableSwitch2,
|
|
64
|
+
AutoRechargeError: () => AutoRechargeError2,
|
|
65
|
+
AutoRechargeFields: () => AutoRechargeFields2,
|
|
66
|
+
AutoRechargeHeader: () => AutoRechargeHeader2,
|
|
67
|
+
AutoRechargeHint: () => AutoRechargeHint2,
|
|
68
|
+
AutoRechargeLoading: () => AutoRechargeLoading2,
|
|
69
|
+
AutoRechargeOverlay: () => AutoRechargeOverlay2,
|
|
70
|
+
AutoRechargeRoot: () => AutoRechargeRoot2,
|
|
71
|
+
AutoRechargeSaveButton: () => AutoRechargeSaveButton2,
|
|
72
|
+
AutoRechargeSetup: () => AutoRechargeSetup2,
|
|
73
|
+
AutoRechargeStatus: () => AutoRechargeStatus2,
|
|
74
|
+
AutoRechargeStatusMessage: () => AutoRechargeStatusMessage2,
|
|
75
|
+
AutoRechargeSummary: () => AutoRechargeSummary2,
|
|
76
|
+
AutoRechargeThresholdField: () => AutoRechargeThresholdField2,
|
|
77
|
+
AutoRechargeTitle: () => AutoRechargeTitle2,
|
|
78
|
+
AutoRechargeTopupField: () => AutoRechargeTopupField2,
|
|
79
|
+
AutoRechargeTrigger: () => AutoRechargeTrigger2,
|
|
80
|
+
AutoRechargeUnitToggle: () => AutoRechargeUnitToggle2,
|
|
81
|
+
AutoRechargeValidationError: () => AutoRechargeValidationError2,
|
|
48
82
|
BalanceBadge: () => BalanceBadge,
|
|
49
83
|
CancelPlanButton: () => CancelPlanButton,
|
|
50
84
|
CancelledPlanNotice: () => CancelledPlanNotice,
|
|
@@ -105,7 +139,7 @@ __export(primitives_exports, {
|
|
|
105
139
|
PaywallNoticePlans: () => Plans,
|
|
106
140
|
PaywallNoticeProductContext: () => ProductContext,
|
|
107
141
|
PaywallNoticeRetry: () => Retry,
|
|
108
|
-
PaywallNoticeRoot: () =>
|
|
142
|
+
PaywallNoticeRoot: () => Root12,
|
|
109
143
|
PlanBadge: () => PlanBadge,
|
|
110
144
|
PlanSelector: () => PlanSelector,
|
|
111
145
|
PlanSelectorCard: () => PlanSelectorCard2,
|
|
@@ -140,16 +174,17 @@ __export(primitives_exports, {
|
|
|
140
174
|
UsageMeterBar: () => Bar,
|
|
141
175
|
UsageMeterEmpty: () => Empty,
|
|
142
176
|
UsageMeterLabel: () => Label,
|
|
143
|
-
UsageMeterLoading: () =>
|
|
177
|
+
UsageMeterLoading: () => Loading8,
|
|
144
178
|
UsageMeterPercentage: () => Percentage,
|
|
145
179
|
UsageMeterResetsIn: () => ResetsIn,
|
|
146
|
-
UsageMeterRoot: () =>
|
|
180
|
+
UsageMeterRoot: () => Root13,
|
|
147
181
|
composeEventHandlers: () => composeEventHandlers,
|
|
148
182
|
composeRefs: () => composeRefs,
|
|
149
183
|
setRef: () => setRef,
|
|
150
184
|
useActivationFlow: () => useActivationFlow,
|
|
151
185
|
useAmountPicker: () => useAmountPicker,
|
|
152
186
|
useAmountPickerCopy: () => useAmountPickerCopy,
|
|
187
|
+
useAutoRechargeForm: () => useAutoRechargeForm,
|
|
153
188
|
useCancelledPlanNotice: () => useCancelledPlanNotice,
|
|
154
189
|
useCheckoutStepsContext: () => useCheckoutSteps,
|
|
155
190
|
useCheckoutSummary: () => useCheckoutSummary,
|
|
@@ -417,6 +452,7 @@ var DEFAULT_ROUTES = {
|
|
|
417
452
|
getProduct: "/api/get-product",
|
|
418
453
|
listPlans: "/api/list-plans",
|
|
419
454
|
getPaymentMethod: "/api/payment-method",
|
|
455
|
+
autoRecharge: "/api/auto-recharge",
|
|
420
456
|
getUsage: "/api/usage",
|
|
421
457
|
getLimits: "/api/limits"
|
|
422
458
|
};
|
|
@@ -454,7 +490,11 @@ function createHttpTransport(config) {
|
|
|
454
490
|
}),
|
|
455
491
|
createTopupPayment: (params) => request(config, routeFor(config, "createTopupPayment"), {
|
|
456
492
|
method: "POST",
|
|
457
|
-
body: {
|
|
493
|
+
body: {
|
|
494
|
+
amount: params.amount,
|
|
495
|
+
currency: params.currency,
|
|
496
|
+
...params.autoRecharge ? { autoRecharge: params.autoRecharge } : {}
|
|
497
|
+
},
|
|
458
498
|
onErrorContext: "createTopupPayment",
|
|
459
499
|
errorPrefix: "Failed to create topup payment"
|
|
460
500
|
}),
|
|
@@ -503,16 +543,12 @@ function createHttpTransport(config) {
|
|
|
503
543
|
}
|
|
504
544
|
);
|
|
505
545
|
},
|
|
506
|
-
createCustomerSession: () => request(
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
onErrorContext: "createCustomerSession",
|
|
513
|
-
errorPrefix: "Failed to create customer session"
|
|
514
|
-
}
|
|
515
|
-
),
|
|
546
|
+
createCustomerSession: () => request(config, routeFor(config, "createCustomerSession"), {
|
|
547
|
+
method: "POST",
|
|
548
|
+
body: {},
|
|
549
|
+
onErrorContext: "createCustomerSession",
|
|
550
|
+
errorPrefix: "Failed to create customer session"
|
|
551
|
+
}),
|
|
516
552
|
getMerchant: () => request(config, routeFor(config, "getMerchant"), {
|
|
517
553
|
method: "GET",
|
|
518
554
|
onErrorContext: "getMerchant",
|
|
@@ -542,6 +578,22 @@ function createHttpTransport(config) {
|
|
|
542
578
|
onErrorContext: "getPaymentMethod",
|
|
543
579
|
errorPrefix: "Failed to load payment method"
|
|
544
580
|
}),
|
|
581
|
+
getAutoRecharge: () => request(config, routeFor(config, "autoRecharge"), {
|
|
582
|
+
method: "GET",
|
|
583
|
+
onErrorContext: "getAutoRecharge",
|
|
584
|
+
errorPrefix: "Failed to load auto-recharge"
|
|
585
|
+
}),
|
|
586
|
+
saveAutoRecharge: (input) => request(config, routeFor(config, "autoRecharge"), {
|
|
587
|
+
method: "PUT",
|
|
588
|
+
body: input,
|
|
589
|
+
onErrorContext: "saveAutoRecharge",
|
|
590
|
+
errorPrefix: "Failed to save auto-recharge"
|
|
591
|
+
}),
|
|
592
|
+
disableAutoRecharge: () => request(config, routeFor(config, "autoRecharge"), {
|
|
593
|
+
method: "DELETE",
|
|
594
|
+
onErrorContext: "disableAutoRecharge",
|
|
595
|
+
errorPrefix: "Failed to disable auto-recharge"
|
|
596
|
+
}),
|
|
545
597
|
getUsage: () => request(config, routeFor(config, "getUsage"), {
|
|
546
598
|
method: "GET",
|
|
547
599
|
onErrorContext: "getUsage",
|
|
@@ -680,6 +732,42 @@ var enCopy = {
|
|
|
680
732
|
creditEstimateExact: "= {credits} credits",
|
|
681
733
|
creditEstimateApprox: "~ {credits} credits"
|
|
682
734
|
},
|
|
735
|
+
autoRecharge: {
|
|
736
|
+
heading: "Auto recharge",
|
|
737
|
+
description: "Automatically top up so you never run out \u2014 recommended for production. You can turn this off anytime.",
|
|
738
|
+
settingsHeading: "Auto recharge settings",
|
|
739
|
+
setupTriggerLabel: "Set up auto-recharge",
|
|
740
|
+
modifyTriggerLabel: "Modify",
|
|
741
|
+
notConfiguredHint: "Automatic top-ups are off. Set up auto-recharge if you want credits added when your balance runs low.",
|
|
742
|
+
enableLabel: "Enable auto-recharge",
|
|
743
|
+
enableQuestion: "Would you like to set up automatic recharge?",
|
|
744
|
+
enableSentence: "Yes, automatically recharge my card when my credit balance falls below a threshold",
|
|
745
|
+
thresholdLabel: "When balance falls below",
|
|
746
|
+
thresholdAriaLabel: "Balance threshold",
|
|
747
|
+
fixedAmountLabel: "Add this amount",
|
|
748
|
+
fixedAmountAriaLabel: "Fixed top-up amount",
|
|
749
|
+
saveButton: "Save settings",
|
|
750
|
+
cancelButton: "Cancel",
|
|
751
|
+
disableButton: "Disable automatic top-up",
|
|
752
|
+
savedMessage: "Automatic top-up settings saved.",
|
|
753
|
+
disabledMessage: "Automatic top-ups disabled.",
|
|
754
|
+
setupRequiredMessage: "Confirm your card to activate automatic top-ups.",
|
|
755
|
+
setupHeading: "Authorize card",
|
|
756
|
+
setupDescription: "Authorize a card for automatic top-ups. You will not be charged now.",
|
|
757
|
+
setupSubmit: "Save card for auto-recharge",
|
|
758
|
+
setupProcessing: "Authorizing...",
|
|
759
|
+
setupAwaitingConfirmation: "Card authorized. Finishing activation \u2014 this can take a moment.",
|
|
760
|
+
setupAuthFailed: "Card authentication failed. Please try a different card.",
|
|
761
|
+
invalidThreshold: "Enter a valid balance threshold.",
|
|
762
|
+
thresholdTooLow: "Balance threshold must be greater than zero.",
|
|
763
|
+
minTopupAmount: "Top-up amount must be at least {amount}.",
|
|
764
|
+
topupBelowThreshold: "Top-up amount must be at least your balance threshold ({amount}).",
|
|
765
|
+
creditsPerRecharge: "\u2248 {credits} credits per recharge",
|
|
766
|
+
creditsPerRechargeApprox: "~ {credits} credits per recharge",
|
|
767
|
+
currencyPerRecharge: "\u2248 {amount} per recharge",
|
|
768
|
+
currencyPerRechargeApprox: "~ {amount} per recharge",
|
|
769
|
+
statusFailed: "Payment failed \u2014 update your card to resume"
|
|
770
|
+
},
|
|
683
771
|
activationFlow: {
|
|
684
772
|
heading: "Confirm your plan",
|
|
685
773
|
activateButton: "Activate",
|
|
@@ -4306,7 +4394,7 @@ function getStripeCacheKey2(publishableKey, accountId) {
|
|
|
4306
4394
|
return accountId ? `${publishableKey}:${accountId}` : publishableKey;
|
|
4307
4395
|
}
|
|
4308
4396
|
function useTopup(options) {
|
|
4309
|
-
const { amount, currency } = options;
|
|
4397
|
+
const { amount, currency, autoRecharge } = options;
|
|
4310
4398
|
const { createTopupPayment, customerRef, updateCustomerRef } = useSolvaPay();
|
|
4311
4399
|
const [loading, setLoading] = (0, import_react27.useState)(false);
|
|
4312
4400
|
const [error, setError] = (0, import_react27.useState)(null);
|
|
@@ -4325,7 +4413,7 @@ function useTopup(options) {
|
|
|
4325
4413
|
setLoading(true);
|
|
4326
4414
|
setError(null);
|
|
4327
4415
|
try {
|
|
4328
|
-
const result = await createTopupPayment({ amount, currency });
|
|
4416
|
+
const result = await createTopupPayment({ amount, currency, autoRecharge });
|
|
4329
4417
|
if (!result || typeof result !== "object") {
|
|
4330
4418
|
throw new Error("Invalid topup payment intent response from server");
|
|
4331
4419
|
}
|
|
@@ -4357,7 +4445,7 @@ function useTopup(options) {
|
|
|
4357
4445
|
setLoading(false);
|
|
4358
4446
|
isStartingRef.current = false;
|
|
4359
4447
|
}
|
|
4360
|
-
}, [amount, currency, createTopupPayment, customerRef, updateCustomerRef, loading]);
|
|
4448
|
+
}, [amount, currency, autoRecharge, createTopupPayment, customerRef, updateCustomerRef, loading]);
|
|
4361
4449
|
const reset = (0, import_react27.useCallback)(() => {
|
|
4362
4450
|
isStartingRef.current = false;
|
|
4363
4451
|
setLoading(false);
|
|
@@ -4389,6 +4477,7 @@ var Root7 = (0, import_react28.forwardRef)(function TopupFormRoot(props, forward
|
|
|
4389
4477
|
const {
|
|
4390
4478
|
amount,
|
|
4391
4479
|
currency,
|
|
4480
|
+
autoRecharge,
|
|
4392
4481
|
onSuccess,
|
|
4393
4482
|
onError,
|
|
4394
4483
|
returnUrl,
|
|
@@ -4412,7 +4501,8 @@ var Root7 = (0, import_react28.forwardRef)(function TopupFormRoot(props, forward
|
|
|
4412
4501
|
stripePromise
|
|
4413
4502
|
} = useTopup({
|
|
4414
4503
|
amount,
|
|
4415
|
-
currency
|
|
4504
|
+
currency,
|
|
4505
|
+
autoRecharge
|
|
4416
4506
|
});
|
|
4417
4507
|
const hasInitializedRef = (0, import_react28.useRef)(false);
|
|
4418
4508
|
const hasAmount = amount > 0;
|
|
@@ -4901,170 +4991,1784 @@ function usePurchaseGate() {
|
|
|
4901
4991
|
return useGateCtx2("usePurchaseGate");
|
|
4902
4992
|
}
|
|
4903
4993
|
|
|
4904
|
-
// src/primitives/
|
|
4994
|
+
// src/primitives/AutoRecharge.tsx
|
|
4995
|
+
var import_react32 = require("react");
|
|
4996
|
+
var import_react_dom = require("react-dom");
|
|
4997
|
+
var import_react_stripe_js3 = require("@stripe/react-stripe-js");
|
|
4998
|
+
var import_stripe_js3 = require("@stripe/stripe-js");
|
|
4999
|
+
|
|
5000
|
+
// src/hooks/useAutoRecharge.ts
|
|
4905
5001
|
var import_react31 = require("react");
|
|
4906
|
-
|
|
4907
|
-
|
|
4908
|
-
|
|
4909
|
-
|
|
4910
|
-
|
|
4911
|
-
|
|
4912
|
-
|
|
5002
|
+
|
|
5003
|
+
// src/hooks/autoRechargeCache.ts
|
|
5004
|
+
var autoRechargeCache = /* @__PURE__ */ new Map();
|
|
5005
|
+
var CACHE_DURATION5 = 5 * 60 * 1e3;
|
|
5006
|
+
function autoRechargeCacheKeyFor(config) {
|
|
5007
|
+
return createTransportCacheKey(config, config?.api?.autoRecharge || "/api/auto-recharge");
|
|
5008
|
+
}
|
|
5009
|
+
|
|
5010
|
+
// src/hooks/useAutoRecharge.ts
|
|
5011
|
+
function mergeAutoRechargeConfig(config, display) {
|
|
5012
|
+
return display ? { ...config, display } : config;
|
|
5013
|
+
}
|
|
5014
|
+
async function fetchAutoRecharge(config) {
|
|
5015
|
+
const transport = config?.transport ?? createHttpTransport(config);
|
|
5016
|
+
if (!transport.getAutoRecharge) return null;
|
|
5017
|
+
const response = await transport.getAutoRecharge();
|
|
5018
|
+
if (!response.config) return null;
|
|
5019
|
+
return mergeAutoRechargeConfig(response.config, response.display);
|
|
5020
|
+
}
|
|
5021
|
+
function useAutoRecharge() {
|
|
5022
|
+
const { _config } = useSolvaPay();
|
|
5023
|
+
const key = autoRechargeCacheKeyFor(_config);
|
|
5024
|
+
const [config, setConfig] = (0, import_react31.useState)(
|
|
5025
|
+
() => autoRechargeCache.get(key)?.config ?? null
|
|
5026
|
+
);
|
|
5027
|
+
const [loading, setLoading] = (0, import_react31.useState)(() => {
|
|
5028
|
+
const cached = autoRechargeCache.get(key);
|
|
5029
|
+
return !cached || !cached.config && !cached.promise;
|
|
5030
|
+
});
|
|
5031
|
+
const [saving, setSaving] = (0, import_react31.useState)(false);
|
|
5032
|
+
const [disabling, setDisabling] = (0, import_react31.useState)(false);
|
|
5033
|
+
const [error, setError] = (0, import_react31.useState)(null);
|
|
5034
|
+
const requestSeq = (0, import_react31.useRef)(0);
|
|
5035
|
+
const load = (0, import_react31.useCallback)(
|
|
5036
|
+
async (force = false) => {
|
|
5037
|
+
const seq = requestSeq.current;
|
|
5038
|
+
const cached = autoRechargeCache.get(key);
|
|
5039
|
+
const now = Date.now();
|
|
5040
|
+
if (!force && cached?.config && now - cached.timestamp < CACHE_DURATION5) {
|
|
5041
|
+
if (seq !== requestSeq.current) return;
|
|
5042
|
+
setConfig(cached.config);
|
|
5043
|
+
setLoading(false);
|
|
5044
|
+
setError(null);
|
|
5045
|
+
return;
|
|
5046
|
+
}
|
|
5047
|
+
if (!force && cached?.promise) {
|
|
5048
|
+
setLoading(true);
|
|
5049
|
+
try {
|
|
5050
|
+
const value = await cached.promise;
|
|
5051
|
+
if (seq !== requestSeq.current) return;
|
|
5052
|
+
setConfig(value);
|
|
5053
|
+
setError(null);
|
|
5054
|
+
} catch (caught) {
|
|
5055
|
+
if (seq !== requestSeq.current) return;
|
|
5056
|
+
setError(caught instanceof Error ? caught : new Error(String(caught)));
|
|
5057
|
+
} finally {
|
|
5058
|
+
if (seq === requestSeq.current) {
|
|
5059
|
+
setLoading(false);
|
|
5060
|
+
}
|
|
5061
|
+
}
|
|
5062
|
+
return;
|
|
5063
|
+
}
|
|
5064
|
+
setLoading(true);
|
|
5065
|
+
setError(null);
|
|
5066
|
+
const promise = fetchAutoRecharge(_config);
|
|
5067
|
+
autoRechargeCache.set(key, {
|
|
5068
|
+
config: cached?.config ?? null,
|
|
5069
|
+
promise,
|
|
5070
|
+
timestamp: now
|
|
5071
|
+
});
|
|
5072
|
+
try {
|
|
5073
|
+
const value = await promise;
|
|
5074
|
+
if (seq !== requestSeq.current) return;
|
|
5075
|
+
autoRechargeCache.set(key, { config: value, promise: null, timestamp: Date.now() });
|
|
5076
|
+
setConfig(value);
|
|
5077
|
+
} catch (caught) {
|
|
5078
|
+
if (seq !== requestSeq.current) return;
|
|
5079
|
+
const err = caught instanceof Error ? caught : new Error(String(caught));
|
|
5080
|
+
autoRechargeCache.set(key, { config: null, promise: null, timestamp: Date.now() });
|
|
5081
|
+
setError(err);
|
|
5082
|
+
} finally {
|
|
5083
|
+
if (seq === requestSeq.current) {
|
|
5084
|
+
setLoading(false);
|
|
5085
|
+
}
|
|
5086
|
+
}
|
|
5087
|
+
},
|
|
5088
|
+
[_config, key]
|
|
5089
|
+
);
|
|
4913
5090
|
(0, import_react31.useEffect)(() => {
|
|
4914
|
-
|
|
4915
|
-
}, [
|
|
4916
|
-
const
|
|
4917
|
-
|
|
4918
|
-
|
|
4919
|
-
|
|
4920
|
-
|
|
4921
|
-
"data-loading": loading ? "" : void 0,
|
|
4922
|
-
"data-has-purchase": activePurchase ? "" : void 0,
|
|
4923
|
-
"data-has-paid-purchase": hasPaidPurchase ? "" : void 0,
|
|
4924
|
-
role: "status",
|
|
4925
|
-
"aria-live": "polite",
|
|
4926
|
-
"aria-busy": loading,
|
|
4927
|
-
"aria-label": interpolate(copy.product.currentProductLabel, { name: planToDisplay }),
|
|
4928
|
-
...rest
|
|
4929
|
-
};
|
|
4930
|
-
if (asChild) {
|
|
4931
|
-
return (
|
|
4932
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
4933
|
-
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Slot, { ref: forwardedRef, ...commonProps, children: children ?? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(import_jsx_runtime22.Fragment, { children: planToDisplay }) })
|
|
4934
|
-
);
|
|
4935
|
-
}
|
|
4936
|
-
void purchases;
|
|
4937
|
-
return (
|
|
4938
|
-
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
4939
|
-
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)("div", { ref: forwardedRef, ...commonProps, children: children ?? planToDisplay })
|
|
5091
|
+
void load();
|
|
5092
|
+
}, [load]);
|
|
5093
|
+
const refresh = (0, import_react31.useCallback)(
|
|
5094
|
+
async (force = true) => {
|
|
5095
|
+
await load(force);
|
|
5096
|
+
},
|
|
5097
|
+
[load]
|
|
4940
5098
|
);
|
|
4941
|
-
|
|
4942
|
-
|
|
4943
|
-
|
|
5099
|
+
const save = (0, import_react31.useCallback)(
|
|
5100
|
+
async (input) => {
|
|
5101
|
+
const transport = _config?.transport ?? createHttpTransport(_config);
|
|
5102
|
+
if (!transport.saveAutoRecharge) {
|
|
5103
|
+
throw new Error("saveAutoRecharge is not available on this transport");
|
|
5104
|
+
}
|
|
5105
|
+
setSaving(true);
|
|
5106
|
+
setError(null);
|
|
5107
|
+
const seq = ++requestSeq.current;
|
|
5108
|
+
try {
|
|
5109
|
+
const result = await transport.saveAutoRecharge(input);
|
|
5110
|
+
if (seq !== requestSeq.current) return result;
|
|
5111
|
+
const nextConfig = mergeAutoRechargeConfig(result.config, result.display);
|
|
5112
|
+
autoRechargeCache.set(key, {
|
|
5113
|
+
config: nextConfig,
|
|
5114
|
+
promise: null,
|
|
5115
|
+
timestamp: Date.now()
|
|
5116
|
+
});
|
|
5117
|
+
setConfig(nextConfig);
|
|
5118
|
+
return result;
|
|
5119
|
+
} catch (caught) {
|
|
5120
|
+
const err = caught instanceof Error ? caught : new Error(String(caught));
|
|
5121
|
+
setError(err);
|
|
5122
|
+
throw err;
|
|
5123
|
+
} finally {
|
|
5124
|
+
setSaving(false);
|
|
5125
|
+
}
|
|
5126
|
+
},
|
|
5127
|
+
[_config, key]
|
|
5128
|
+
);
|
|
5129
|
+
const disable = (0, import_react31.useCallback)(async () => {
|
|
5130
|
+
const transport = _config?.transport ?? createHttpTransport(_config);
|
|
5131
|
+
if (!transport.disableAutoRecharge) {
|
|
5132
|
+
throw new Error("disableAutoRecharge is not available on this transport");
|
|
5133
|
+
}
|
|
5134
|
+
setDisabling(true);
|
|
5135
|
+
setError(null);
|
|
5136
|
+
const seq = ++requestSeq.current;
|
|
5137
|
+
try {
|
|
5138
|
+
const result = await transport.disableAutoRecharge();
|
|
5139
|
+
if (seq === requestSeq.current) {
|
|
5140
|
+
setConfig((current) => {
|
|
5141
|
+
const disabledConfig = current ? { ...current, enabled: false } : null;
|
|
5142
|
+
autoRechargeCache.set(key, {
|
|
5143
|
+
config: disabledConfig,
|
|
5144
|
+
promise: null,
|
|
5145
|
+
timestamp: Date.now()
|
|
5146
|
+
});
|
|
5147
|
+
return disabledConfig;
|
|
5148
|
+
});
|
|
5149
|
+
await refresh(true);
|
|
5150
|
+
setConfig((current) => {
|
|
5151
|
+
const disabledConfig = current ? { ...current, enabled: false } : null;
|
|
5152
|
+
autoRechargeCache.set(key, {
|
|
5153
|
+
config: disabledConfig,
|
|
5154
|
+
promise: null,
|
|
5155
|
+
timestamp: Date.now()
|
|
5156
|
+
});
|
|
5157
|
+
return disabledConfig;
|
|
5158
|
+
});
|
|
5159
|
+
}
|
|
5160
|
+
return result;
|
|
5161
|
+
} catch (caught) {
|
|
5162
|
+
const err = caught instanceof Error ? caught : new Error(String(caught));
|
|
5163
|
+
setError(err);
|
|
5164
|
+
throw err;
|
|
5165
|
+
} finally {
|
|
5166
|
+
setDisabling(false);
|
|
5167
|
+
}
|
|
5168
|
+
}, [_config, key, refresh]);
|
|
5169
|
+
return { config, loading, saving, disabling, error, refresh, save, disable };
|
|
5170
|
+
}
|
|
4944
5171
|
|
|
4945
|
-
// src/primitives/
|
|
4946
|
-
var
|
|
5172
|
+
// src/primitives/autoRechargeActivation.ts
|
|
5173
|
+
var defaultSleep = (ms) => new Promise((resolve) => setTimeout(resolve, ms));
|
|
5174
|
+
async function waitForAutoRechargeActivation({
|
|
5175
|
+
refresh,
|
|
5176
|
+
getStatus,
|
|
5177
|
+
attempts = 5,
|
|
5178
|
+
delayMs = 800,
|
|
5179
|
+
sleep = defaultSleep
|
|
5180
|
+
}) {
|
|
5181
|
+
for (let attempt = 0; attempt < attempts; attempt++) {
|
|
5182
|
+
await refresh(true);
|
|
5183
|
+
if (getStatus() === "active") return true;
|
|
5184
|
+
if (attempt < attempts - 1) await sleep(delayMs);
|
|
5185
|
+
}
|
|
5186
|
+
return getStatus() === "active";
|
|
5187
|
+
}
|
|
4947
5188
|
|
|
4948
|
-
// src/primitives/
|
|
4949
|
-
var
|
|
5189
|
+
// src/primitives/setupIntentReturn.ts
|
|
5190
|
+
var SETUP_INTENT_PARAMS = ["setup_intent", "setup_intent_client_secret", "redirect_status"];
|
|
5191
|
+
function readSetupIntentClientSecret(search) {
|
|
5192
|
+
return new URLSearchParams(search).get("setup_intent_client_secret");
|
|
5193
|
+
}
|
|
5194
|
+
function stripSetupIntentParams() {
|
|
5195
|
+
if (typeof window === "undefined") return;
|
|
5196
|
+
const url = new URL(window.location.href);
|
|
5197
|
+
let changed = false;
|
|
5198
|
+
for (const param of SETUP_INTENT_PARAMS) {
|
|
5199
|
+
if (url.searchParams.has(param)) {
|
|
5200
|
+
url.searchParams.delete(param);
|
|
5201
|
+
changed = true;
|
|
5202
|
+
}
|
|
5203
|
+
}
|
|
5204
|
+
if (!changed) return;
|
|
5205
|
+
const query = url.searchParams.toString();
|
|
5206
|
+
window.history.replaceState({}, "", `${url.pathname}${query ? `?${query}` : ""}${url.hash}`);
|
|
5207
|
+
}
|
|
4950
5208
|
|
|
4951
|
-
// src/
|
|
4952
|
-
var
|
|
5209
|
+
// src/utils/credit-estimation.ts
|
|
5210
|
+
var import_core2 = require("@solvapay/core");
|
|
5211
|
+
function estimateCredits(resolvedAmountMajor, currency, creditsPerMinorUnit, displayExchangeRate) {
|
|
5212
|
+
if (resolvedAmountMajor == null || resolvedAmountMajor <= 0) return null;
|
|
5213
|
+
if (creditsPerMinorUnit == null || creditsPerMinorUnit <= 0) return null;
|
|
5214
|
+
const rate = displayExchangeRate ?? 1;
|
|
5215
|
+
const resolvedAmountMinor = Math.round(resolvedAmountMajor * getMinorUnitsPerMajor(currency));
|
|
5216
|
+
return Math.round(resolvedAmountMinor / rate * creditsPerMinorUnit);
|
|
5217
|
+
}
|
|
5218
|
+
function estimateCurrencyMajorFromCredits(credits, currency, creditsPerMinorUnit, displayExchangeRate) {
|
|
5219
|
+
if (credits == null || credits <= 0) return null;
|
|
5220
|
+
if (creditsPerMinorUnit == null || creditsPerMinorUnit <= 0) return null;
|
|
5221
|
+
const rate = displayExchangeRate ?? 1;
|
|
5222
|
+
const displayMinor = (0, import_core2.creditsToDisplayMinorUnits)({
|
|
5223
|
+
credits,
|
|
5224
|
+
creditsPerMinorUnit,
|
|
5225
|
+
displayExchangeRate: rate,
|
|
5226
|
+
displayCurrency: currency
|
|
5227
|
+
});
|
|
5228
|
+
if (displayMinor === null) return null;
|
|
5229
|
+
return displayMinor / getMinorUnitsPerMajor(currency);
|
|
5230
|
+
}
|
|
4953
5231
|
|
|
4954
|
-
// src/
|
|
4955
|
-
var
|
|
4956
|
-
|
|
4957
|
-
|
|
4958
|
-
|
|
5232
|
+
// src/helpers/stripe-minimums.ts
|
|
5233
|
+
var STRIPE_MINIMUM_MINOR = {
|
|
5234
|
+
USD: 50,
|
|
5235
|
+
EUR: 50,
|
|
5236
|
+
GBP: 30,
|
|
5237
|
+
SEK: 300,
|
|
5238
|
+
NOK: 300,
|
|
5239
|
+
DKK: 250,
|
|
5240
|
+
CHF: 50,
|
|
5241
|
+
CAD: 50,
|
|
5242
|
+
AUD: 50,
|
|
5243
|
+
JPY: 50,
|
|
5244
|
+
KRW: 500
|
|
5245
|
+
};
|
|
5246
|
+
var DEFAULT_MINIMUM_MINOR = 50;
|
|
5247
|
+
function getStripeMinimumMinor(currency) {
|
|
5248
|
+
return STRIPE_MINIMUM_MINOR[currency.toUpperCase()] ?? DEFAULT_MINIMUM_MINOR;
|
|
4959
5249
|
}
|
|
4960
5250
|
|
|
4961
|
-
// src/
|
|
4962
|
-
|
|
4963
|
-
|
|
5251
|
+
// src/helpers/auto-recharge-form.ts
|
|
5252
|
+
var DEFAULT_VALIDATION_MESSAGES = {
|
|
5253
|
+
invalidThreshold: "Enter a valid balance threshold.",
|
|
5254
|
+
thresholdTooLow: "Balance threshold must be greater than zero.",
|
|
5255
|
+
minTopupAmount: "Top-up amount must be at least {amount}.",
|
|
5256
|
+
topupBelowThreshold: "Top-up amount must be at least your balance threshold ({amount})."
|
|
5257
|
+
};
|
|
5258
|
+
function amountAnchors(thresholdValue, topupValue, unit = "currency") {
|
|
5259
|
+
return {
|
|
5260
|
+
thresholdBaseValue: thresholdValue,
|
|
5261
|
+
thresholdBaseUnit: unit,
|
|
5262
|
+
topupBaseValue: topupValue,
|
|
5263
|
+
topupBaseUnit: unit
|
|
5264
|
+
};
|
|
4964
5265
|
}
|
|
4965
|
-
function
|
|
4966
|
-
const
|
|
4967
|
-
const
|
|
4968
|
-
|
|
4969
|
-
|
|
4970
|
-
|
|
5266
|
+
function createDefaultAutoRechargeForm(currency, defaultTopupMajor, defaultThresholdMajor) {
|
|
5267
|
+
const topup = defaultTopupMajor != null && defaultTopupMajor > 0 ? String(defaultTopupMajor) : "10";
|
|
5268
|
+
const threshold = defaultThresholdMajor != null && defaultThresholdMajor >= 0 ? String(defaultThresholdMajor) : "5";
|
|
5269
|
+
return {
|
|
5270
|
+
enabled: false,
|
|
5271
|
+
thresholdAmountMajor: threshold,
|
|
5272
|
+
thresholdUnit: "currency",
|
|
5273
|
+
topupAmountMajor: topup,
|
|
5274
|
+
topupUnit: "currency",
|
|
5275
|
+
...amountAnchors(threshold, topup, "currency")
|
|
5276
|
+
};
|
|
4971
5277
|
}
|
|
4972
|
-
function
|
|
4973
|
-
const
|
|
4974
|
-
|
|
4975
|
-
);
|
|
4976
|
-
|
|
4977
|
-
|
|
4978
|
-
|
|
4979
|
-
|
|
5278
|
+
function parsePositiveNumber(value) {
|
|
5279
|
+
const trimmed = value.trim();
|
|
5280
|
+
if (trimmed.length === 0) return null;
|
|
5281
|
+
const parsed = Number(trimmed);
|
|
5282
|
+
if (!Number.isFinite(parsed) || parsed <= 0) return null;
|
|
5283
|
+
return parsed;
|
|
5284
|
+
}
|
|
5285
|
+
function parseNonNegativeNumber(value) {
|
|
5286
|
+
const trimmed = value.trim();
|
|
5287
|
+
if (trimmed.length === 0) return null;
|
|
5288
|
+
const parsed = Number(trimmed);
|
|
5289
|
+
if (!Number.isFinite(parsed) || parsed < 0) return null;
|
|
5290
|
+
return parsed;
|
|
5291
|
+
}
|
|
5292
|
+
function validateAutoRechargeForm(form, currency, conversion, messages = DEFAULT_VALIDATION_MESSAGES) {
|
|
5293
|
+
if (!form.enabled) {
|
|
5294
|
+
return {
|
|
5295
|
+
ok: true,
|
|
5296
|
+
payload: {
|
|
5297
|
+
enabled: false,
|
|
5298
|
+
triggerType: "balance",
|
|
5299
|
+
currency: currency.toUpperCase()
|
|
5300
|
+
}
|
|
5301
|
+
};
|
|
5302
|
+
}
|
|
5303
|
+
const payload = {
|
|
5304
|
+
enabled: true,
|
|
5305
|
+
triggerType: "balance",
|
|
5306
|
+
currency: currency.toUpperCase()
|
|
4980
5307
|
};
|
|
5308
|
+
const minorPerMajor = getMinorUnitsPerMajor(currency);
|
|
5309
|
+
const minMinor = getStripeMinimumMinor(currency);
|
|
5310
|
+
const thresholdRaw = parseNonNegativeNumber(form.thresholdAmountMajor);
|
|
5311
|
+
if (thresholdRaw == null) {
|
|
5312
|
+
return { ok: false, error: messages.invalidThreshold };
|
|
5313
|
+
}
|
|
5314
|
+
if (form.thresholdUnit === "credits") {
|
|
5315
|
+
const major = estimateCurrencyMajorFromCredits(
|
|
5316
|
+
thresholdRaw,
|
|
5317
|
+
currency,
|
|
5318
|
+
conversion?.creditsPerMinorUnit,
|
|
5319
|
+
conversion?.displayExchangeRate
|
|
5320
|
+
);
|
|
5321
|
+
if (major == null) {
|
|
5322
|
+
return { ok: false, error: messages.invalidThreshold };
|
|
5323
|
+
}
|
|
5324
|
+
payload.thresholdAmountMajor = major;
|
|
5325
|
+
} else {
|
|
5326
|
+
payload.thresholdAmountMajor = thresholdRaw;
|
|
5327
|
+
}
|
|
5328
|
+
if (payload.thresholdAmountMajor == null || payload.thresholdAmountMajor <= 0) {
|
|
5329
|
+
return { ok: false, error: messages.thresholdTooLow };
|
|
5330
|
+
}
|
|
5331
|
+
const amountRaw = parsePositiveNumber(form.topupAmountMajor);
|
|
5332
|
+
if (amountRaw == null) {
|
|
5333
|
+
return {
|
|
5334
|
+
ok: false,
|
|
5335
|
+
error: interpolate(messages.minTopupAmount, {
|
|
5336
|
+
amount: formatPrice(minMinor, currency, { free: "" })
|
|
5337
|
+
})
|
|
5338
|
+
};
|
|
5339
|
+
}
|
|
5340
|
+
const amountMajor = form.topupUnit === "credits" ? estimateCurrencyMajorFromCredits(
|
|
5341
|
+
amountRaw,
|
|
5342
|
+
currency,
|
|
5343
|
+
conversion?.creditsPerMinorUnit,
|
|
5344
|
+
conversion?.displayExchangeRate
|
|
5345
|
+
) : amountRaw;
|
|
5346
|
+
if (amountMajor == null || Math.round(amountMajor * minorPerMajor) < minMinor) {
|
|
5347
|
+
return {
|
|
5348
|
+
ok: false,
|
|
5349
|
+
error: interpolate(messages.minTopupAmount, {
|
|
5350
|
+
amount: formatPrice(minMinor, currency, { free: "" })
|
|
5351
|
+
})
|
|
5352
|
+
};
|
|
5353
|
+
}
|
|
5354
|
+
payload.topupAmountMajor = amountMajor;
|
|
5355
|
+
if (amountMajor < payload.thresholdAmountMajor) {
|
|
5356
|
+
return {
|
|
5357
|
+
ok: false,
|
|
5358
|
+
error: interpolate(messages.topupBelowThreshold, {
|
|
5359
|
+
amount: formatPrice(
|
|
5360
|
+
Math.round(payload.thresholdAmountMajor * minorPerMajor),
|
|
5361
|
+
currency,
|
|
5362
|
+
{ free: "" }
|
|
5363
|
+
)
|
|
5364
|
+
})
|
|
5365
|
+
};
|
|
5366
|
+
}
|
|
5367
|
+
return { ok: true, payload };
|
|
4981
5368
|
}
|
|
4982
|
-
function
|
|
4983
|
-
|
|
4984
|
-
|
|
4985
|
-
|
|
5369
|
+
function triggerAmountMajorFromConfig(config) {
|
|
5370
|
+
const topupCurrency = config.topup.currency.toUpperCase();
|
|
5371
|
+
const minorPerMajor = getMinorUnitsPerMajor(topupCurrency);
|
|
5372
|
+
const { thresholdAmountMinor } = config.trigger;
|
|
5373
|
+
if (!Number.isFinite(thresholdAmountMinor) || thresholdAmountMinor < 0) {
|
|
5374
|
+
return null;
|
|
4986
5375
|
}
|
|
4987
|
-
|
|
4988
|
-
|
|
4989
|
-
|
|
4990
|
-
const
|
|
4991
|
-
|
|
5376
|
+
return thresholdAmountMinor / minorPerMajor;
|
|
5377
|
+
}
|
|
5378
|
+
function configToForm(config, currency) {
|
|
5379
|
+
const base = createDefaultAutoRechargeForm(currency);
|
|
5380
|
+
const display = config.display;
|
|
5381
|
+
if (display?.thresholdAmountMajor != null && display.topupAmountMajor != null) {
|
|
5382
|
+
const thresholdStr2 = String(Math.max(0, display.thresholdAmountMajor));
|
|
5383
|
+
const topupStr2 = String(display.topupAmountMajor);
|
|
5384
|
+
return {
|
|
5385
|
+
...base,
|
|
5386
|
+
enabled: config.enabled,
|
|
5387
|
+
thresholdAmountMajor: thresholdStr2,
|
|
5388
|
+
topupAmountMajor: topupStr2,
|
|
5389
|
+
...amountAnchors(thresholdStr2, topupStr2, "currency")
|
|
5390
|
+
};
|
|
5391
|
+
}
|
|
5392
|
+
const thresholdMajor = triggerAmountMajorFromConfig(config);
|
|
5393
|
+
const thresholdStr = thresholdMajor != null ? String(Math.max(0, thresholdMajor)) : "0";
|
|
5394
|
+
const topupStr = String(config.topup.amountMinor / getMinorUnitsPerMajor(currency));
|
|
5395
|
+
return {
|
|
5396
|
+
...base,
|
|
5397
|
+
enabled: config.enabled,
|
|
5398
|
+
thresholdAmountMajor: thresholdStr,
|
|
5399
|
+
topupAmountMajor: topupStr,
|
|
5400
|
+
...amountAnchors(thresholdStr, topupStr, "currency")
|
|
5401
|
+
};
|
|
4992
5402
|
}
|
|
4993
|
-
function
|
|
4994
|
-
const
|
|
4995
|
-
|
|
4996
|
-
|
|
5403
|
+
function formatAmountWithUnit(value, unit, currency) {
|
|
5404
|
+
const num = Number(value);
|
|
5405
|
+
if (!value || !Number.isFinite(num)) return "\u2014";
|
|
5406
|
+
if (unit === "credits") {
|
|
5407
|
+
return `${new Intl.NumberFormat().format(num)} credits`;
|
|
5408
|
+
}
|
|
5409
|
+
return formatPrice(Math.round(num * getMinorUnitsPerMajor(currency)), currency, { free: "" });
|
|
4997
5410
|
}
|
|
4998
|
-
function
|
|
4999
|
-
|
|
5000
|
-
const
|
|
5001
|
-
|
|
5002
|
-
|
|
5411
|
+
function buildSummaryLine(form, currency) {
|
|
5412
|
+
if (!form.enabled) return null;
|
|
5413
|
+
const thresholdDisplay = formatAmountWithUnit(
|
|
5414
|
+
form.thresholdAmountMajor,
|
|
5415
|
+
form.thresholdUnit,
|
|
5416
|
+
currency
|
|
5417
|
+
);
|
|
5418
|
+
const fixedDisplay = formatAmountWithUnit(form.topupAmountMajor, form.topupUnit, currency);
|
|
5419
|
+
return `When my balance falls below ${thresholdDisplay}, add ${fixedDisplay}.`;
|
|
5420
|
+
}
|
|
5421
|
+
function convertAmountForUnitFlip(value, fromUnit, toUnit, currency, creditsPerMinorUnit, displayExchangeRate) {
|
|
5422
|
+
if (fromUnit === toUnit) return value;
|
|
5423
|
+
const parsed = Number(value);
|
|
5424
|
+
if (!Number.isFinite(parsed) || parsed <= 0) return value;
|
|
5425
|
+
if (fromUnit === "currency" && toUnit === "credits") {
|
|
5426
|
+
const credits = estimateCredits(parsed, currency, creditsPerMinorUnit, displayExchangeRate);
|
|
5427
|
+
return credits != null ? String(credits) : value;
|
|
5003
5428
|
}
|
|
5004
|
-
|
|
5429
|
+
const major = estimateCurrencyMajorFromCredits(
|
|
5430
|
+
parsed,
|
|
5431
|
+
currency,
|
|
5432
|
+
creditsPerMinorUnit,
|
|
5433
|
+
displayExchangeRate
|
|
5434
|
+
);
|
|
5435
|
+
return major != null ? String(major) : value;
|
|
5005
5436
|
}
|
|
5006
|
-
function
|
|
5007
|
-
if (
|
|
5008
|
-
|
|
5009
|
-
|
|
5010
|
-
|
|
5011
|
-
|
|
5012
|
-
|
|
5437
|
+
function flipUnitValue(anchor, targetUnit, currency, creditsPerMinorUnit, displayExchangeRate) {
|
|
5438
|
+
if (targetUnit === anchor.unit) {
|
|
5439
|
+
return { value: anchor.value, unit: anchor.unit };
|
|
5440
|
+
}
|
|
5441
|
+
const converted = convertAmountForUnitFlip(
|
|
5442
|
+
anchor.value,
|
|
5443
|
+
anchor.unit,
|
|
5444
|
+
targetUnit,
|
|
5445
|
+
currency,
|
|
5446
|
+
creditsPerMinorUnit,
|
|
5447
|
+
displayExchangeRate
|
|
5448
|
+
);
|
|
5449
|
+
return { value: converted, unit: targetUnit };
|
|
5013
5450
|
}
|
|
5014
5451
|
|
|
5015
|
-
// src/
|
|
5016
|
-
|
|
5017
|
-
|
|
5018
|
-
|
|
5019
|
-
|
|
5020
|
-
|
|
5021
|
-
|
|
5022
|
-
|
|
5023
|
-
|
|
5024
|
-
|
|
5025
|
-
|
|
5026
|
-
|
|
5027
|
-
|
|
5028
|
-
|
|
5029
|
-
|
|
5030
|
-
|
|
5031
|
-
|
|
5032
|
-
|
|
5033
|
-
|
|
5034
|
-
|
|
5035
|
-
|
|
5036
|
-
|
|
5037
|
-
|
|
5038
|
-
|
|
5039
|
-
|
|
5040
|
-
|
|
5041
|
-
|
|
5042
|
-
|
|
5043
|
-
|
|
5044
|
-
|
|
5045
|
-
|
|
5046
|
-
|
|
5047
|
-
|
|
5048
|
-
|
|
5049
|
-
|
|
5050
|
-
|
|
5051
|
-
|
|
5052
|
-
|
|
5053
|
-
|
|
5054
|
-
|
|
5055
|
-
);
|
|
5056
|
-
|
|
5057
|
-
const
|
|
5058
|
-
const
|
|
5059
|
-
const
|
|
5060
|
-
const
|
|
5061
|
-
const
|
|
5062
|
-
const
|
|
5063
|
-
const
|
|
5064
|
-
const
|
|
5065
|
-
const
|
|
5066
|
-
const
|
|
5067
|
-
|
|
5452
|
+
// src/primitives/AutoRecharge.tsx
|
|
5453
|
+
var import_jsx_runtime22 = require("react/jsx-runtime");
|
|
5454
|
+
var AutoRechargeContext = (0, import_react32.createContext)(null);
|
|
5455
|
+
function useAutoRechargeCtx(part) {
|
|
5456
|
+
const ctx = (0, import_react32.useContext)(AutoRechargeContext);
|
|
5457
|
+
if (!ctx) {
|
|
5458
|
+
throw new Error(`AutoRecharge.${part} must be rendered inside <AutoRecharge.Root>.`);
|
|
5459
|
+
}
|
|
5460
|
+
return ctx;
|
|
5461
|
+
}
|
|
5462
|
+
function getCurrencySymbol2(currency) {
|
|
5463
|
+
try {
|
|
5464
|
+
const parts = new Intl.NumberFormat("en", { style: "currency", currency }).formatToParts(0);
|
|
5465
|
+
const sym = parts.find((p) => p.type === "currency");
|
|
5466
|
+
return sym?.value ?? currency.toUpperCase();
|
|
5467
|
+
} catch {
|
|
5468
|
+
return currency.toUpperCase();
|
|
5469
|
+
}
|
|
5470
|
+
}
|
|
5471
|
+
var stripePromiseCache3 = /* @__PURE__ */ new Map();
|
|
5472
|
+
function getStripeCacheKey3(publishableKey, accountId) {
|
|
5473
|
+
return accountId ? `${publishableKey}:${accountId}` : publishableKey;
|
|
5474
|
+
}
|
|
5475
|
+
var Root10 = (0, import_react32.forwardRef)(function AutoRechargeRoot({
|
|
5476
|
+
currency = "USD",
|
|
5477
|
+
defaultThresholdAmountMajor,
|
|
5478
|
+
defaultTopupAmountMajor,
|
|
5479
|
+
open: openProp,
|
|
5480
|
+
defaultOpen = false,
|
|
5481
|
+
onOpenChange,
|
|
5482
|
+
onSetupRequired,
|
|
5483
|
+
onSaved,
|
|
5484
|
+
onDisabled,
|
|
5485
|
+
deferCardSetup = false,
|
|
5486
|
+
onPendingConfig,
|
|
5487
|
+
asChild,
|
|
5488
|
+
children,
|
|
5489
|
+
className,
|
|
5490
|
+
...rest
|
|
5491
|
+
}, forwardedRef) {
|
|
5492
|
+
const solva = (0, import_react32.useContext)(SolvaPayContext);
|
|
5493
|
+
if (!solva) throw new MissingProviderError("AutoRecharge");
|
|
5494
|
+
const autoRecharge = useAutoRecharge();
|
|
5495
|
+
const { creditsPerMinorUnit, displayExchangeRate } = useBalance();
|
|
5496
|
+
const copy = useCopy();
|
|
5497
|
+
const titleId = (0, import_react32.useId)();
|
|
5498
|
+
const triggerRef = (0, import_react32.useRef)(null);
|
|
5499
|
+
const defaultTopup = defaultTopupAmountMajor ?? defaultThresholdAmountMajor ?? void 0;
|
|
5500
|
+
const [uncontrolledOpen, setUncontrolledOpen] = (0, import_react32.useState)(defaultOpen);
|
|
5501
|
+
const isControlled = openProp !== void 0;
|
|
5502
|
+
const open = isControlled ? openProp : uncontrolledOpen;
|
|
5503
|
+
const setOpen = (0, import_react32.useCallback)(
|
|
5504
|
+
(next) => {
|
|
5505
|
+
if (!isControlled) {
|
|
5506
|
+
setUncontrolledOpen(next);
|
|
5507
|
+
}
|
|
5508
|
+
onOpenChange?.(next);
|
|
5509
|
+
},
|
|
5510
|
+
[isControlled, onOpenChange]
|
|
5511
|
+
);
|
|
5512
|
+
const registerTriggerRef = (0, import_react32.useCallback)((node) => {
|
|
5513
|
+
triggerRef.current = node;
|
|
5514
|
+
}, []);
|
|
5515
|
+
const focusTrigger = (0, import_react32.useCallback)(() => {
|
|
5516
|
+
triggerRef.current?.focus();
|
|
5517
|
+
}, []);
|
|
5518
|
+
const [form, setForm] = (0, import_react32.useState)(
|
|
5519
|
+
() => autoRecharge.config ? configToForm(autoRecharge.config, currency) : createDefaultAutoRechargeForm(currency, defaultTopup)
|
|
5520
|
+
);
|
|
5521
|
+
const [validationError, setValidationError] = (0, import_react32.useState)(null);
|
|
5522
|
+
const [statusMessage, setStatusMessage] = (0, import_react32.useState)(null);
|
|
5523
|
+
const [setup, setSetup] = (0, import_react32.useState)(null);
|
|
5524
|
+
const latestConfigRef = (0, import_react32.useRef)(autoRecharge.config);
|
|
5525
|
+
(0, import_react32.useEffect)(() => {
|
|
5526
|
+
latestConfigRef.current = autoRecharge.config;
|
|
5527
|
+
}, [autoRecharge.config]);
|
|
5528
|
+
(0, import_react32.useEffect)(() => {
|
|
5529
|
+
if (autoRecharge.config) {
|
|
5530
|
+
setForm(configToForm(autoRecharge.config, currency));
|
|
5531
|
+
}
|
|
5532
|
+
}, [autoRecharge.config, currency]);
|
|
5533
|
+
const canToggleUnits = creditsPerMinorUnit != null && creditsPerMinorUnit > 0;
|
|
5534
|
+
const rate = displayExchangeRate ?? 1;
|
|
5535
|
+
const isApproximate = rate !== 1;
|
|
5536
|
+
const emitValidation = (0, import_react32.useCallback)(
|
|
5537
|
+
(next) => {
|
|
5538
|
+
const result = validateAutoRechargeForm(
|
|
5539
|
+
next,
|
|
5540
|
+
currency,
|
|
5541
|
+
{ creditsPerMinorUnit, displayExchangeRate },
|
|
5542
|
+
copy.autoRecharge
|
|
5543
|
+
);
|
|
5544
|
+
if (!result.ok) {
|
|
5545
|
+
setValidationError(result.error);
|
|
5546
|
+
return null;
|
|
5547
|
+
}
|
|
5548
|
+
setValidationError(null);
|
|
5549
|
+
return result.payload;
|
|
5550
|
+
},
|
|
5551
|
+
[currency, creditsPerMinorUnit, displayExchangeRate, copy.autoRecharge]
|
|
5552
|
+
);
|
|
5553
|
+
const updateForm = (0, import_react32.useCallback)(
|
|
5554
|
+
(patch) => {
|
|
5555
|
+
setForm((prev) => {
|
|
5556
|
+
const next = { ...prev, ...patch };
|
|
5557
|
+
emitValidation(next);
|
|
5558
|
+
return next;
|
|
5559
|
+
});
|
|
5560
|
+
},
|
|
5561
|
+
[emitValidation]
|
|
5562
|
+
);
|
|
5563
|
+
const resetForm = (0, import_react32.useCallback)(() => {
|
|
5564
|
+
if (autoRecharge.config) {
|
|
5565
|
+
setForm(configToForm(autoRecharge.config, currency));
|
|
5566
|
+
} else {
|
|
5567
|
+
setForm(createDefaultAutoRechargeForm(currency, defaultTopup));
|
|
5568
|
+
}
|
|
5569
|
+
setValidationError(null);
|
|
5570
|
+
}, [autoRecharge.config, currency, defaultTopup]);
|
|
5571
|
+
const flipUnit = (0, import_react32.useCallback)(
|
|
5572
|
+
(valueKey, unitKey, baseValueKey, baseUnitKey, currentUnit) => {
|
|
5573
|
+
const nextUnit = currentUnit === "currency" ? "credits" : "currency";
|
|
5574
|
+
setForm((prev) => {
|
|
5575
|
+
const anchor = { value: prev[baseValueKey], unit: prev[baseUnitKey] };
|
|
5576
|
+
const flipped = flipUnitValue(
|
|
5577
|
+
anchor,
|
|
5578
|
+
nextUnit,
|
|
5579
|
+
currency,
|
|
5580
|
+
creditsPerMinorUnit,
|
|
5581
|
+
displayExchangeRate
|
|
5582
|
+
);
|
|
5583
|
+
const next = {
|
|
5584
|
+
...prev,
|
|
5585
|
+
[unitKey]: flipped.unit,
|
|
5586
|
+
[valueKey]: flipped.value
|
|
5587
|
+
};
|
|
5588
|
+
emitValidation(next);
|
|
5589
|
+
return next;
|
|
5590
|
+
});
|
|
5591
|
+
},
|
|
5592
|
+
[currency, creditsPerMinorUnit, displayExchangeRate, emitValidation]
|
|
5593
|
+
);
|
|
5594
|
+
const fixedTopupHint = (0, import_react32.useMemo)(() => {
|
|
5595
|
+
const parsed = Number(form.topupAmountMajor);
|
|
5596
|
+
if (!Number.isFinite(parsed) || parsed <= 0) return null;
|
|
5597
|
+
if (form.topupUnit === "currency") {
|
|
5598
|
+
const credits = estimateCredits(parsed, currency, creditsPerMinorUnit, displayExchangeRate);
|
|
5599
|
+
if (credits == null) return null;
|
|
5600
|
+
return { credits, approximate: isApproximate };
|
|
5601
|
+
}
|
|
5602
|
+
const major = estimateCurrencyMajorFromCredits(
|
|
5603
|
+
parsed,
|
|
5604
|
+
currency,
|
|
5605
|
+
creditsPerMinorUnit,
|
|
5606
|
+
displayExchangeRate
|
|
5607
|
+
);
|
|
5608
|
+
if (major == null) return null;
|
|
5609
|
+
return { major, approximate: isApproximate };
|
|
5610
|
+
}, [
|
|
5611
|
+
form.topupAmountMajor,
|
|
5612
|
+
form.topupUnit,
|
|
5613
|
+
currency,
|
|
5614
|
+
creditsPerMinorUnit,
|
|
5615
|
+
displayExchangeRate,
|
|
5616
|
+
isApproximate
|
|
5617
|
+
]);
|
|
5618
|
+
const summaryLine = (0, import_react32.useMemo)(() => buildSummaryLine(form, currency), [form, currency]);
|
|
5619
|
+
const savedSummaryLine = (0, import_react32.useMemo)(() => {
|
|
5620
|
+
if (!autoRecharge.config?.enabled) return null;
|
|
5621
|
+
return buildSummaryLine(
|
|
5622
|
+
configToForm(autoRecharge.config, currency),
|
|
5623
|
+
currency
|
|
5624
|
+
);
|
|
5625
|
+
}, [autoRecharge.config, currency]);
|
|
5626
|
+
const save = (0, import_react32.useCallback)(async () => {
|
|
5627
|
+
const payload = emitValidation(form);
|
|
5628
|
+
if (!payload) return;
|
|
5629
|
+
const saveInput = deferCardSetup ? { ...payload, deferSetupIntent: true } : payload;
|
|
5630
|
+
const result = await autoRecharge.save(saveInput);
|
|
5631
|
+
if (result.setupClientSecret) {
|
|
5632
|
+
setSetup(result);
|
|
5633
|
+
setStatusMessage(copy.autoRecharge.setupRequiredMessage);
|
|
5634
|
+
await onSetupRequired?.(result);
|
|
5635
|
+
return;
|
|
5636
|
+
}
|
|
5637
|
+
setSetup(null);
|
|
5638
|
+
if (deferCardSetup) {
|
|
5639
|
+
await onPendingConfig?.(payload);
|
|
5640
|
+
}
|
|
5641
|
+
setStatusMessage(
|
|
5642
|
+
payload.enabled ? copy.autoRecharge.savedMessage : copy.autoRecharge.disabledMessage
|
|
5643
|
+
);
|
|
5644
|
+
setOpen(false);
|
|
5645
|
+
await onSaved?.(result);
|
|
5646
|
+
}, [
|
|
5647
|
+
autoRecharge,
|
|
5648
|
+
copy.autoRecharge,
|
|
5649
|
+
deferCardSetup,
|
|
5650
|
+
emitValidation,
|
|
5651
|
+
form,
|
|
5652
|
+
onPendingConfig,
|
|
5653
|
+
onSaved,
|
|
5654
|
+
onSetupRequired,
|
|
5655
|
+
setOpen
|
|
5656
|
+
]);
|
|
5657
|
+
const disable = (0, import_react32.useCallback)(async () => {
|
|
5658
|
+
await autoRecharge.disable();
|
|
5659
|
+
setStatusMessage(copy.autoRecharge.disabledMessage);
|
|
5660
|
+
setSetup(null);
|
|
5661
|
+
await onDisabled?.();
|
|
5662
|
+
}, [autoRecharge, copy.autoRecharge, onDisabled]);
|
|
5663
|
+
const completeSetup = (0, import_react32.useCallback)(async () => {
|
|
5664
|
+
const activated = await waitForAutoRechargeActivation({
|
|
5665
|
+
refresh: autoRecharge.refresh,
|
|
5666
|
+
getStatus: () => latestConfigRef.current?.status
|
|
5667
|
+
});
|
|
5668
|
+
setSetup(null);
|
|
5669
|
+
if (!form.enabled) return;
|
|
5670
|
+
if (activated) {
|
|
5671
|
+
setStatusMessage(copy.autoRecharge.savedMessage);
|
|
5672
|
+
setOpen(false);
|
|
5673
|
+
} else {
|
|
5674
|
+
setStatusMessage(copy.autoRecharge.setupAwaitingConfirmation);
|
|
5675
|
+
}
|
|
5676
|
+
}, [autoRecharge, copy.autoRecharge, form.enabled, setOpen]);
|
|
5677
|
+
const dataState = setup ? "setup" : autoRecharge.error ? "error" : autoRecharge.loading ? "loading" : autoRecharge.saving ? "saving" : autoRecharge.disabling ? "disabling" : "idle";
|
|
5678
|
+
const ctx = (0, import_react32.useMemo)(
|
|
5679
|
+
() => ({
|
|
5680
|
+
form,
|
|
5681
|
+
updateForm,
|
|
5682
|
+
resetForm,
|
|
5683
|
+
validationError,
|
|
5684
|
+
currency,
|
|
5685
|
+
config: autoRecharge.config,
|
|
5686
|
+
loading: autoRecharge.loading,
|
|
5687
|
+
saving: autoRecharge.saving,
|
|
5688
|
+
disabling: autoRecharge.disabling,
|
|
5689
|
+
error: autoRecharge.error,
|
|
5690
|
+
statusMessage,
|
|
5691
|
+
setup,
|
|
5692
|
+
dataState,
|
|
5693
|
+
creditsPerMinorUnit,
|
|
5694
|
+
displayExchangeRate,
|
|
5695
|
+
canToggleUnits,
|
|
5696
|
+
isApproximate,
|
|
5697
|
+
summaryLine,
|
|
5698
|
+
savedSummaryLine,
|
|
5699
|
+
deferCardSetup,
|
|
5700
|
+
fixedTopupHint: fixedTopupHint && "credits" in fixedTopupHint ? String(fixedTopupHint.credits) : fixedTopupHint && "major" in fixedTopupHint ? formatPrice(
|
|
5701
|
+
Math.round(fixedTopupHint.major * getMinorUnitsPerMajor(currency)),
|
|
5702
|
+
currency,
|
|
5703
|
+
{ free: "" }
|
|
5704
|
+
) : null,
|
|
5705
|
+
open,
|
|
5706
|
+
setOpen,
|
|
5707
|
+
titleId,
|
|
5708
|
+
registerTriggerRef,
|
|
5709
|
+
focusTrigger,
|
|
5710
|
+
save,
|
|
5711
|
+
disable,
|
|
5712
|
+
completeSetup,
|
|
5713
|
+
flipUnit
|
|
5714
|
+
}),
|
|
5715
|
+
[
|
|
5716
|
+
form,
|
|
5717
|
+
updateForm,
|
|
5718
|
+
resetForm,
|
|
5719
|
+
validationError,
|
|
5720
|
+
currency,
|
|
5721
|
+
autoRecharge.config,
|
|
5722
|
+
autoRecharge.loading,
|
|
5723
|
+
autoRecharge.saving,
|
|
5724
|
+
autoRecharge.disabling,
|
|
5725
|
+
autoRecharge.error,
|
|
5726
|
+
statusMessage,
|
|
5727
|
+
setup,
|
|
5728
|
+
dataState,
|
|
5729
|
+
creditsPerMinorUnit,
|
|
5730
|
+
displayExchangeRate,
|
|
5731
|
+
canToggleUnits,
|
|
5732
|
+
isApproximate,
|
|
5733
|
+
summaryLine,
|
|
5734
|
+
savedSummaryLine,
|
|
5735
|
+
deferCardSetup,
|
|
5736
|
+
fixedTopupHint,
|
|
5737
|
+
open,
|
|
5738
|
+
setOpen,
|
|
5739
|
+
titleId,
|
|
5740
|
+
registerTriggerRef,
|
|
5741
|
+
focusTrigger,
|
|
5742
|
+
save,
|
|
5743
|
+
disable,
|
|
5744
|
+
completeSetup,
|
|
5745
|
+
flipUnit
|
|
5746
|
+
]
|
|
5747
|
+
);
|
|
5748
|
+
const Comp = asChild ? Slot : "section";
|
|
5749
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(AutoRechargeContext.Provider, { value: ctx, children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5750
|
+
Comp,
|
|
5751
|
+
{
|
|
5752
|
+
ref: forwardedRef,
|
|
5753
|
+
className,
|
|
5754
|
+
"aria-label": "Automatic credit top-up",
|
|
5755
|
+
"data-solvapay-auto-recharge": "",
|
|
5756
|
+
"data-state": dataState,
|
|
5757
|
+
...rest,
|
|
5758
|
+
children
|
|
5759
|
+
}
|
|
5760
|
+
) });
|
|
5761
|
+
});
|
|
5762
|
+
var Loading7 = (0, import_react32.forwardRef)(
|
|
5763
|
+
function AutoRechargeLoading({ className, children, ...rest }, forwardedRef) {
|
|
5764
|
+
const ctx = useAutoRechargeCtx("Loading");
|
|
5765
|
+
if (!ctx.loading) return null;
|
|
5766
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("p", { ref: forwardedRef, className, "data-solvapay-auto-recharge-loading": "", ...rest, children: children ?? /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(import_jsx_runtime22.Fragment, { children: [
|
|
5767
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Spinner, { size: "sm" }),
|
|
5768
|
+
" Loading auto-recharge settings\u2026"
|
|
5769
|
+
] }) });
|
|
5770
|
+
}
|
|
5771
|
+
);
|
|
5772
|
+
var Card2 = (0, import_react32.forwardRef)(function AutoRechargeCard({ className, children, ...rest }, forwardedRef) {
|
|
5773
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5774
|
+
"section",
|
|
5775
|
+
{
|
|
5776
|
+
ref: forwardedRef,
|
|
5777
|
+
className,
|
|
5778
|
+
"data-solvapay-auto-recharge-card": "",
|
|
5779
|
+
...rest,
|
|
5780
|
+
children
|
|
5781
|
+
}
|
|
5782
|
+
);
|
|
5783
|
+
});
|
|
5784
|
+
var CardHeading = (0, import_react32.forwardRef)(
|
|
5785
|
+
function AutoRechargeCardHeading({ className, children, ...rest }, forwardedRef) {
|
|
5786
|
+
const copy = useCopy();
|
|
5787
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5788
|
+
"h3",
|
|
5789
|
+
{
|
|
5790
|
+
ref: forwardedRef,
|
|
5791
|
+
className,
|
|
5792
|
+
"data-solvapay-auto-recharge-card-heading": "",
|
|
5793
|
+
...rest,
|
|
5794
|
+
children: children ?? copy.autoRecharge.heading
|
|
5795
|
+
}
|
|
5796
|
+
);
|
|
5797
|
+
}
|
|
5798
|
+
);
|
|
5799
|
+
var CardSummary = (0, import_react32.forwardRef)(
|
|
5800
|
+
function AutoRechargeCardSummary({ className, children, ...rest }, forwardedRef) {
|
|
5801
|
+
const ctx = useAutoRechargeCtx("CardSummary");
|
|
5802
|
+
const copy = useCopy();
|
|
5803
|
+
const text = ctx.savedSummaryLine ?? copy.autoRecharge.notConfiguredHint;
|
|
5804
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5805
|
+
"p",
|
|
5806
|
+
{
|
|
5807
|
+
ref: forwardedRef,
|
|
5808
|
+
className,
|
|
5809
|
+
"data-solvapay-auto-recharge-card-summary": "",
|
|
5810
|
+
...rest,
|
|
5811
|
+
children: children ?? text
|
|
5812
|
+
}
|
|
5813
|
+
);
|
|
5814
|
+
}
|
|
5815
|
+
);
|
|
5816
|
+
var Trigger = (0, import_react32.forwardRef)(function AutoRechargeTrigger({ asChild, onClick, children, className, ...rest }, forwardedRef) {
|
|
5817
|
+
const ctx = useAutoRechargeCtx("Trigger");
|
|
5818
|
+
const copy = useCopy();
|
|
5819
|
+
const hasExistingConfig = Boolean(ctx.config?.enabled);
|
|
5820
|
+
const label = hasExistingConfig ? copy.autoRecharge.modifyTriggerLabel : copy.autoRecharge.setupTriggerLabel;
|
|
5821
|
+
const setRefs = (node) => {
|
|
5822
|
+
ctx.registerTriggerRef(node);
|
|
5823
|
+
if (typeof forwardedRef === "function") {
|
|
5824
|
+
forwardedRef(node);
|
|
5825
|
+
} else if (forwardedRef) {
|
|
5826
|
+
forwardedRef.current = node;
|
|
5827
|
+
}
|
|
5828
|
+
};
|
|
5829
|
+
const commonProps = {
|
|
5830
|
+
"data-solvapay-auto-recharge-trigger": "",
|
|
5831
|
+
type: "button",
|
|
5832
|
+
"aria-haspopup": "dialog",
|
|
5833
|
+
"aria-expanded": ctx.open,
|
|
5834
|
+
disabled: ctx.loading,
|
|
5835
|
+
onClick: composeEventHandlers(onClick, (event) => {
|
|
5836
|
+
event.preventDefault();
|
|
5837
|
+
ctx.resetForm();
|
|
5838
|
+
ctx.setOpen(true);
|
|
5839
|
+
}),
|
|
5840
|
+
className,
|
|
5841
|
+
...rest
|
|
5842
|
+
};
|
|
5843
|
+
if (asChild) {
|
|
5844
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Slot, { ref: setRefs, ...commonProps, children: children ?? label });
|
|
5845
|
+
}
|
|
5846
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("button", { ref: setRefs, ...commonProps, children: children ?? label });
|
|
5847
|
+
});
|
|
5848
|
+
var Overlay = (0, import_react32.forwardRef)(
|
|
5849
|
+
function AutoRechargeOverlay({ onClick, className, ...rest }, forwardedRef) {
|
|
5850
|
+
const ctx = useAutoRechargeCtx("Overlay");
|
|
5851
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5852
|
+
"div",
|
|
5853
|
+
{
|
|
5854
|
+
ref: forwardedRef,
|
|
5855
|
+
className,
|
|
5856
|
+
"data-solvapay-auto-recharge-overlay": "",
|
|
5857
|
+
"aria-hidden": "true",
|
|
5858
|
+
onClick: composeEventHandlers(onClick, () => {
|
|
5859
|
+
ctx.resetForm();
|
|
5860
|
+
ctx.setOpen(false);
|
|
5861
|
+
ctx.focusTrigger();
|
|
5862
|
+
}),
|
|
5863
|
+
...rest
|
|
5864
|
+
}
|
|
5865
|
+
);
|
|
5866
|
+
}
|
|
5867
|
+
);
|
|
5868
|
+
var Content = (0, import_react32.forwardRef)(function AutoRechargeContent({ className, children, ...rest }, forwardedRef) {
|
|
5869
|
+
const ctx = useAutoRechargeCtx("Content");
|
|
5870
|
+
const panelRef = (0, import_react32.useRef)(null);
|
|
5871
|
+
(0, import_react32.useEffect)(() => {
|
|
5872
|
+
if (!ctx.open) return;
|
|
5873
|
+
const handleKeyDown = (event) => {
|
|
5874
|
+
if (event.key === "Escape") {
|
|
5875
|
+
ctx.resetForm();
|
|
5876
|
+
ctx.setOpen(false);
|
|
5877
|
+
ctx.focusTrigger();
|
|
5878
|
+
}
|
|
5879
|
+
};
|
|
5880
|
+
document.addEventListener("keydown", handleKeyDown);
|
|
5881
|
+
const focusTarget = panelRef.current?.querySelector(
|
|
5882
|
+
'button:not([disabled]), input:not([disabled]), [href], [tabindex]:not([tabindex="-1"])'
|
|
5883
|
+
);
|
|
5884
|
+
focusTarget?.focus();
|
|
5885
|
+
return () => {
|
|
5886
|
+
document.removeEventListener("keydown", handleKeyDown);
|
|
5887
|
+
};
|
|
5888
|
+
}, [ctx.open, ctx.resetForm, ctx.setOpen, ctx.focusTrigger]);
|
|
5889
|
+
if (!ctx.open || typeof document === "undefined") return null;
|
|
5890
|
+
return (0, import_react_dom.createPortal)(
|
|
5891
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("div", { "data-solvapay-auto-recharge-portal": "", children: [
|
|
5892
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Overlay, {}),
|
|
5893
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5894
|
+
"div",
|
|
5895
|
+
{
|
|
5896
|
+
ref: (node) => {
|
|
5897
|
+
panelRef.current = node;
|
|
5898
|
+
if (typeof forwardedRef === "function") {
|
|
5899
|
+
forwardedRef(node);
|
|
5900
|
+
} else if (forwardedRef) {
|
|
5901
|
+
forwardedRef.current = node;
|
|
5902
|
+
}
|
|
5903
|
+
},
|
|
5904
|
+
role: "dialog",
|
|
5905
|
+
"aria-modal": "true",
|
|
5906
|
+
"aria-labelledby": ctx.titleId,
|
|
5907
|
+
className,
|
|
5908
|
+
"data-solvapay-auto-recharge-content": "",
|
|
5909
|
+
...rest,
|
|
5910
|
+
children
|
|
5911
|
+
}
|
|
5912
|
+
)
|
|
5913
|
+
] }),
|
|
5914
|
+
document.body
|
|
5915
|
+
);
|
|
5916
|
+
});
|
|
5917
|
+
var Title = (0, import_react32.forwardRef)(
|
|
5918
|
+
function AutoRechargeTitle({ className, children, ...rest }, forwardedRef) {
|
|
5919
|
+
const ctx = useAutoRechargeCtx("Title");
|
|
5920
|
+
const copy = useCopy();
|
|
5921
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5922
|
+
"h2",
|
|
5923
|
+
{
|
|
5924
|
+
ref: forwardedRef,
|
|
5925
|
+
id: ctx.titleId,
|
|
5926
|
+
className,
|
|
5927
|
+
"data-solvapay-auto-recharge-title": "",
|
|
5928
|
+
...rest,
|
|
5929
|
+
children: children ?? copy.autoRecharge.settingsHeading
|
|
5930
|
+
}
|
|
5931
|
+
);
|
|
5932
|
+
}
|
|
5933
|
+
);
|
|
5934
|
+
var EnableQuestion = (0, import_react32.forwardRef)(
|
|
5935
|
+
function AutoRechargeEnableQuestion({ className, children, ...rest }, forwardedRef) {
|
|
5936
|
+
const copy = useCopy();
|
|
5937
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("p", { ref: forwardedRef, className, "data-solvapay-auto-recharge-question": "", ...rest, children: children ?? copy.autoRecharge.enableQuestion });
|
|
5938
|
+
}
|
|
5939
|
+
);
|
|
5940
|
+
var EnableSentence = (0, import_react32.forwardRef)(
|
|
5941
|
+
function AutoRechargeEnableSentence({ className, children, ...rest }, forwardedRef) {
|
|
5942
|
+
const copy = useCopy();
|
|
5943
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5944
|
+
"label",
|
|
5945
|
+
{
|
|
5946
|
+
ref: forwardedRef,
|
|
5947
|
+
className,
|
|
5948
|
+
"data-solvapay-auto-recharge-enable-sentence": "",
|
|
5949
|
+
...rest,
|
|
5950
|
+
children: children ?? copy.autoRecharge.enableSentence
|
|
5951
|
+
}
|
|
5952
|
+
);
|
|
5953
|
+
}
|
|
5954
|
+
);
|
|
5955
|
+
var EnableRow = (0, import_react32.forwardRef)(
|
|
5956
|
+
function AutoRechargeEnableRow({ className, children, ...rest }, forwardedRef) {
|
|
5957
|
+
const enableId = (0, import_react32.useId)();
|
|
5958
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5959
|
+
"div",
|
|
5960
|
+
{
|
|
5961
|
+
ref: forwardedRef,
|
|
5962
|
+
className,
|
|
5963
|
+
"data-solvapay-auto-recharge-enable-row": "",
|
|
5964
|
+
...rest,
|
|
5965
|
+
children: children ?? /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(import_jsx_runtime22.Fragment, { children: [
|
|
5966
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(EnableSwitch, { appearance: "checkbox", id: enableId }),
|
|
5967
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(EnableSentence, { htmlFor: enableId })
|
|
5968
|
+
] })
|
|
5969
|
+
}
|
|
5970
|
+
);
|
|
5971
|
+
}
|
|
5972
|
+
);
|
|
5973
|
+
var CancelButton = (0, import_react32.forwardRef)(
|
|
5974
|
+
function AutoRechargeCancelButton({ asChild, onClick, children, className, ...rest }, forwardedRef) {
|
|
5975
|
+
const ctx = useAutoRechargeCtx("CancelButton");
|
|
5976
|
+
const copy = useCopy();
|
|
5977
|
+
const commonProps = {
|
|
5978
|
+
"data-solvapay-auto-recharge-cancel": "",
|
|
5979
|
+
type: "button",
|
|
5980
|
+
onClick: composeEventHandlers(onClick, (event) => {
|
|
5981
|
+
event.preventDefault();
|
|
5982
|
+
ctx.resetForm();
|
|
5983
|
+
ctx.setOpen(false);
|
|
5984
|
+
ctx.focusTrigger();
|
|
5985
|
+
}),
|
|
5986
|
+
className,
|
|
5987
|
+
...rest
|
|
5988
|
+
};
|
|
5989
|
+
if (asChild) {
|
|
5990
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
5991
|
+
Slot,
|
|
5992
|
+
{
|
|
5993
|
+
ref: forwardedRef,
|
|
5994
|
+
...commonProps,
|
|
5995
|
+
children: children ?? copy.autoRecharge.cancelButton
|
|
5996
|
+
}
|
|
5997
|
+
);
|
|
5998
|
+
}
|
|
5999
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("button", { ref: forwardedRef, ...commonProps, children: children ?? copy.autoRecharge.cancelButton });
|
|
6000
|
+
}
|
|
6001
|
+
);
|
|
6002
|
+
var Header = (0, import_react32.forwardRef)(
|
|
6003
|
+
function AutoRechargeHeader({ className, ...rest }, forwardedRef) {
|
|
6004
|
+
const copy = useCopy();
|
|
6005
|
+
const headingId = (0, import_react32.useId)();
|
|
6006
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
|
|
6007
|
+
"header",
|
|
6008
|
+
{
|
|
6009
|
+
ref: forwardedRef,
|
|
6010
|
+
className,
|
|
6011
|
+
"data-solvapay-auto-recharge-header": "",
|
|
6012
|
+
...rest,
|
|
6013
|
+
children: [
|
|
6014
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("section", { "data-solvapay-auto-recharge-heading-group": "", children: [
|
|
6015
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)("h3", { id: headingId, "data-solvapay-auto-recharge-heading": "", children: copy.autoRecharge.heading }),
|
|
6016
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Description, {})
|
|
6017
|
+
] }),
|
|
6018
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(EnableSwitch, { "aria-labelledby": headingId })
|
|
6019
|
+
]
|
|
6020
|
+
}
|
|
6021
|
+
);
|
|
6022
|
+
}
|
|
6023
|
+
);
|
|
6024
|
+
var Description = (0, import_react32.forwardRef)(
|
|
6025
|
+
function AutoRechargeDescription({ className, children, ...rest }, forwardedRef) {
|
|
6026
|
+
const copy = useCopy();
|
|
6027
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6028
|
+
"p",
|
|
6029
|
+
{
|
|
6030
|
+
ref: forwardedRef,
|
|
6031
|
+
className,
|
|
6032
|
+
"data-solvapay-auto-recharge-description": "",
|
|
6033
|
+
...rest,
|
|
6034
|
+
children: children ?? copy.autoRecharge.description
|
|
6035
|
+
}
|
|
6036
|
+
);
|
|
6037
|
+
}
|
|
6038
|
+
);
|
|
6039
|
+
var EnableSwitch = (0, import_react32.forwardRef)(
|
|
6040
|
+
function AutoRechargeEnableSwitch({ asChild, appearance = "switch", onChange, className, ...rest }, forwardedRef) {
|
|
6041
|
+
const ctx = useAutoRechargeCtx("EnableSwitch");
|
|
6042
|
+
const copy = useCopy();
|
|
6043
|
+
const commonProps = {
|
|
6044
|
+
"data-solvapay-auto-recharge-enable": "",
|
|
6045
|
+
"data-appearance": appearance,
|
|
6046
|
+
type: "checkbox",
|
|
6047
|
+
...appearance === "switch" ? { role: "switch", "aria-checked": ctx.form.enabled } : {},
|
|
6048
|
+
checked: ctx.form.enabled,
|
|
6049
|
+
"aria-label": copy.autoRecharge.enableLabel,
|
|
6050
|
+
disabled: ctx.loading || ctx.saving || ctx.disabling || !!ctx.setup,
|
|
6051
|
+
onChange: composeEventHandlers(onChange, (event) => {
|
|
6052
|
+
ctx.updateForm({ enabled: event.currentTarget.checked });
|
|
6053
|
+
}),
|
|
6054
|
+
className,
|
|
6055
|
+
...rest
|
|
6056
|
+
};
|
|
6057
|
+
if (asChild) {
|
|
6058
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6059
|
+
Slot,
|
|
6060
|
+
{
|
|
6061
|
+
ref: forwardedRef,
|
|
6062
|
+
...commonProps
|
|
6063
|
+
}
|
|
6064
|
+
);
|
|
6065
|
+
}
|
|
6066
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("input", { ref: forwardedRef, ...commonProps });
|
|
6067
|
+
}
|
|
6068
|
+
);
|
|
6069
|
+
var Fields = (0, import_react32.forwardRef)(
|
|
6070
|
+
function AutoRechargeFields({ className, children, ...rest }, forwardedRef) {
|
|
6071
|
+
const ctx = useAutoRechargeCtx("Fields");
|
|
6072
|
+
const copy = useCopy();
|
|
6073
|
+
if (!ctx.form.enabled) return null;
|
|
6074
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
|
|
6075
|
+
"fieldset",
|
|
6076
|
+
{
|
|
6077
|
+
ref: forwardedRef,
|
|
6078
|
+
className,
|
|
6079
|
+
disabled: ctx.saving || ctx.disabling,
|
|
6080
|
+
"data-solvapay-auto-recharge-fields": "",
|
|
6081
|
+
"data-solvapay-auto-recharge-body": "",
|
|
6082
|
+
"data-state": "open",
|
|
6083
|
+
...rest,
|
|
6084
|
+
children: [
|
|
6085
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)("legend", { className: "sr-only", children: copy.autoRecharge.heading }),
|
|
6086
|
+
children ?? /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(import_jsx_runtime22.Fragment, { children: [
|
|
6087
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Summary3, {}),
|
|
6088
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ThresholdField, {}),
|
|
6089
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TopupField, {}),
|
|
6090
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ValidationError, {})
|
|
6091
|
+
] })
|
|
6092
|
+
]
|
|
6093
|
+
}
|
|
6094
|
+
);
|
|
6095
|
+
}
|
|
6096
|
+
);
|
|
6097
|
+
var Setup = (0, import_react32.forwardRef)(
|
|
6098
|
+
function AutoRechargeSetup({ className, children, ...rest }, forwardedRef) {
|
|
6099
|
+
const ctx = useAutoRechargeCtx("Setup");
|
|
6100
|
+
if (!ctx.setup?.setupClientSecret) return null;
|
|
6101
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6102
|
+
"div",
|
|
6103
|
+
{
|
|
6104
|
+
ref: forwardedRef,
|
|
6105
|
+
className,
|
|
6106
|
+
"data-solvapay-auto-recharge-setup-panel": "",
|
|
6107
|
+
...rest,
|
|
6108
|
+
children: children ?? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(CardSetup, { setup: ctx.setup, onComplete: ctx.completeSetup })
|
|
6109
|
+
}
|
|
6110
|
+
);
|
|
6111
|
+
}
|
|
6112
|
+
);
|
|
6113
|
+
var Body = (0, import_react32.forwardRef)(
|
|
6114
|
+
function AutoRechargeBody({ className, children, ...rest }, forwardedRef) {
|
|
6115
|
+
const ctx = useAutoRechargeCtx("Body");
|
|
6116
|
+
if (ctx.setup?.setupClientSecret) {
|
|
6117
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Setup, { className });
|
|
6118
|
+
}
|
|
6119
|
+
if (!ctx.form.enabled) return null;
|
|
6120
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Fields, { ref: forwardedRef, className, ...rest, children: children ?? /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(import_jsx_runtime22.Fragment, { children: [
|
|
6121
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Summary3, {}),
|
|
6122
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ThresholdField, {}),
|
|
6123
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(TopupField, {}),
|
|
6124
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(ValidationError, {}),
|
|
6125
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Actions, {})
|
|
6126
|
+
] }) });
|
|
6127
|
+
}
|
|
6128
|
+
);
|
|
6129
|
+
var Summary3 = (0, import_react32.forwardRef)(
|
|
6130
|
+
function AutoRechargeSummary({ className, children, ...rest }, forwardedRef) {
|
|
6131
|
+
const ctx = useAutoRechargeCtx("Summary");
|
|
6132
|
+
if (!ctx.summaryLine) return null;
|
|
6133
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("p", { ref: forwardedRef, className, "data-solvapay-auto-recharge-summary": "", ...rest, children: children ?? ctx.summaryLine });
|
|
6134
|
+
}
|
|
6135
|
+
);
|
|
6136
|
+
var AmountField = (0, import_react32.forwardRef)(function AutoRechargeAmountField({ field, showLabel = true, asChild, onChange, className, ...rest }, forwardedRef) {
|
|
6137
|
+
const ctx = useAutoRechargeCtx("AmountField");
|
|
6138
|
+
const copy = useCopy();
|
|
6139
|
+
const fieldConfig = {
|
|
6140
|
+
threshold: {
|
|
6141
|
+
label: copy.autoRecharge.thresholdLabel,
|
|
6142
|
+
ariaLabel: copy.autoRecharge.thresholdAriaLabel,
|
|
6143
|
+
unitToggleLabel: "balance threshold",
|
|
6144
|
+
value: ctx.form.thresholdAmountMajor,
|
|
6145
|
+
unit: ctx.form.thresholdUnit,
|
|
6146
|
+
unitKey: "thresholdUnit",
|
|
6147
|
+
valueKey: "thresholdAmountMajor",
|
|
6148
|
+
baseValueKey: "thresholdBaseValue",
|
|
6149
|
+
baseUnitKey: "thresholdBaseUnit",
|
|
6150
|
+
mode: ctx.form.thresholdUnit === "currency" ? "currency" : "number",
|
|
6151
|
+
onValue: (value) => ctx.updateForm({
|
|
6152
|
+
thresholdAmountMajor: value,
|
|
6153
|
+
thresholdBaseValue: value,
|
|
6154
|
+
thresholdBaseUnit: ctx.form.thresholdUnit
|
|
6155
|
+
})
|
|
6156
|
+
},
|
|
6157
|
+
fixed: {
|
|
6158
|
+
label: copy.autoRecharge.fixedAmountLabel,
|
|
6159
|
+
ariaLabel: copy.autoRecharge.fixedAmountAriaLabel,
|
|
6160
|
+
unitToggleLabel: "fixed top-up amount",
|
|
6161
|
+
value: ctx.form.topupAmountMajor,
|
|
6162
|
+
unit: ctx.form.topupUnit,
|
|
6163
|
+
unitKey: "topupUnit",
|
|
6164
|
+
valueKey: "topupAmountMajor",
|
|
6165
|
+
baseValueKey: "topupBaseValue",
|
|
6166
|
+
baseUnitKey: "topupBaseUnit",
|
|
6167
|
+
mode: ctx.form.topupUnit === "currency" ? "currency" : "number",
|
|
6168
|
+
onValue: (value) => ctx.updateForm({
|
|
6169
|
+
topupAmountMajor: value,
|
|
6170
|
+
topupBaseValue: value,
|
|
6171
|
+
topupBaseUnit: ctx.form.topupUnit
|
|
6172
|
+
})
|
|
6173
|
+
}
|
|
6174
|
+
}[field];
|
|
6175
|
+
const inputId = (0, import_react32.useId)();
|
|
6176
|
+
const prefix = fieldConfig.mode === "currency" ? getCurrencySymbol2(ctx.currency) : void 0;
|
|
6177
|
+
const handleChange = (event) => {
|
|
6178
|
+
const raw = event.target.value;
|
|
6179
|
+
const next = fieldConfig.mode === "currency" ? raw.replace(/[^0-9.]/g, "") : raw.replace(/[^0-9]/g, "");
|
|
6180
|
+
fieldConfig.onValue(next);
|
|
6181
|
+
};
|
|
6182
|
+
const inputProps = {
|
|
6183
|
+
id: inputId,
|
|
6184
|
+
"data-solvapay-auto-recharge-amount": "",
|
|
6185
|
+
"data-field": field,
|
|
6186
|
+
type: "text",
|
|
6187
|
+
inputMode: fieldConfig.mode === "currency" ? "decimal" : "numeric",
|
|
6188
|
+
placeholder: fieldConfig.mode === "currency" ? "0.00" : "0",
|
|
6189
|
+
value: fieldConfig.value,
|
|
6190
|
+
"aria-label": fieldConfig.ariaLabel,
|
|
6191
|
+
onChange: composeEventHandlers(onChange, handleChange),
|
|
6192
|
+
className,
|
|
6193
|
+
...rest
|
|
6194
|
+
};
|
|
6195
|
+
const slotRef = forwardedRef;
|
|
6196
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("p", { "data-solvapay-auto-recharge-field": "", "data-field": field, children: [
|
|
6197
|
+
showLabel ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("label", { htmlFor: inputId, children: fieldConfig.label }) : null,
|
|
6198
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("span", { "data-solvapay-auto-recharge-amount-row": "", children: [
|
|
6199
|
+
prefix ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("span", { "data-solvapay-auto-recharge-currency-prefix": "", "aria-hidden": "true", children: prefix }) : null,
|
|
6200
|
+
asChild ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Slot, { ref: slotRef, ...inputProps }) : /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("input", { ref: forwardedRef, ...inputProps }),
|
|
6201
|
+
ctx.canToggleUnits ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6202
|
+
UnitToggle,
|
|
6203
|
+
{
|
|
6204
|
+
unit: fieldConfig.unit,
|
|
6205
|
+
fieldLabel: fieldConfig.unitToggleLabel,
|
|
6206
|
+
onToggle: () => ctx.flipUnit(
|
|
6207
|
+
fieldConfig.valueKey,
|
|
6208
|
+
fieldConfig.unitKey,
|
|
6209
|
+
fieldConfig.baseValueKey,
|
|
6210
|
+
fieldConfig.baseUnitKey,
|
|
6211
|
+
fieldConfig.unit
|
|
6212
|
+
)
|
|
6213
|
+
}
|
|
6214
|
+
) : null
|
|
6215
|
+
] })
|
|
6216
|
+
] });
|
|
6217
|
+
});
|
|
6218
|
+
var ThresholdField = (0, import_react32.forwardRef)(
|
|
6219
|
+
function AutoRechargeThresholdField({ className, ...rest }, ref) {
|
|
6220
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("section", { ref, className, ...rest, children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(AmountField, { field: "threshold" }) });
|
|
6221
|
+
}
|
|
6222
|
+
);
|
|
6223
|
+
var TopupField = (0, import_react32.forwardRef)(
|
|
6224
|
+
function AutoRechargeTopupField({ className, ...rest }, ref) {
|
|
6225
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(
|
|
6226
|
+
"section",
|
|
6227
|
+
{
|
|
6228
|
+
ref,
|
|
6229
|
+
className,
|
|
6230
|
+
"data-solvapay-auto-recharge-topup-field": "",
|
|
6231
|
+
...rest,
|
|
6232
|
+
children: [
|
|
6233
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(AmountField, { field: "fixed" }),
|
|
6234
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Hint, {})
|
|
6235
|
+
]
|
|
6236
|
+
}
|
|
6237
|
+
);
|
|
6238
|
+
}
|
|
6239
|
+
);
|
|
6240
|
+
var UnitToggle = (0, import_react32.forwardRef)(function AutoRechargeUnitToggle({ unit, fieldLabel, onToggle, className, ...rest }, forwardedRef) {
|
|
6241
|
+
const ctx = useAutoRechargeCtx("UnitToggle");
|
|
6242
|
+
const targetUnitLabel = unit === "currency" ? "credits" : "currency";
|
|
6243
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6244
|
+
"button",
|
|
6245
|
+
{
|
|
6246
|
+
ref: forwardedRef,
|
|
6247
|
+
type: "button",
|
|
6248
|
+
className,
|
|
6249
|
+
"data-solvapay-auto-recharge-unit-toggle": "",
|
|
6250
|
+
"aria-label": `Switch ${fieldLabel} to ${targetUnitLabel}`,
|
|
6251
|
+
onClick: onToggle,
|
|
6252
|
+
...rest,
|
|
6253
|
+
children: unit === "currency" ? ctx.currency.toUpperCase() : "credits"
|
|
6254
|
+
}
|
|
6255
|
+
);
|
|
6256
|
+
});
|
|
6257
|
+
var Hint = (0, import_react32.forwardRef)(
|
|
6258
|
+
function AutoRechargeHint({ className, ...rest }, forwardedRef) {
|
|
6259
|
+
const ctx = useAutoRechargeCtx("Hint");
|
|
6260
|
+
const copy = useCopy();
|
|
6261
|
+
const hint = ctx.fixedTopupHint;
|
|
6262
|
+
if (!hint) return null;
|
|
6263
|
+
const isCreditsHint = ctx.form.topupUnit === "currency";
|
|
6264
|
+
const text = isCreditsHint ? interpolate(
|
|
6265
|
+
ctx.isApproximate ? copy.autoRecharge.creditsPerRechargeApprox : copy.autoRecharge.creditsPerRecharge,
|
|
6266
|
+
{ credits: new Intl.NumberFormat().format(Number(hint)) }
|
|
6267
|
+
) : interpolate(
|
|
6268
|
+
ctx.isApproximate ? copy.autoRecharge.currencyPerRechargeApprox : copy.autoRecharge.currencyPerRecharge,
|
|
6269
|
+
{ amount: hint }
|
|
6270
|
+
);
|
|
6271
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("p", { ref: forwardedRef, className, "data-solvapay-auto-recharge-hint": "", ...rest, children: text });
|
|
6272
|
+
}
|
|
6273
|
+
);
|
|
6274
|
+
var ValidationError = (0, import_react32.forwardRef)(function AutoRechargeValidationError({ className, ...rest }, forwardedRef) {
|
|
6275
|
+
const ctx = useAutoRechargeCtx("ValidationError");
|
|
6276
|
+
if (!ctx.validationError) return null;
|
|
6277
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6278
|
+
"p",
|
|
6279
|
+
{
|
|
6280
|
+
ref: forwardedRef,
|
|
6281
|
+
role: "alert",
|
|
6282
|
+
"aria-live": "polite",
|
|
6283
|
+
className,
|
|
6284
|
+
"data-solvapay-auto-recharge-validation-error": "",
|
|
6285
|
+
...rest,
|
|
6286
|
+
children: ctx.validationError
|
|
6287
|
+
}
|
|
6288
|
+
);
|
|
6289
|
+
});
|
|
6290
|
+
var Actions = (0, import_react32.forwardRef)(
|
|
6291
|
+
function AutoRechargeActions({ className, children, ...rest }, forwardedRef) {
|
|
6292
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6293
|
+
"menu",
|
|
6294
|
+
{
|
|
6295
|
+
ref: forwardedRef,
|
|
6296
|
+
className,
|
|
6297
|
+
"data-solvapay-auto-recharge-actions": "",
|
|
6298
|
+
...rest,
|
|
6299
|
+
children: children ?? /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(import_jsx_runtime22.Fragment, { children: [
|
|
6300
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)("li", { children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(CancelButton, {}) }),
|
|
6301
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)("li", { children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(SaveButton, {}) })
|
|
6302
|
+
] })
|
|
6303
|
+
}
|
|
6304
|
+
);
|
|
6305
|
+
}
|
|
6306
|
+
);
|
|
6307
|
+
var SaveButton = (0, import_react32.forwardRef)(function AutoRechargeSaveButton({ asChild, onClick, children, className, ...rest }, forwardedRef) {
|
|
6308
|
+
const ctx = useAutoRechargeCtx("SaveButton");
|
|
6309
|
+
const copy = useCopy();
|
|
6310
|
+
const dataState = ctx.saving ? "processing" : ctx.validationError ? "disabled" : "idle";
|
|
6311
|
+
const commonProps = {
|
|
6312
|
+
"data-solvapay-auto-recharge-save": "",
|
|
6313
|
+
"data-state": dataState,
|
|
6314
|
+
type: "button",
|
|
6315
|
+
disabled: ctx.saving || ctx.disabling || !!ctx.validationError,
|
|
6316
|
+
"aria-busy": ctx.saving,
|
|
6317
|
+
onClick: composeEventHandlers(onClick, (event) => {
|
|
6318
|
+
event.preventDefault();
|
|
6319
|
+
void ctx.save();
|
|
6320
|
+
}),
|
|
6321
|
+
className,
|
|
6322
|
+
...rest
|
|
6323
|
+
};
|
|
6324
|
+
const content = ctx.saving ? /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)(import_jsx_runtime22.Fragment, { children: [
|
|
6325
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Spinner, { size: "sm" }),
|
|
6326
|
+
" ",
|
|
6327
|
+
copy.cta.processing
|
|
6328
|
+
] }) : children ?? copy.autoRecharge.saveButton;
|
|
6329
|
+
if (asChild) {
|
|
6330
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6331
|
+
Slot,
|
|
6332
|
+
{
|
|
6333
|
+
ref: forwardedRef,
|
|
6334
|
+
...commonProps,
|
|
6335
|
+
children: content
|
|
6336
|
+
}
|
|
6337
|
+
);
|
|
6338
|
+
}
|
|
6339
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("button", { ref: forwardedRef, ...commonProps, children: content });
|
|
6340
|
+
});
|
|
6341
|
+
var DisableButton = (0, import_react32.forwardRef)(
|
|
6342
|
+
function AutoRechargeDisableButton({ asChild, onClick, children, className, ...rest }, forwardedRef) {
|
|
6343
|
+
const ctx = useAutoRechargeCtx("DisableButton");
|
|
6344
|
+
const copy = useCopy();
|
|
6345
|
+
if (!ctx.config) return null;
|
|
6346
|
+
const commonProps = {
|
|
6347
|
+
"data-solvapay-auto-recharge-disable": "",
|
|
6348
|
+
type: "button",
|
|
6349
|
+
disabled: ctx.saving || ctx.disabling,
|
|
6350
|
+
"aria-busy": ctx.disabling,
|
|
6351
|
+
onClick: composeEventHandlers(onClick, (event) => {
|
|
6352
|
+
event.preventDefault();
|
|
6353
|
+
void ctx.disable();
|
|
6354
|
+
}),
|
|
6355
|
+
className,
|
|
6356
|
+
...rest
|
|
6357
|
+
};
|
|
6358
|
+
if (asChild) {
|
|
6359
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6360
|
+
Slot,
|
|
6361
|
+
{
|
|
6362
|
+
ref: forwardedRef,
|
|
6363
|
+
...commonProps,
|
|
6364
|
+
children: children ?? copy.autoRecharge.disableButton
|
|
6365
|
+
}
|
|
6366
|
+
);
|
|
6367
|
+
}
|
|
6368
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("button", { ref: forwardedRef, ...commonProps, children: children ?? copy.autoRecharge.disableButton });
|
|
6369
|
+
}
|
|
6370
|
+
);
|
|
6371
|
+
var ErrorSlot7 = (0, import_react32.forwardRef)(
|
|
6372
|
+
function AutoRechargeError({ className, children, ...rest }, forwardedRef) {
|
|
6373
|
+
const ctx = useAutoRechargeCtx("Error");
|
|
6374
|
+
if (!ctx.error) return null;
|
|
6375
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6376
|
+
"p",
|
|
6377
|
+
{
|
|
6378
|
+
ref: forwardedRef,
|
|
6379
|
+
role: "alert",
|
|
6380
|
+
"aria-live": "polite",
|
|
6381
|
+
className,
|
|
6382
|
+
"data-solvapay-auto-recharge-error": "",
|
|
6383
|
+
...rest,
|
|
6384
|
+
children: children ?? ctx.error.message
|
|
6385
|
+
}
|
|
6386
|
+
);
|
|
6387
|
+
}
|
|
6388
|
+
);
|
|
6389
|
+
var StatusMessage = (0, import_react32.forwardRef)(
|
|
6390
|
+
function AutoRechargeStatusMessage({ className, children, ...rest }, forwardedRef) {
|
|
6391
|
+
const ctx = useAutoRechargeCtx("StatusMessage");
|
|
6392
|
+
if (!ctx.statusMessage) return null;
|
|
6393
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6394
|
+
"p",
|
|
6395
|
+
{
|
|
6396
|
+
ref: forwardedRef,
|
|
6397
|
+
"aria-live": "polite",
|
|
6398
|
+
className,
|
|
6399
|
+
"data-solvapay-auto-recharge-status-message": "",
|
|
6400
|
+
...rest,
|
|
6401
|
+
children: children ?? ctx.statusMessage
|
|
6402
|
+
}
|
|
6403
|
+
);
|
|
6404
|
+
}
|
|
6405
|
+
);
|
|
6406
|
+
var Status = (0, import_react32.forwardRef)(
|
|
6407
|
+
function AutoRechargeStatus({ className, ...rest }, forwardedRef) {
|
|
6408
|
+
const ctx = useAutoRechargeCtx("Status");
|
|
6409
|
+
const copy = useCopy();
|
|
6410
|
+
const status = ctx.config?.status;
|
|
6411
|
+
if (!status || status === "active" || status === "disabled" || status === "pending_setup") {
|
|
6412
|
+
return null;
|
|
6413
|
+
}
|
|
6414
|
+
const label = status === "failed" ? copy.autoRecharge.statusFailed : null;
|
|
6415
|
+
if (!label) return null;
|
|
6416
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6417
|
+
"span",
|
|
6418
|
+
{
|
|
6419
|
+
ref: forwardedRef,
|
|
6420
|
+
className,
|
|
6421
|
+
"data-solvapay-auto-recharge-status": "",
|
|
6422
|
+
"data-status": status,
|
|
6423
|
+
...rest,
|
|
6424
|
+
children: label
|
|
6425
|
+
}
|
|
6426
|
+
);
|
|
6427
|
+
}
|
|
6428
|
+
);
|
|
6429
|
+
function CardSetupInner({ onComplete }) {
|
|
6430
|
+
const copy = useCopy();
|
|
6431
|
+
const stripe = (0, import_react_stripe_js3.useStripe)();
|
|
6432
|
+
const elements = (0, import_react_stripe_js3.useElements)();
|
|
6433
|
+
const [processing, setProcessing] = (0, import_react32.useState)(false);
|
|
6434
|
+
const [error, setError] = (0, import_react32.useState)(null);
|
|
6435
|
+
(0, import_react32.useEffect)(() => {
|
|
6436
|
+
if (!stripe) return;
|
|
6437
|
+
const clientSecret = readSetupIntentClientSecret(window.location.search);
|
|
6438
|
+
if (!clientSecret) return;
|
|
6439
|
+
let cancelled = false;
|
|
6440
|
+
void (async () => {
|
|
6441
|
+
setProcessing(true);
|
|
6442
|
+
const { setupIntent, error: retrieveError } = await stripe.retrieveSetupIntent(clientSecret);
|
|
6443
|
+
if (cancelled) return;
|
|
6444
|
+
stripSetupIntentParams();
|
|
6445
|
+
if (retrieveError || !setupIntent) {
|
|
6446
|
+
setError(copy.autoRecharge.setupAuthFailed);
|
|
6447
|
+
setProcessing(false);
|
|
6448
|
+
return;
|
|
6449
|
+
}
|
|
6450
|
+
if (setupIntent.status === "succeeded" || setupIntent.status === "processing") {
|
|
6451
|
+
await onComplete();
|
|
6452
|
+
} else {
|
|
6453
|
+
setError(copy.autoRecharge.setupAuthFailed);
|
|
6454
|
+
}
|
|
6455
|
+
if (!cancelled) setProcessing(false);
|
|
6456
|
+
})();
|
|
6457
|
+
return () => {
|
|
6458
|
+
cancelled = true;
|
|
6459
|
+
};
|
|
6460
|
+
}, [stripe, onComplete, copy.autoRecharge]);
|
|
6461
|
+
const handleSubmit = async (event) => {
|
|
6462
|
+
event.preventDefault();
|
|
6463
|
+
if (!stripe || !elements) {
|
|
6464
|
+
setError("Stripe is still loading. Please wait.");
|
|
6465
|
+
return;
|
|
6466
|
+
}
|
|
6467
|
+
setProcessing(true);
|
|
6468
|
+
setError(null);
|
|
6469
|
+
const { error: submitError } = await elements.submit();
|
|
6470
|
+
if (submitError) {
|
|
6471
|
+
setError(submitError.message ?? "Card authorization failed");
|
|
6472
|
+
setProcessing(false);
|
|
6473
|
+
return;
|
|
6474
|
+
}
|
|
6475
|
+
const { error: confirmError } = await stripe.confirmSetup({
|
|
6476
|
+
elements,
|
|
6477
|
+
confirmParams: {
|
|
6478
|
+
return_url: typeof window !== "undefined" ? window.location.href : "/"
|
|
6479
|
+
},
|
|
6480
|
+
redirect: "if_required"
|
|
6481
|
+
});
|
|
6482
|
+
if (confirmError) {
|
|
6483
|
+
setError(confirmError.message ?? "Card authorization failed");
|
|
6484
|
+
setProcessing(false);
|
|
6485
|
+
return;
|
|
6486
|
+
}
|
|
6487
|
+
await onComplete();
|
|
6488
|
+
setProcessing(false);
|
|
6489
|
+
};
|
|
6490
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("form", { onSubmit: handleSubmit, "data-solvapay-auto-recharge-setup": "", children: [
|
|
6491
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)("h4", { children: copy.autoRecharge.setupHeading }),
|
|
6492
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)("p", { children: copy.autoRecharge.setupDescription }),
|
|
6493
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(import_react_stripe_js3.PaymentElement, { options: withPaymentElementDefaults() }),
|
|
6494
|
+
error ? /* @__PURE__ */ (0, import_jsx_runtime22.jsx)("p", { role: "alert", "aria-live": "polite", "data-solvapay-auto-recharge-setup-error": "", children: error }) : null,
|
|
6495
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6496
|
+
"button",
|
|
6497
|
+
{
|
|
6498
|
+
type: "submit",
|
|
6499
|
+
disabled: processing || !stripe,
|
|
6500
|
+
"data-solvapay-auto-recharge-setup-submit": "",
|
|
6501
|
+
children: processing ? copy.autoRecharge.setupProcessing : copy.autoRecharge.setupSubmit
|
|
6502
|
+
}
|
|
6503
|
+
)
|
|
6504
|
+
] });
|
|
6505
|
+
}
|
|
6506
|
+
function CardSetup({ setup, onComplete }) {
|
|
6507
|
+
const stripePromise = (0, import_react32.useMemo)(() => {
|
|
6508
|
+
if (!setup.publishableKey || !setup.setupClientSecret) return null;
|
|
6509
|
+
const options = {
|
|
6510
|
+
...setup.stripeAccountId ? { stripeAccount: setup.stripeAccountId } : {},
|
|
6511
|
+
developerTools: { assistant: { enabled: false } }
|
|
6512
|
+
};
|
|
6513
|
+
const cacheKey = getStripeCacheKey3(setup.publishableKey, setup.stripeAccountId);
|
|
6514
|
+
const cached = stripePromiseCache3.get(cacheKey);
|
|
6515
|
+
if (cached) return cached;
|
|
6516
|
+
const promise = (0, import_stripe_js3.loadStripe)(setup.publishableKey, options);
|
|
6517
|
+
stripePromiseCache3.set(cacheKey, promise);
|
|
6518
|
+
return promise;
|
|
6519
|
+
}, [setup.publishableKey, setup.setupClientSecret, setup.stripeAccountId]);
|
|
6520
|
+
if (!stripePromise || !setup.setupClientSecret) {
|
|
6521
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsxs)("p", { "data-solvapay-auto-recharge-setup-loading": "", children: [
|
|
6522
|
+
/* @__PURE__ */ (0, import_jsx_runtime22.jsx)(Spinner, { size: "sm" }),
|
|
6523
|
+
" Loading card form\u2026"
|
|
6524
|
+
] });
|
|
6525
|
+
}
|
|
6526
|
+
return /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(
|
|
6527
|
+
import_react_stripe_js3.Elements,
|
|
6528
|
+
{
|
|
6529
|
+
stripe: stripePromise,
|
|
6530
|
+
options: { clientSecret: setup.setupClientSecret },
|
|
6531
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime22.jsx)(CardSetupInner, { onComplete })
|
|
6532
|
+
},
|
|
6533
|
+
setup.setupClientSecret
|
|
6534
|
+
);
|
|
6535
|
+
}
|
|
6536
|
+
var AutoRechargeRoot2 = Root10;
|
|
6537
|
+
var AutoRechargeLoading2 = Loading7;
|
|
6538
|
+
var AutoRechargeCard2 = Card2;
|
|
6539
|
+
var AutoRechargeCardHeading2 = CardHeading;
|
|
6540
|
+
var AutoRechargeCardSummary2 = CardSummary;
|
|
6541
|
+
var AutoRechargeTrigger2 = Trigger;
|
|
6542
|
+
var AutoRechargeOverlay2 = Overlay;
|
|
6543
|
+
var AutoRechargeContent2 = Content;
|
|
6544
|
+
var AutoRechargeTitle2 = Title;
|
|
6545
|
+
var AutoRechargeEnableQuestion2 = EnableQuestion;
|
|
6546
|
+
var AutoRechargeEnableSentence2 = EnableSentence;
|
|
6547
|
+
var AutoRechargeEnableRow2 = EnableRow;
|
|
6548
|
+
var AutoRechargeCancelButton2 = CancelButton;
|
|
6549
|
+
var AutoRechargeHeader2 = Header;
|
|
6550
|
+
var AutoRechargeDescription2 = Description;
|
|
6551
|
+
var AutoRechargeEnableSwitch2 = EnableSwitch;
|
|
6552
|
+
var AutoRechargeFields2 = Fields;
|
|
6553
|
+
var AutoRechargeSetup2 = Setup;
|
|
6554
|
+
var AutoRechargeBody2 = Body;
|
|
6555
|
+
var AutoRechargeSummary2 = Summary3;
|
|
6556
|
+
var AutoRechargeThresholdField2 = ThresholdField;
|
|
6557
|
+
var AutoRechargeTopupField2 = TopupField;
|
|
6558
|
+
var AutoRechargeAmountField2 = AmountField;
|
|
6559
|
+
var AutoRechargeUnitToggle2 = UnitToggle;
|
|
6560
|
+
var AutoRechargeHint2 = Hint;
|
|
6561
|
+
var AutoRechargeValidationError2 = ValidationError;
|
|
6562
|
+
var AutoRechargeActions2 = Actions;
|
|
6563
|
+
var AutoRechargeSaveButton2 = SaveButton;
|
|
6564
|
+
var AutoRechargeDisableButton2 = DisableButton;
|
|
6565
|
+
var AutoRechargeError2 = ErrorSlot7;
|
|
6566
|
+
var AutoRechargeStatusMessage2 = StatusMessage;
|
|
6567
|
+
var AutoRechargeStatus2 = Status;
|
|
6568
|
+
var AutoRechargeCardSetup = CardSetup;
|
|
6569
|
+
var AutoRecharge = {
|
|
6570
|
+
Root: Root10,
|
|
6571
|
+
Loading: Loading7,
|
|
6572
|
+
Card: Card2,
|
|
6573
|
+
CardHeading,
|
|
6574
|
+
CardSummary,
|
|
6575
|
+
Trigger,
|
|
6576
|
+
Overlay,
|
|
6577
|
+
Content,
|
|
6578
|
+
Title,
|
|
6579
|
+
EnableQuestion,
|
|
6580
|
+
EnableSentence,
|
|
6581
|
+
EnableRow,
|
|
6582
|
+
CancelButton,
|
|
6583
|
+
Header,
|
|
6584
|
+
Description,
|
|
6585
|
+
EnableSwitch,
|
|
6586
|
+
Fields,
|
|
6587
|
+
Setup,
|
|
6588
|
+
Body,
|
|
6589
|
+
Summary: Summary3,
|
|
6590
|
+
ThresholdField,
|
|
6591
|
+
TopupField,
|
|
6592
|
+
AmountField,
|
|
6593
|
+
UnitToggle,
|
|
6594
|
+
Hint,
|
|
6595
|
+
ValidationError,
|
|
6596
|
+
Actions,
|
|
6597
|
+
SaveButton,
|
|
6598
|
+
DisableButton,
|
|
6599
|
+
Error: ErrorSlot7,
|
|
6600
|
+
StatusMessage,
|
|
6601
|
+
Status,
|
|
6602
|
+
CardSetup
|
|
6603
|
+
};
|
|
6604
|
+
function useAutoRechargeForm() {
|
|
6605
|
+
return useAutoRechargeCtx("useAutoRechargeForm");
|
|
6606
|
+
}
|
|
6607
|
+
|
|
6608
|
+
// src/primitives/ProductBadge.tsx
|
|
6609
|
+
var import_react33 = require("react");
|
|
6610
|
+
var import_jsx_runtime23 = require("react/jsx-runtime");
|
|
6611
|
+
var ProductBadgeImpl = (0, import_react33.forwardRef)(function ProductBadge({ asChild, children, ...rest }, forwardedRef) {
|
|
6612
|
+
const solva = (0, import_react33.useContext)(SolvaPayContext);
|
|
6613
|
+
if (!solva) throw new MissingProviderError("ProductBadge");
|
|
6614
|
+
const { purchases, loading, hasPaidPurchase, activePurchase } = usePurchase();
|
|
6615
|
+
const copy = useCopy();
|
|
6616
|
+
const [hasLoadedOnce, setHasLoadedOnce] = (0, import_react33.useState)(false);
|
|
6617
|
+
(0, import_react33.useEffect)(() => {
|
|
6618
|
+
if (!loading) setHasLoadedOnce(true);
|
|
6619
|
+
}, [loading]);
|
|
6620
|
+
const planToDisplay = activePurchase?.productName ?? null;
|
|
6621
|
+
const shouldShow = planToDisplay !== null && (!loading || hasLoadedOnce);
|
|
6622
|
+
if (!shouldShow) return null;
|
|
6623
|
+
const commonProps = {
|
|
6624
|
+
"data-solvapay-product-badge": "",
|
|
6625
|
+
"data-loading": loading ? "" : void 0,
|
|
6626
|
+
"data-has-purchase": activePurchase ? "" : void 0,
|
|
6627
|
+
"data-has-paid-purchase": hasPaidPurchase ? "" : void 0,
|
|
6628
|
+
role: "status",
|
|
6629
|
+
"aria-live": "polite",
|
|
6630
|
+
"aria-busy": loading,
|
|
6631
|
+
"aria-label": interpolate(copy.product.currentProductLabel, { name: planToDisplay }),
|
|
6632
|
+
...rest
|
|
6633
|
+
};
|
|
6634
|
+
if (asChild) {
|
|
6635
|
+
return (
|
|
6636
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
6637
|
+
/* @__PURE__ */ (0, import_jsx_runtime23.jsx)(Slot, { ref: forwardedRef, ...commonProps, children: children ?? /* @__PURE__ */ (0, import_jsx_runtime23.jsx)(import_jsx_runtime23.Fragment, { children: planToDisplay }) })
|
|
6638
|
+
);
|
|
6639
|
+
}
|
|
6640
|
+
void purchases;
|
|
6641
|
+
return (
|
|
6642
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
6643
|
+
/* @__PURE__ */ (0, import_jsx_runtime23.jsx)("div", { ref: forwardedRef, ...commonProps, children: children ?? planToDisplay })
|
|
6644
|
+
);
|
|
6645
|
+
});
|
|
6646
|
+
var ProductBadge2 = ProductBadgeImpl;
|
|
6647
|
+
var PlanBadge = ProductBadgeImpl;
|
|
6648
|
+
|
|
6649
|
+
// src/primitives/PaywallNotice.tsx
|
|
6650
|
+
var import_react38 = require("react");
|
|
6651
|
+
|
|
6652
|
+
// src/primitives/checkout/index.tsx
|
|
6653
|
+
var import_react36 = require("react");
|
|
6654
|
+
|
|
6655
|
+
// src/hooks/useCheckoutFlow.ts
|
|
6656
|
+
var import_react35 = require("react");
|
|
6657
|
+
|
|
6658
|
+
// src/hooks/useTransport.ts
|
|
6659
|
+
var import_react34 = require("react");
|
|
6660
|
+
function useTransport() {
|
|
6661
|
+
const { _config } = useSolvaPay();
|
|
6662
|
+
return (0, import_react34.useMemo)(() => _config?.transport ?? createHttpTransport(_config), [_config]);
|
|
6663
|
+
}
|
|
6664
|
+
|
|
6665
|
+
// src/primitives/checkout/shared.ts
|
|
6666
|
+
function isPayg(plan) {
|
|
6667
|
+
return isPaygPlan(plan ?? null);
|
|
6668
|
+
}
|
|
6669
|
+
function planSortByPaygFirstThenAsc(a, b) {
|
|
6670
|
+
const aPayg = isPayg(a);
|
|
6671
|
+
const bPayg = isPayg(b);
|
|
6672
|
+
if (aPayg && !bPayg) return -1;
|
|
6673
|
+
if (!aPayg && bPayg) return 1;
|
|
6674
|
+
return (a.price ?? 0) - (b.price ?? 0);
|
|
6675
|
+
}
|
|
6676
|
+
function buildDefaultCheckoutPlanFilter(allPlans) {
|
|
6677
|
+
const hasNonPaygPaid = allPlans.some(
|
|
6678
|
+
(p) => p.requiresPayment !== false && !isPayg(p)
|
|
6679
|
+
);
|
|
6680
|
+
return (plan) => {
|
|
6681
|
+
if (plan.requiresPayment === false) return false;
|
|
6682
|
+
if (hasNonPaygPaid && isPayg(plan)) return false;
|
|
6683
|
+
return true;
|
|
6684
|
+
};
|
|
6685
|
+
}
|
|
6686
|
+
function formatContinueLabel(plan, locale, pricingOption) {
|
|
6687
|
+
if (!plan) return "Continue";
|
|
6688
|
+
if (isPayg(plan)) {
|
|
6689
|
+
return `Continue with ${plan.name ?? "Pay as you go"}`;
|
|
6690
|
+
}
|
|
6691
|
+
const option = pricingOption ?? resolvePlanPricingOption(plan, null);
|
|
6692
|
+
const currency = option.currency.toUpperCase();
|
|
6693
|
+
const priceLabel = formatPrice(option.price ?? 0, currency, { locale });
|
|
6694
|
+
const cycle = plan.billingCycle ? `/${shortCycle(plan.billingCycle)}` : "";
|
|
6695
|
+
return `Continue with ${plan.name ?? "Plan"} \u2014 ${priceLabel}${cycle}`;
|
|
6696
|
+
}
|
|
6697
|
+
function formatPaygRate(plan, locale) {
|
|
6698
|
+
const creditsPerUnit = plan.creditsPerUnit ?? 1;
|
|
6699
|
+
const creditLabel = creditsPerUnit === 1 ? "credit" : "credits";
|
|
6700
|
+
return `${creditsPerUnit.toLocaleString(locale)} ${creditLabel} / call`;
|
|
6701
|
+
}
|
|
6702
|
+
function inferIncludedCredits(plan) {
|
|
6703
|
+
const price = plan.price ?? 0;
|
|
6704
|
+
const creditsPerUnit = plan.creditsPerUnit ?? 0;
|
|
6705
|
+
if (price > 0 && creditsPerUnit > 0) {
|
|
6706
|
+
return Math.round(price * creditsPerUnit);
|
|
6707
|
+
}
|
|
6708
|
+
return 0;
|
|
6709
|
+
}
|
|
6710
|
+
function shortCycle(cycle) {
|
|
6711
|
+
if (!cycle) return "mo";
|
|
6712
|
+
const lc = cycle.toLowerCase();
|
|
6713
|
+
if (lc.startsWith("year") || lc === "annually" || lc === "annual") return "yr";
|
|
6714
|
+
if (lc.startsWith("week")) return "wk";
|
|
6715
|
+
if (lc.startsWith("day")) return "d";
|
|
6716
|
+
return "mo";
|
|
6717
|
+
}
|
|
6718
|
+
|
|
6719
|
+
// src/hooks/useCheckoutFlow.ts
|
|
6720
|
+
function useCheckoutFlow(opts) {
|
|
6721
|
+
const {
|
|
6722
|
+
productRef,
|
|
6723
|
+
initialStep = "plan",
|
|
6724
|
+
initialAmountMinor = null
|
|
6725
|
+
} = opts;
|
|
6726
|
+
const onPlanSelectRef = (0, import_react35.useRef)(opts.onPlanSelect);
|
|
6727
|
+
const onAmountSelectRef = (0, import_react35.useRef)(opts.onAmountSelect);
|
|
6728
|
+
const onPurchaseSuccessRef = (0, import_react35.useRef)(opts.onPurchaseSuccess);
|
|
6729
|
+
const onErrorRef = (0, import_react35.useRef)(opts.onError);
|
|
6730
|
+
onPlanSelectRef.current = opts.onPlanSelect;
|
|
6731
|
+
onAmountSelectRef.current = opts.onAmountSelect;
|
|
6732
|
+
onPurchaseSuccessRef.current = opts.onPurchaseSuccess;
|
|
6733
|
+
onErrorRef.current = opts.onError;
|
|
6734
|
+
const planCtx = usePlanSelector();
|
|
6735
|
+
const planSelection = usePlanSelection();
|
|
6736
|
+
const transport = useTransport();
|
|
6737
|
+
const locale = useLocale();
|
|
6738
|
+
const balance = useBalance();
|
|
6739
|
+
const { creditsPerMinorUnit, displayExchangeRate, adjustBalance } = balance;
|
|
6740
|
+
const { refetchPurchase } = useSolvaPay();
|
|
6741
|
+
const { merchant } = useMerchant();
|
|
6742
|
+
const [topupCurrencyOverride, setTopupCurrencyOverride] = (0, import_react35.useState)(null);
|
|
6743
|
+
const topupCurrencies = (0, import_react35.useMemo)(() => {
|
|
6744
|
+
const fromMerchant = (merchant?.supportedTopupCurrencies ?? []).map((code) => code.toUpperCase()).filter(Boolean);
|
|
6745
|
+
const fallback = opts.topupCurrency?.toUpperCase() ?? merchant?.defaultCurrency?.toUpperCase() ?? null;
|
|
6746
|
+
const list = fromMerchant.length > 0 ? fromMerchant : fallback ? [fallback] : [];
|
|
6747
|
+
return Array.from(new Set(list));
|
|
6748
|
+
}, [merchant?.supportedTopupCurrencies, merchant?.defaultCurrency, opts.topupCurrency]);
|
|
6749
|
+
const resolvedDefaultTopupCurrency = opts.topupCurrency?.toUpperCase() ?? merchant?.defaultCurrency?.toUpperCase() ?? null;
|
|
6750
|
+
const planPickerCurrency = planCtx.preferredCurrency?.toUpperCase() ?? null;
|
|
6751
|
+
const topupCurrency = (topupCurrencyOverride && topupCurrencies.includes(topupCurrencyOverride) ? topupCurrencyOverride : null) ?? (planPickerCurrency && topupCurrencies.includes(planPickerCurrency) ? planPickerCurrency : null) ?? resolvedDefaultTopupCurrency;
|
|
6752
|
+
const topupCurrencyReady = topupCurrency != null;
|
|
6753
|
+
const setTopupCurrency = (0, import_react35.useCallback)(
|
|
6754
|
+
(code) => {
|
|
6755
|
+
const normalized = code.toUpperCase();
|
|
6756
|
+
setTopupCurrencyOverride(normalized);
|
|
6757
|
+
},
|
|
6758
|
+
[]
|
|
6759
|
+
);
|
|
6760
|
+
const [step, setStep] = (0, import_react35.useState)(initialStep);
|
|
6761
|
+
const [status, setStatus] = (0, import_react35.useState)("idle");
|
|
6762
|
+
const [selectedAmountMinor, setSelectedAmountMinor] = (0, import_react35.useState)(initialAmountMinor);
|
|
6763
|
+
const [successMeta, setSuccessMeta] = (0, import_react35.useState)(null);
|
|
6764
|
+
const [error, setError] = (0, import_react35.useState)(null);
|
|
6765
|
+
const selectedAmountMinorRef = (0, import_react35.useRef)(initialAmountMinor);
|
|
6766
|
+
const selectedPlan = planCtx.selectedPlan;
|
|
6767
|
+
const selectedPlanRef = planCtx.selectedPlanRef;
|
|
6768
|
+
const selectedPlanShape = selectedPlan;
|
|
6769
|
+
const branch = selectedPlanShape ? isPayg(selectedPlanShape) ? "payg" : "recurring" : null;
|
|
6770
|
+
const canGoBack = step === "amount" || step === "payment";
|
|
6771
|
+
const selectPlan = (0, import_react35.useCallback)(
|
|
5068
6772
|
(ref) => {
|
|
5069
6773
|
planCtx.select(ref);
|
|
5070
6774
|
const plan = planCtx.plans.find((p) => p.reference === ref) ?? null;
|
|
@@ -5074,7 +6778,7 @@ function useCheckoutFlow(opts) {
|
|
|
5074
6778
|
},
|
|
5075
6779
|
[planCtx]
|
|
5076
6780
|
);
|
|
5077
|
-
const selectAmount = (0,
|
|
6781
|
+
const selectAmount = (0, import_react35.useCallback)(
|
|
5078
6782
|
(amountMinor) => {
|
|
5079
6783
|
selectedAmountMinorRef.current = amountMinor;
|
|
5080
6784
|
setSelectedAmountMinor(amountMinor);
|
|
@@ -5083,7 +6787,7 @@ function useCheckoutFlow(opts) {
|
|
|
5083
6787
|
},
|
|
5084
6788
|
[topupCurrency]
|
|
5085
6789
|
);
|
|
5086
|
-
const runActivate = (0,
|
|
6790
|
+
const runActivate = (0, import_react35.useCallback)(async () => {
|
|
5087
6791
|
if (!selectedPlanShape || !selectedPlanRef) return false;
|
|
5088
6792
|
setError(null);
|
|
5089
6793
|
setStatus("activating");
|
|
@@ -5100,7 +6804,7 @@ function useCheckoutFlow(opts) {
|
|
|
5100
6804
|
return false;
|
|
5101
6805
|
}
|
|
5102
6806
|
}, [productRef, selectedPlanRef, selectedPlanShape, transport]);
|
|
5103
|
-
const advanceFromPlan = (0,
|
|
6807
|
+
const advanceFromPlan = (0, import_react35.useCallback)(async () => {
|
|
5104
6808
|
if (!selectedPlanShape || !selectedPlanRef) return;
|
|
5105
6809
|
if (branch === "payg") {
|
|
5106
6810
|
if (planCtx.currentPlanRef === selectedPlanRef) {
|
|
@@ -5114,7 +6818,7 @@ function useCheckoutFlow(opts) {
|
|
|
5114
6818
|
setError(null);
|
|
5115
6819
|
setStep("payment");
|
|
5116
6820
|
}, [branch, planCtx.currentPlanRef, runActivate, selectedPlanRef, selectedPlanShape]);
|
|
5117
|
-
const recordPaygSuccess = (0,
|
|
6821
|
+
const recordPaygSuccess = (0, import_react35.useCallback)(
|
|
5118
6822
|
(creditsAddedFromBackend) => {
|
|
5119
6823
|
if (!selectedPlanShape || selectedAmountMinor == null) return;
|
|
5120
6824
|
const currency = topupCurrency ?? "USD";
|
|
@@ -5148,7 +6852,7 @@ function useCheckoutFlow(opts) {
|
|
|
5148
6852
|
topupCurrency
|
|
5149
6853
|
]
|
|
5150
6854
|
);
|
|
5151
|
-
const recordRecurringSuccess = (0,
|
|
6855
|
+
const recordRecurringSuccess = (0, import_react35.useCallback)(() => {
|
|
5152
6856
|
if (!selectedPlanShape) return;
|
|
5153
6857
|
const pricingOption = selectedPlan ? resolvePlanPricingOption(selectedPlan, planSelection?.selectedCurrency) : {
|
|
5154
6858
|
currency: selectedPlanShape.currency ?? "USD",
|
|
@@ -5167,7 +6871,7 @@ function useCheckoutFlow(opts) {
|
|
|
5167
6871
|
setStep("success");
|
|
5168
6872
|
onPurchaseSuccessRef.current?.(meta);
|
|
5169
6873
|
}, [selectedPlanShape, selectedPlan, planSelection?.selectedCurrency]);
|
|
5170
|
-
const advance = (0,
|
|
6874
|
+
const advance = (0, import_react35.useCallback)(async () => {
|
|
5171
6875
|
if (step === "plan") {
|
|
5172
6876
|
await advanceFromPlan();
|
|
5173
6877
|
return;
|
|
@@ -5194,7 +6898,7 @@ function useCheckoutFlow(opts) {
|
|
|
5194
6898
|
selectedAmountMinor,
|
|
5195
6899
|
step
|
|
5196
6900
|
]);
|
|
5197
|
-
const back = (0,
|
|
6901
|
+
const back = (0, import_react35.useCallback)(() => {
|
|
5198
6902
|
setError(null);
|
|
5199
6903
|
if (step === "amount") {
|
|
5200
6904
|
setStep("plan");
|
|
@@ -5205,7 +6909,7 @@ function useCheckoutFlow(opts) {
|
|
|
5205
6909
|
return;
|
|
5206
6910
|
}
|
|
5207
6911
|
}, [branch, step]);
|
|
5208
|
-
const reset = (0,
|
|
6912
|
+
const reset = (0, import_react35.useCallback)(() => {
|
|
5209
6913
|
setStep("plan");
|
|
5210
6914
|
selectedAmountMinorRef.current = null;
|
|
5211
6915
|
setSelectedAmountMinor(null);
|
|
@@ -5214,13 +6918,13 @@ function useCheckoutFlow(opts) {
|
|
|
5214
6918
|
setStatus("idle");
|
|
5215
6919
|
setTopupCurrencyOverride(null);
|
|
5216
6920
|
}, []);
|
|
5217
|
-
const retry = (0,
|
|
6921
|
+
const retry = (0, import_react35.useCallback)(async () => {
|
|
5218
6922
|
if (status !== "error") return;
|
|
5219
6923
|
if (step === "plan" && branch === "payg") {
|
|
5220
6924
|
await runActivate();
|
|
5221
6925
|
}
|
|
5222
6926
|
}, [branch, runActivate, status, step]);
|
|
5223
|
-
const notifyPaymentSuccess = (0,
|
|
6927
|
+
const notifyPaymentSuccess = (0, import_react35.useCallback)(
|
|
5224
6928
|
(_intent, extras) => {
|
|
5225
6929
|
if (branch === "payg") {
|
|
5226
6930
|
recordPaygSuccess(extras?.creditsAdded);
|
|
@@ -5230,7 +6934,7 @@ function useCheckoutFlow(opts) {
|
|
|
5230
6934
|
},
|
|
5231
6935
|
[branch, recordPaygSuccess, recordRecurringSuccess]
|
|
5232
6936
|
);
|
|
5233
|
-
return (0,
|
|
6937
|
+
return (0, import_react35.useMemo)(
|
|
5234
6938
|
() => ({
|
|
5235
6939
|
step,
|
|
5236
6940
|
status,
|
|
@@ -5279,10 +6983,10 @@ function useCheckoutFlow(opts) {
|
|
|
5279
6983
|
}
|
|
5280
6984
|
|
|
5281
6985
|
// src/primitives/checkout/index.tsx
|
|
5282
|
-
var
|
|
5283
|
-
var CheckoutContext = (0,
|
|
6986
|
+
var import_jsx_runtime24 = require("react/jsx-runtime");
|
|
6987
|
+
var CheckoutContext = (0, import_react36.createContext)(null);
|
|
5284
6988
|
function useCheckoutContext(part) {
|
|
5285
|
-
const ctx = (0,
|
|
6989
|
+
const ctx = (0, import_react36.useContext)(CheckoutContext);
|
|
5286
6990
|
if (!ctx) {
|
|
5287
6991
|
throw new Error(`CheckoutSteps.${part} must be rendered inside <CheckoutSteps.Root>.`);
|
|
5288
6992
|
}
|
|
@@ -5291,7 +6995,7 @@ function useCheckoutContext(part) {
|
|
|
5291
6995
|
function useCheckoutSteps() {
|
|
5292
6996
|
return useCheckoutContext("useCheckoutSteps");
|
|
5293
6997
|
}
|
|
5294
|
-
var
|
|
6998
|
+
var Root11 = (0, import_react36.forwardRef)(function CheckoutStepsRoot(props, forwardedRef) {
|
|
5295
6999
|
const {
|
|
5296
7000
|
productRef,
|
|
5297
7001
|
returnUrl: _returnUrl,
|
|
@@ -5313,9 +7017,9 @@ var Root10 = (0, import_react34.forwardRef)(function CheckoutStepsRoot(props, fo
|
|
|
5313
7017
|
children
|
|
5314
7018
|
} = props;
|
|
5315
7019
|
if (externalFlow) {
|
|
5316
|
-
return /* @__PURE__ */ (0,
|
|
7020
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { ref: forwardedRef, "data-solvapay-checkout": "", className, children: /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(CheckoutContext.Provider, { value: externalFlow, children }) });
|
|
5317
7021
|
}
|
|
5318
|
-
return /* @__PURE__ */ (0,
|
|
7022
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5319
7023
|
RootWithPlanSelector,
|
|
5320
7024
|
{
|
|
5321
7025
|
productRef,
|
|
@@ -5358,11 +7062,11 @@ function RootWithPlanSelector({
|
|
|
5358
7062
|
children
|
|
5359
7063
|
}) {
|
|
5360
7064
|
const { plans } = usePlans({ productRef });
|
|
5361
|
-
const resolvedFilter = (0,
|
|
7065
|
+
const resolvedFilter = (0, import_react36.useMemo)(
|
|
5362
7066
|
() => filter ?? buildDefaultCheckoutPlanFilter(plans),
|
|
5363
7067
|
[filter, plans]
|
|
5364
7068
|
);
|
|
5365
|
-
return /* @__PURE__ */ (0,
|
|
7069
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5366
7070
|
PlanSelector.Root,
|
|
5367
7071
|
{
|
|
5368
7072
|
productRef,
|
|
@@ -5372,7 +7076,7 @@ function RootWithPlanSelector({
|
|
|
5372
7076
|
currentPlanRef,
|
|
5373
7077
|
autoSelectFirstPaid,
|
|
5374
7078
|
initialPlanRef,
|
|
5375
|
-
children: /* @__PURE__ */ (0,
|
|
7079
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5376
7080
|
FlowProvider,
|
|
5377
7081
|
{
|
|
5378
7082
|
productRef,
|
|
@@ -5414,22 +7118,22 @@ function FlowProvider({
|
|
|
5414
7118
|
onPurchaseSuccess,
|
|
5415
7119
|
onError
|
|
5416
7120
|
});
|
|
5417
|
-
return /* @__PURE__ */ (0,
|
|
7121
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { ref: forwardedRef, "data-solvapay-checkout": "", "data-step": flow.step, className, children: /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(CheckoutContext.Provider, { value: flow, children }) });
|
|
5418
7122
|
}
|
|
5419
7123
|
function IfStep({ step, children }) {
|
|
5420
7124
|
const flow = useCheckoutContext("IfStep");
|
|
5421
7125
|
const matches = Array.isArray(step) ? step.includes(flow.step) : flow.step === step;
|
|
5422
7126
|
if (!matches) return null;
|
|
5423
|
-
return /* @__PURE__ */ (0,
|
|
7127
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(import_jsx_runtime24.Fragment, { children });
|
|
5424
7128
|
}
|
|
5425
|
-
var StepHeading = (0,
|
|
7129
|
+
var StepHeading = (0, import_react36.forwardRef)(function CheckoutStepsStepHeading({ asChild, children, className, ...rest }, forwardedRef) {
|
|
5426
7130
|
const flow = useCheckoutContext("StepHeading");
|
|
5427
7131
|
const copy = useCopy();
|
|
5428
7132
|
const paywallCtx = usePaywallNoticeOptional();
|
|
5429
7133
|
if (flow.step === "success") return null;
|
|
5430
7134
|
const defaultText = resolveStepHeading(flow.step, copy, paywallCtx?.content ?? null);
|
|
5431
7135
|
const Comp = asChild ? Slot : "h3";
|
|
5432
|
-
return /* @__PURE__ */ (0,
|
|
7136
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5433
7137
|
Comp,
|
|
5434
7138
|
{
|
|
5435
7139
|
ref: forwardedRef,
|
|
@@ -5441,7 +7145,7 @@ var StepHeading = (0, import_react34.forwardRef)(function CheckoutStepsStepHeadi
|
|
|
5441
7145
|
}
|
|
5442
7146
|
);
|
|
5443
7147
|
});
|
|
5444
|
-
var StepMessage = (0,
|
|
7148
|
+
var StepMessage = (0, import_react36.forwardRef)(function CheckoutStepsStepMessage({ asChild, children, className, ...rest }, forwardedRef) {
|
|
5445
7149
|
const flow = useCheckoutContext("StepMessage");
|
|
5446
7150
|
const copy = useCopy();
|
|
5447
7151
|
const paywallCtx = usePaywallNoticeOptional();
|
|
@@ -5449,7 +7153,7 @@ var StepMessage = (0, import_react34.forwardRef)(function CheckoutStepsStepMessa
|
|
|
5449
7153
|
const defaultText = resolveStepMessage(flow, copy, paywallCtx?.content ?? null);
|
|
5450
7154
|
if (!defaultText && children == null) return null;
|
|
5451
7155
|
const Comp = asChild ? Slot : "p";
|
|
5452
|
-
return /* @__PURE__ */ (0,
|
|
7156
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5453
7157
|
Comp,
|
|
5454
7158
|
{
|
|
5455
7159
|
ref: forwardedRef,
|
|
@@ -5496,21 +7200,21 @@ function resolveStepMessage(flow, copy, content) {
|
|
|
5496
7200
|
return "";
|
|
5497
7201
|
}
|
|
5498
7202
|
function PlanGrid({ className, children }) {
|
|
5499
|
-
return /* @__PURE__ */ (0,
|
|
5500
|
-
/* @__PURE__ */ (0,
|
|
5501
|
-
/* @__PURE__ */ (0,
|
|
5502
|
-
/* @__PURE__ */ (0,
|
|
5503
|
-
/* @__PURE__ */ (0,
|
|
7203
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PlanSelector.Grid, { className: className ?? "solvapay-checkout-plan-grid", children: children ?? /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(PlanSelector.Card, { className: "solvapay-checkout-plan-card", children: [
|
|
7204
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PlanSelector.CardBadge, { className: "solvapay-checkout-plan-card-badge" }),
|
|
7205
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PlanSelector.CardName, { className: "solvapay-checkout-plan-card-name" }),
|
|
7206
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PlanSelector.CardPrice, { className: "solvapay-checkout-plan-card-price" }),
|
|
7207
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PlanSelector.CardInterval, { className: "solvapay-checkout-plan-card-interval" })
|
|
5504
7208
|
] }) });
|
|
5505
7209
|
}
|
|
5506
|
-
var PlanContinueButton = (0,
|
|
7210
|
+
var PlanContinueButton = (0, import_react36.forwardRef)(
|
|
5507
7211
|
function PlanContinueButton2({ className, children, onClick, disabled, ...rest }, ref) {
|
|
5508
7212
|
const flow = useCheckoutContext("PlanContinueButton");
|
|
5509
7213
|
const locale = useLocale();
|
|
5510
7214
|
const selectedPlanShape = flow.selectedPlan;
|
|
5511
7215
|
const isDisabled = disabled || !flow.selectedPlanRef || flow.status === "activating";
|
|
5512
7216
|
const label = children ?? formatContinueLabel(selectedPlanShape, locale);
|
|
5513
|
-
return /* @__PURE__ */ (0,
|
|
7217
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5514
7218
|
"button",
|
|
5515
7219
|
{
|
|
5516
7220
|
ref,
|
|
@@ -5533,13 +7237,13 @@ var PlanContinueButton = (0, import_react34.forwardRef)(
|
|
|
5533
7237
|
function AmountPicker2({ className, children }) {
|
|
5534
7238
|
const flow = useCheckoutContext("AmountPicker");
|
|
5535
7239
|
if (!flow.topupCurrencyReady || flow.topupCurrency == null) {
|
|
5536
|
-
return /* @__PURE__ */ (0,
|
|
7240
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5537
7241
|
"div",
|
|
5538
7242
|
{
|
|
5539
7243
|
className: className ?? "solvapay-amount-picker",
|
|
5540
7244
|
"data-state": "loading",
|
|
5541
7245
|
"aria-busy": "true",
|
|
5542
|
-
children: /* @__PURE__ */ (0,
|
|
7246
|
+
children: /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "solvapay-amount-picker-pills", children: [0, 1, 2, 3].map((i) => /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5543
7247
|
"span",
|
|
5544
7248
|
{
|
|
5545
7249
|
className: "solvapay-amount-picker-pill",
|
|
@@ -5551,7 +7255,7 @@ function AmountPicker2({ className, children }) {
|
|
|
5551
7255
|
}
|
|
5552
7256
|
);
|
|
5553
7257
|
}
|
|
5554
|
-
return /* @__PURE__ */ (0,
|
|
7258
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5555
7259
|
AmountPicker.Root,
|
|
5556
7260
|
{
|
|
5557
7261
|
currency: flow.topupCurrency,
|
|
@@ -5562,16 +7266,16 @@ function AmountPicker2({ className, children }) {
|
|
|
5562
7266
|
flow.selectAmount(value);
|
|
5563
7267
|
}
|
|
5564
7268
|
},
|
|
5565
|
-
children: children ?? /* @__PURE__ */ (0,
|
|
7269
|
+
children: children ?? /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(DefaultAmountTree, {})
|
|
5566
7270
|
}
|
|
5567
7271
|
);
|
|
5568
7272
|
}
|
|
5569
7273
|
function DefaultAmountTree() {
|
|
5570
7274
|
const ctx = useAmountPicker();
|
|
5571
7275
|
const { selectAmountLabel, customAmountLabel, creditEstimate } = useAmountPickerCopy();
|
|
5572
|
-
return /* @__PURE__ */ (0,
|
|
5573
|
-
/* @__PURE__ */ (0,
|
|
5574
|
-
/* @__PURE__ */ (0,
|
|
7276
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(import_jsx_runtime24.Fragment, { children: [
|
|
7277
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "solvapay-amount-picker-label", children: selectAmountLabel }),
|
|
7278
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "solvapay-amount-picker-pills", children: ctx.quickAmounts.map((amount) => /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5575
7279
|
AmountPicker.Option,
|
|
5576
7280
|
{
|
|
5577
7281
|
amount,
|
|
@@ -5579,11 +7283,11 @@ function DefaultAmountTree() {
|
|
|
5579
7283
|
},
|
|
5580
7284
|
amount
|
|
5581
7285
|
)) }),
|
|
5582
|
-
/* @__PURE__ */ (0,
|
|
5583
|
-
/* @__PURE__ */ (0,
|
|
5584
|
-
/* @__PURE__ */ (0,
|
|
5585
|
-
/* @__PURE__ */ (0,
|
|
5586
|
-
/* @__PURE__ */ (0,
|
|
7286
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-amount-picker-custom-wrapper", children: [
|
|
7287
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "solvapay-amount-picker-custom-label", children: customAmountLabel }),
|
|
7288
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-amount-picker-custom-row", children: [
|
|
7289
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "solvapay-amount-picker-currency-symbol", children: ctx.currencySymbol }),
|
|
7290
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5587
7291
|
AmountPicker.Custom,
|
|
5588
7292
|
{
|
|
5589
7293
|
className: "solvapay-amount-picker-custom-input",
|
|
@@ -5592,7 +7296,7 @@ function DefaultAmountTree() {
|
|
|
5592
7296
|
)
|
|
5593
7297
|
] })
|
|
5594
7298
|
] }),
|
|
5595
|
-
/* @__PURE__ */ (0,
|
|
7299
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5596
7300
|
"p",
|
|
5597
7301
|
{
|
|
5598
7302
|
className: "solvapay-amount-picker-credit-estimate",
|
|
@@ -5602,7 +7306,7 @@ function DefaultAmountTree() {
|
|
|
5602
7306
|
)
|
|
5603
7307
|
] });
|
|
5604
7308
|
}
|
|
5605
|
-
var AmountContinueButton = (0,
|
|
7309
|
+
var AmountContinueButton = (0, import_react36.forwardRef)(
|
|
5606
7310
|
function AmountContinueButton2({ className, children, onClick, disabled, ...rest }, ref) {
|
|
5607
7311
|
const flow = useCheckoutContext("AmountContinueButton");
|
|
5608
7312
|
const locale = useLocale();
|
|
@@ -5611,7 +7315,7 @@ var AmountContinueButton = (0, import_react34.forwardRef)(
|
|
|
5611
7315
|
const ready = flow.topupCurrencyReady && currency != null;
|
|
5612
7316
|
const isDisabled = disabled || !ready || amountMinor == null;
|
|
5613
7317
|
const label = children ?? (ready && currency != null && amountMinor != null ? `Continue \u2014 ${formatPrice(amountMinor, currency, { locale })}` : "Continue");
|
|
5614
|
-
return /* @__PURE__ */ (0,
|
|
7318
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(
|
|
5615
7319
|
"button",
|
|
5616
7320
|
{
|
|
5617
7321
|
ref,
|
|
@@ -5634,10 +7338,10 @@ var AmountContinueButton = (0, import_react34.forwardRef)(
|
|
|
5634
7338
|
function Payment({ className }) {
|
|
5635
7339
|
const flow = useCheckoutContext("Payment");
|
|
5636
7340
|
if (flow.branch === "payg") {
|
|
5637
|
-
return /* @__PURE__ */ (0,
|
|
7341
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PaygPayment, { className });
|
|
5638
7342
|
}
|
|
5639
7343
|
if (flow.branch === "recurring") {
|
|
5640
|
-
return /* @__PURE__ */ (0,
|
|
7344
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(RecurringPayment, { className });
|
|
5641
7345
|
}
|
|
5642
7346
|
return null;
|
|
5643
7347
|
}
|
|
@@ -5651,12 +7355,12 @@ function PaygPayment({ className }) {
|
|
|
5651
7355
|
const currency = flow.topupCurrency;
|
|
5652
7356
|
if (!selectedPlanShape || amountMinor == null || currency == null) return null;
|
|
5653
7357
|
const creditsAdded = creditsPerMinorUnit != null && creditsPerMinorUnit > 0 ? Math.floor(amountMinor / (displayExchangeRate ?? 1) * creditsPerMinorUnit) : null;
|
|
5654
|
-
return /* @__PURE__ */ (0,
|
|
5655
|
-
/* @__PURE__ */ (0,
|
|
5656
|
-
/* @__PURE__ */ (0,
|
|
5657
|
-
creditsAdded != null ? /* @__PURE__ */ (0,
|
|
7358
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: className ?? "solvapay-checkout-payment", "data-branch": "payg", children: [
|
|
7359
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "solvapay-checkout-order-summary", "data-variant": "payg", children: /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-order-summary-row", children: [
|
|
7360
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { children: creditsAdded != null ? `${creditsAdded.toLocaleString(locale)} credits` : formatPrice(amountMinor, currency, { locale }) }),
|
|
7361
|
+
creditsAdded != null ? /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { children: formatPrice(amountMinor, currency, { locale }) }) : null
|
|
5658
7362
|
] }) }),
|
|
5659
|
-
/* @__PURE__ */ (0,
|
|
7363
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(
|
|
5660
7364
|
TopupForm.Root,
|
|
5661
7365
|
{
|
|
5662
7366
|
amount: amountMinor,
|
|
@@ -5665,11 +7369,11 @@ function PaygPayment({ className }) {
|
|
|
5665
7369
|
className: "solvapay-checkout-topup-form",
|
|
5666
7370
|
onSuccess: (intent, extras) => flow.notifyPaymentSuccess(intent, extras),
|
|
5667
7371
|
children: [
|
|
5668
|
-
/* @__PURE__ */ (0,
|
|
5669
|
-
/* @__PURE__ */ (0,
|
|
5670
|
-
/* @__PURE__ */ (0,
|
|
5671
|
-
/* @__PURE__ */ (0,
|
|
5672
|
-
/* @__PURE__ */ (0,
|
|
7372
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(TopupForm.Loading, {}),
|
|
7373
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(TopupForm.PaymentElement, {}),
|
|
7374
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(TopupForm.Error, { className: "solvapay-checkout-error" }),
|
|
7375
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(MandateText, { mode: "topup", amountMinor, currency }),
|
|
7376
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(TopupForm.SubmitButton, { className: "solvapay-checkout-pay-button", children: [
|
|
5673
7377
|
"Pay ",
|
|
5674
7378
|
formatPrice(amountMinor, currency, { locale })
|
|
5675
7379
|
] })
|
|
@@ -5692,12 +7396,12 @@ function RecurringPayment({ className }) {
|
|
|
5692
7396
|
const isRecurring = !!cycle;
|
|
5693
7397
|
const formattedAmount = formatPrice(amountMinor, currency, { locale });
|
|
5694
7398
|
const priceLine = isRecurring ? `${formattedAmount}/${shortCycle(cycle)}` : formattedAmount;
|
|
5695
|
-
return /* @__PURE__ */ (0,
|
|
5696
|
-
/* @__PURE__ */ (0,
|
|
5697
|
-
/* @__PURE__ */ (0,
|
|
5698
|
-
/* @__PURE__ */ (0,
|
|
7399
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: className ?? "solvapay-checkout-payment", "data-branch": "recurring", children: [
|
|
7400
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "solvapay-checkout-order-summary", "data-variant": "recurring", children: /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-order-summary-row", children: [
|
|
7401
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { children: planName }),
|
|
7402
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { children: priceLine })
|
|
5699
7403
|
] }) }),
|
|
5700
|
-
/* @__PURE__ */ (0,
|
|
7404
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(
|
|
5701
7405
|
PaymentForm.Root,
|
|
5702
7406
|
{
|
|
5703
7407
|
planRef: flow.selectedPlanRef,
|
|
@@ -5706,28 +7410,28 @@ function RecurringPayment({ className }) {
|
|
|
5706
7410
|
requireTermsAcceptance: false,
|
|
5707
7411
|
onSuccess: (intent) => flow.notifyPaymentSuccess(intent),
|
|
5708
7412
|
children: [
|
|
5709
|
-
/* @__PURE__ */ (0,
|
|
5710
|
-
/* @__PURE__ */ (0,
|
|
5711
|
-
/* @__PURE__ */ (0,
|
|
5712
|
-
/* @__PURE__ */ (0,
|
|
5713
|
-
/* @__PURE__ */ (0,
|
|
7413
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PaymentForm.Loading, {}),
|
|
7414
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PaymentForm.PaymentElement, {}),
|
|
7415
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PaymentForm.Error, { className: "solvapay-checkout-error" }),
|
|
7416
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PaymentForm.MandateText, {}),
|
|
7417
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)(PaymentForm.SubmitButton, { className: "solvapay-checkout-pay-button", children: isRecurring ? `Subscribe \u2014 ${priceLine}` : `Pay ${formattedAmount}` })
|
|
5714
7418
|
]
|
|
5715
7419
|
}
|
|
5716
7420
|
)
|
|
5717
7421
|
] });
|
|
5718
7422
|
}
|
|
5719
|
-
var CheckoutEnvContext = (0,
|
|
7423
|
+
var CheckoutEnvContext = (0, import_react36.createContext)(null);
|
|
5720
7424
|
function useReturnUrl() {
|
|
5721
|
-
return (0,
|
|
7425
|
+
return (0, import_react36.useContext)(CheckoutEnvContext)?.returnUrl ?? "";
|
|
5722
7426
|
}
|
|
5723
7427
|
function useProductRef() {
|
|
5724
|
-
return (0,
|
|
7428
|
+
return (0, import_react36.useContext)(CheckoutEnvContext)?.productRef ?? "";
|
|
5725
7429
|
}
|
|
5726
|
-
var BackLink = (0,
|
|
7430
|
+
var BackLink = (0, import_react36.forwardRef)(function CheckoutStepsBackLink({ label, glyph = "\u2190", className, onClick, ...rest }, ref) {
|
|
5727
7431
|
const flow = useCheckoutContext("BackLink");
|
|
5728
7432
|
if (!flow.canGoBack) return null;
|
|
5729
7433
|
const resolvedLabel = label ?? (flow.step === "payment" && flow.branch === "payg" ? "Change amount" : flow.step === "payment" && flow.branch === "recurring" ? "Change plan" : "Back");
|
|
5730
|
-
return /* @__PURE__ */ (0,
|
|
7434
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)(
|
|
5731
7435
|
"button",
|
|
5732
7436
|
{
|
|
5733
7437
|
ref,
|
|
@@ -5741,8 +7445,8 @@ var BackLink = (0, import_react34.forwardRef)(function CheckoutStepsBackLink({ l
|
|
|
5741
7445
|
},
|
|
5742
7446
|
...rest,
|
|
5743
7447
|
children: [
|
|
5744
|
-
/* @__PURE__ */ (0,
|
|
5745
|
-
/* @__PURE__ */ (0,
|
|
7448
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "solvapay-checkout-back-link-glyph", "aria-hidden": "true", children: glyph }),
|
|
7449
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("span", { className: "solvapay-checkout-back-link-label", children: resolvedLabel })
|
|
5746
7450
|
]
|
|
5747
7451
|
}
|
|
5748
7452
|
);
|
|
@@ -5752,74 +7456,74 @@ function Success({ className, children }) {
|
|
|
5752
7456
|
const locale = useLocale();
|
|
5753
7457
|
if (flow.step !== "success" || !flow.successMeta) return null;
|
|
5754
7458
|
if (children) {
|
|
5755
|
-
return /* @__PURE__ */ (0,
|
|
7459
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: className ?? "solvapay-checkout-success", children });
|
|
5756
7460
|
}
|
|
5757
7461
|
const meta = flow.successMeta;
|
|
5758
7462
|
if (meta.branch === "payg") {
|
|
5759
|
-
return /* @__PURE__ */ (0,
|
|
5760
|
-
/* @__PURE__ */ (0,
|
|
5761
|
-
/* @__PURE__ */ (0,
|
|
5762
|
-
/* @__PURE__ */ (0,
|
|
5763
|
-
/* @__PURE__ */ (0,
|
|
5764
|
-
/* @__PURE__ */ (0,
|
|
5765
|
-
/* @__PURE__ */ (0,
|
|
5766
|
-
/* @__PURE__ */ (0,
|
|
7463
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: className ?? "solvapay-checkout-success", "data-branch": "payg", children: [
|
|
7464
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "solvapay-checkout-success-check", "aria-hidden": "true", children: "\u2713" }),
|
|
7465
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("h2", { className: "solvapay-checkout-success-heading", children: "Credits added" }),
|
|
7466
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "solvapay-checkout-success-subheading", children: "Pay as you go plan is active." }),
|
|
7467
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("dl", { className: "solvapay-checkout-receipt", "data-variant": "payg", children: [
|
|
7468
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-receipt-row", children: [
|
|
7469
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dt", { children: "Amount" }),
|
|
7470
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dd", { children: formatPrice(meta.amountMinor, meta.currency, { locale }) })
|
|
5767
7471
|
] }),
|
|
5768
|
-
/* @__PURE__ */ (0,
|
|
5769
|
-
/* @__PURE__ */ (0,
|
|
5770
|
-
/* @__PURE__ */ (0,
|
|
7472
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-receipt-row", children: [
|
|
7473
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dt", { children: "Credits" }),
|
|
7474
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("dd", { children: [
|
|
5771
7475
|
"+",
|
|
5772
7476
|
meta.creditsAdded.toLocaleString(locale)
|
|
5773
7477
|
] })
|
|
5774
7478
|
] }),
|
|
5775
|
-
/* @__PURE__ */ (0,
|
|
5776
|
-
/* @__PURE__ */ (0,
|
|
5777
|
-
/* @__PURE__ */ (0,
|
|
7479
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-receipt-row", children: [
|
|
7480
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dt", { children: "Plan" }),
|
|
7481
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dd", { children: meta.plan.name ?? "Pay as you go" })
|
|
5778
7482
|
] }),
|
|
5779
|
-
/* @__PURE__ */ (0,
|
|
5780
|
-
/* @__PURE__ */ (0,
|
|
5781
|
-
/* @__PURE__ */ (0,
|
|
7483
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-receipt-row", children: [
|
|
7484
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dt", { children: "Rate" }),
|
|
7485
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dd", { children: meta.rateLabel })
|
|
5782
7486
|
] })
|
|
5783
7487
|
] })
|
|
5784
7488
|
] });
|
|
5785
7489
|
}
|
|
5786
|
-
return /* @__PURE__ */ (0,
|
|
5787
|
-
/* @__PURE__ */ (0,
|
|
5788
|
-
/* @__PURE__ */ (0,
|
|
7490
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: className ?? "solvapay-checkout-success", "data-branch": "recurring", children: [
|
|
7491
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("div", { className: "solvapay-checkout-success-check", "aria-hidden": "true", children: "\u2713" }),
|
|
7492
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("h2", { className: "solvapay-checkout-success-heading", children: [
|
|
5789
7493
|
meta.plan.name ?? "Plan",
|
|
5790
7494
|
" active"
|
|
5791
7495
|
] }),
|
|
5792
|
-
/* @__PURE__ */ (0,
|
|
5793
|
-
/* @__PURE__ */ (0,
|
|
5794
|
-
/* @__PURE__ */ (0,
|
|
5795
|
-
/* @__PURE__ */ (0,
|
|
5796
|
-
/* @__PURE__ */ (0,
|
|
7496
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("p", { className: "solvapay-checkout-success-subheading", children: "Subscription is live and credits are ready." }),
|
|
7497
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("dl", { className: "solvapay-checkout-receipt", "data-variant": "recurring", children: [
|
|
7498
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-receipt-row", children: [
|
|
7499
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dt", { children: "Plan" }),
|
|
7500
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dd", { children: meta.plan.name ?? "Plan" })
|
|
5797
7501
|
] }),
|
|
5798
|
-
meta.creditsIncluded > 0 ? /* @__PURE__ */ (0,
|
|
5799
|
-
/* @__PURE__ */ (0,
|
|
5800
|
-
/* @__PURE__ */ (0,
|
|
7502
|
+
meta.creditsIncluded > 0 ? /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-receipt-row", children: [
|
|
7503
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dt", { children: "Credits" }),
|
|
7504
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("dd", { children: [
|
|
5801
7505
|
"+",
|
|
5802
7506
|
meta.creditsIncluded.toLocaleString(locale)
|
|
5803
7507
|
] })
|
|
5804
7508
|
] }) : null,
|
|
5805
|
-
/* @__PURE__ */ (0,
|
|
5806
|
-
/* @__PURE__ */ (0,
|
|
5807
|
-
/* @__PURE__ */ (0,
|
|
7509
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-receipt-row", children: [
|
|
7510
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dt", { children: "Charged today" }),
|
|
7511
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dd", { children: formatPrice(meta.chargedTodayMinor, meta.currency, { locale }) })
|
|
5808
7512
|
] }),
|
|
5809
|
-
meta.nextRenewalLabel ? /* @__PURE__ */ (0,
|
|
5810
|
-
/* @__PURE__ */ (0,
|
|
5811
|
-
/* @__PURE__ */ (0,
|
|
7513
|
+
meta.nextRenewalLabel ? /* @__PURE__ */ (0, import_jsx_runtime24.jsxs)("div", { className: "solvapay-checkout-receipt-row", children: [
|
|
7514
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dt", { children: "Next renewal" }),
|
|
7515
|
+
/* @__PURE__ */ (0, import_jsx_runtime24.jsx)("dd", { children: meta.nextRenewalLabel })
|
|
5812
7516
|
] }) : null
|
|
5813
7517
|
] })
|
|
5814
7518
|
] });
|
|
5815
7519
|
}
|
|
5816
|
-
var RootWithEnv = (0,
|
|
7520
|
+
var RootWithEnv = (0, import_react36.forwardRef)(
|
|
5817
7521
|
function CheckoutStepsRootWithEnv(props, forwardedRef) {
|
|
5818
|
-
const env = (0,
|
|
7522
|
+
const env = (0, import_react36.useMemo)(
|
|
5819
7523
|
() => ({ returnUrl: props.returnUrl, productRef: props.productRef }),
|
|
5820
7524
|
[props.returnUrl, props.productRef]
|
|
5821
7525
|
);
|
|
5822
|
-
return /* @__PURE__ */ (0,
|
|
7526
|
+
return /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(CheckoutEnvContext.Provider, { value: env, children: /* @__PURE__ */ (0, import_jsx_runtime24.jsx)(Root11, { ...props, ref: forwardedRef }) });
|
|
5823
7527
|
}
|
|
5824
7528
|
);
|
|
5825
7529
|
var CheckoutSteps = {
|
|
@@ -5848,7 +7552,7 @@ var CheckoutStepsBackLink2 = BackLink;
|
|
|
5848
7552
|
var CheckoutStepsSuccess = Success;
|
|
5849
7553
|
|
|
5850
7554
|
// src/hooks/usePaywallResolver.ts
|
|
5851
|
-
var
|
|
7555
|
+
var import_react37 = require("react");
|
|
5852
7556
|
function balanceCoversNextUnit(balance, credits) {
|
|
5853
7557
|
if (!balance) return false;
|
|
5854
7558
|
if (typeof balance.remainingUnits === "number" && balance.remainingUnits > 0) {
|
|
@@ -5862,7 +7566,7 @@ function balanceCoversNextUnit(balance, credits) {
|
|
|
5862
7566
|
function usePaywallResolver(content) {
|
|
5863
7567
|
const { activePurchase, hasPaidPurchase, refetch: refetchPurchase } = usePurchase();
|
|
5864
7568
|
const { credits, refetch: refetchBalance } = useBalance();
|
|
5865
|
-
const resolved = (0,
|
|
7569
|
+
const resolved = (0, import_react37.useMemo)(() => {
|
|
5866
7570
|
if (!content) return false;
|
|
5867
7571
|
const productMatches = !content.product || activePurchase?.productRef === content.product || activePurchase?.productName === content.product;
|
|
5868
7572
|
if (content.kind === "payment_required") {
|
|
@@ -5872,7 +7576,7 @@ function usePaywallResolver(content) {
|
|
|
5872
7576
|
if (balanceCoversNextUnit(content.balance, credits)) return true;
|
|
5873
7577
|
return Boolean(productMatches && activePurchase?.status === "active");
|
|
5874
7578
|
}, [content, hasPaidPurchase, activePurchase, credits]);
|
|
5875
|
-
const refetch = (0,
|
|
7579
|
+
const refetch = (0, import_react37.useCallback)(async () => {
|
|
5876
7580
|
await Promise.all([
|
|
5877
7581
|
refetchPurchase().catch(() => void 0),
|
|
5878
7582
|
refetchBalance().catch(() => void 0)
|
|
@@ -5882,32 +7586,32 @@ function usePaywallResolver(content) {
|
|
|
5882
7586
|
}
|
|
5883
7587
|
|
|
5884
7588
|
// src/primitives/PaywallNotice.tsx
|
|
5885
|
-
var
|
|
5886
|
-
var PaywallNoticeContext = (0,
|
|
7589
|
+
var import_jsx_runtime25 = require("react/jsx-runtime");
|
|
7590
|
+
var PaywallNoticeContext = (0, import_react38.createContext)(null);
|
|
5887
7591
|
function usePaywallNoticeCtx(part) {
|
|
5888
|
-
const ctx = (0,
|
|
7592
|
+
const ctx = (0, import_react38.useContext)(PaywallNoticeContext);
|
|
5889
7593
|
if (!ctx) {
|
|
5890
7594
|
throw new Error(`PaywallNotice.${part} must be rendered inside <PaywallNotice.Root>.`);
|
|
5891
7595
|
}
|
|
5892
7596
|
return ctx;
|
|
5893
7597
|
}
|
|
5894
|
-
var
|
|
7598
|
+
var Root12 = (0, import_react38.forwardRef)(function PaywallNoticeRoot({ content, onResolved, classNames, asChild, children, ...rest }, forwardedRef) {
|
|
5895
7599
|
const { resolved, refetch } = usePaywallResolver(content);
|
|
5896
|
-
const classNamesResolved = (0,
|
|
5897
|
-
const onResolvedRef = (0,
|
|
5898
|
-
(0,
|
|
7600
|
+
const classNamesResolved = (0, import_react38.useMemo)(() => classNames ?? {}, [classNames]);
|
|
7601
|
+
const onResolvedRef = (0, import_react38.useRef)(onResolved);
|
|
7602
|
+
(0, import_react38.useEffect)(() => {
|
|
5899
7603
|
onResolvedRef.current = onResolved;
|
|
5900
7604
|
}, [onResolved]);
|
|
5901
|
-
const hasResolvedRef = (0,
|
|
5902
|
-
const signalResolved = (0,
|
|
7605
|
+
const hasResolvedRef = (0, import_react38.useRef)(false);
|
|
7606
|
+
const signalResolved = (0, import_react38.useCallback)(() => {
|
|
5903
7607
|
if (hasResolvedRef.current) return;
|
|
5904
7608
|
hasResolvedRef.current = true;
|
|
5905
7609
|
onResolvedRef.current?.();
|
|
5906
7610
|
}, []);
|
|
5907
|
-
(0,
|
|
7611
|
+
(0, import_react38.useEffect)(() => {
|
|
5908
7612
|
if (resolved) signalResolved();
|
|
5909
7613
|
}, [resolved, signalResolved]);
|
|
5910
|
-
const ctx = (0,
|
|
7614
|
+
const ctx = (0, import_react38.useMemo)(
|
|
5911
7615
|
() => ({
|
|
5912
7616
|
content,
|
|
5913
7617
|
resolved,
|
|
@@ -5918,7 +7622,7 @@ var Root11 = (0, import_react36.forwardRef)(function PaywallNoticeRoot({ content
|
|
|
5918
7622
|
[content, resolved, refetch, signalResolved, classNamesResolved]
|
|
5919
7623
|
);
|
|
5920
7624
|
const Comp = asChild ? Slot : "div";
|
|
5921
|
-
return /* @__PURE__ */ (0,
|
|
7625
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PaywallNoticeContext.Provider, { value: ctx, children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
5922
7626
|
Comp,
|
|
5923
7627
|
{
|
|
5924
7628
|
ref: forwardedRef,
|
|
@@ -5931,12 +7635,12 @@ var Root11 = (0, import_react36.forwardRef)(function PaywallNoticeRoot({ content
|
|
|
5931
7635
|
}
|
|
5932
7636
|
) });
|
|
5933
7637
|
});
|
|
5934
|
-
var Heading4 = (0,
|
|
7638
|
+
var Heading4 = (0, import_react38.forwardRef)(function PaywallNoticeHeading({ asChild, children, className, ...rest }, forwardedRef) {
|
|
5935
7639
|
const ctx = usePaywallNoticeCtx("Heading");
|
|
5936
7640
|
const copy = useCopy();
|
|
5937
7641
|
const defaultText = ctx.resolved ? copy.paywall.resolvedHeading : ctx.content.kind === "payment_required" ? copy.paywall.paymentRequiredHeading : isTopupGate(ctx.content) ? copy.paywall.topupRequiredHeading : copy.paywall.activationRequiredHeading;
|
|
5938
7642
|
const Comp = asChild ? Slot : "h2";
|
|
5939
|
-
return /* @__PURE__ */ (0,
|
|
7643
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
5940
7644
|
Comp,
|
|
5941
7645
|
{
|
|
5942
7646
|
ref: forwardedRef,
|
|
@@ -5947,12 +7651,12 @@ var Heading4 = (0, import_react36.forwardRef)(function PaywallNoticeHeading({ as
|
|
|
5947
7651
|
}
|
|
5948
7652
|
);
|
|
5949
7653
|
});
|
|
5950
|
-
var Message = (0,
|
|
7654
|
+
var Message = (0, import_react38.forwardRef)(function PaywallNoticeMessage({ asChild, children, className, ...rest }, forwardedRef) {
|
|
5951
7655
|
const ctx = usePaywallNoticeCtx("Message");
|
|
5952
7656
|
const copy = useCopy();
|
|
5953
7657
|
const Comp = asChild ? Slot : "p";
|
|
5954
7658
|
const defaultText = resolvePaywallMessage(ctx.content, copy.paywall);
|
|
5955
|
-
return /* @__PURE__ */ (0,
|
|
7659
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
5956
7660
|
Comp,
|
|
5957
7661
|
{
|
|
5958
7662
|
ref: forwardedRef,
|
|
@@ -5995,14 +7699,14 @@ function resolvePaywallMessage(content, paywallCopy) {
|
|
|
5995
7699
|
}
|
|
5996
7700
|
return content.message ?? "";
|
|
5997
7701
|
}
|
|
5998
|
-
var ProductContext = (0,
|
|
7702
|
+
var ProductContext = (0, import_react38.forwardRef)(function PaywallNoticeProductContext({ asChild, children, className, ...rest }, forwardedRef) {
|
|
5999
7703
|
const ctx = usePaywallNoticeCtx("ProductContext");
|
|
6000
7704
|
const copy = useCopy();
|
|
6001
7705
|
const product = ctx.content.kind === "activation_required" ? ctx.content.productDetails : void 0;
|
|
6002
7706
|
if (!product?.name) return null;
|
|
6003
7707
|
const label = interpolate(copy.paywall.productContext, { product: product.name });
|
|
6004
7708
|
const Comp = asChild ? Slot : "div";
|
|
6005
|
-
return /* @__PURE__ */ (0,
|
|
7709
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
6006
7710
|
Comp,
|
|
6007
7711
|
{
|
|
6008
7712
|
ref: forwardedRef,
|
|
@@ -6013,7 +7717,7 @@ var ProductContext = (0, import_react36.forwardRef)(function PaywallNoticeProduc
|
|
|
6013
7717
|
}
|
|
6014
7718
|
);
|
|
6015
7719
|
});
|
|
6016
|
-
var Balance = (0,
|
|
7720
|
+
var Balance = (0, import_react38.forwardRef)(function PaywallNoticeBalance({ asChild, children, className, ...rest }, forwardedRef) {
|
|
6017
7721
|
const ctx = usePaywallNoticeCtx("Balance");
|
|
6018
7722
|
const copy = useCopy();
|
|
6019
7723
|
const balance = ctx.content.balance;
|
|
@@ -6023,7 +7727,7 @@ var Balance = (0, import_react36.forwardRef)(function PaywallNoticeBalance({ asC
|
|
|
6023
7727
|
required: String(balance.creditsPerUnit ?? 1)
|
|
6024
7728
|
});
|
|
6025
7729
|
const Comp = asChild ? Slot : "div";
|
|
6026
|
-
return /* @__PURE__ */ (0,
|
|
7730
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
6027
7731
|
Comp,
|
|
6028
7732
|
{
|
|
6029
7733
|
ref: forwardedRef,
|
|
@@ -6039,27 +7743,27 @@ function Plans({ className, children }) {
|
|
|
6039
7743
|
if (ctx.content.kind !== "activation_required") return null;
|
|
6040
7744
|
if (!ctx.content.product) return null;
|
|
6041
7745
|
const defaultClass = className ?? ctx.classNames.plans ?? "solvapay-paywall-plans";
|
|
6042
|
-
return /* @__PURE__ */ (0,
|
|
6043
|
-
/* @__PURE__ */ (0,
|
|
6044
|
-
/* @__PURE__ */ (0,
|
|
6045
|
-
/* @__PURE__ */ (0,
|
|
6046
|
-
/* @__PURE__ */ (0,
|
|
6047
|
-
/* @__PURE__ */ (0,
|
|
7746
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)("div", { "data-solvapay-paywall-plans": "", className: defaultClass, children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.Root, { productRef: ctx.content.product, filter: hidesFreePlan, children: children ?? /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(import_jsx_runtime25.Fragment, { children: [
|
|
7747
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.Grid, { children: /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(PlanSelector.Card, { children: [
|
|
7748
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.CardBadge, {}),
|
|
7749
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.CardName, {}),
|
|
7750
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.CardPrice, {}),
|
|
7751
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.CardInterval, {})
|
|
6048
7752
|
] }) }),
|
|
6049
|
-
/* @__PURE__ */ (0,
|
|
6050
|
-
/* @__PURE__ */ (0,
|
|
7753
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.Loading, {}),
|
|
7754
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.Error, {})
|
|
6051
7755
|
] }) }) });
|
|
6052
7756
|
}
|
|
6053
7757
|
function hidesFreePlan(plan) {
|
|
6054
7758
|
return plan.requiresPayment !== false;
|
|
6055
7759
|
}
|
|
6056
|
-
var HostedCheckoutLink = (0,
|
|
7760
|
+
var HostedCheckoutLink = (0, import_react38.forwardRef)(function PaywallNoticeHostedCheckoutLink({ asChild, children, className, ...rest }, forwardedRef) {
|
|
6057
7761
|
const ctx = usePaywallNoticeCtx("HostedCheckoutLink");
|
|
6058
7762
|
const copy = useCopy();
|
|
6059
7763
|
const href = ctx.content.checkoutUrl;
|
|
6060
7764
|
if (!href) return null;
|
|
6061
7765
|
const Comp = asChild ? Slot : "a";
|
|
6062
|
-
return /* @__PURE__ */ (0,
|
|
7766
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
6063
7767
|
Comp,
|
|
6064
7768
|
{
|
|
6065
7769
|
ref: forwardedRef,
|
|
@@ -6077,12 +7781,12 @@ function EmbeddedCheckout({ returnUrl, topupCurrency, className }) {
|
|
|
6077
7781
|
const ctx = usePaywallNoticeCtx("EmbeddedCheckout");
|
|
6078
7782
|
const productRef = ctx.content.product;
|
|
6079
7783
|
const { plans } = usePlans({ productRef: productRef ?? void 0 });
|
|
6080
|
-
const filter = (0,
|
|
7784
|
+
const filter = (0, import_react38.useMemo)(() => buildDefaultCheckoutPlanFilter(plans), [plans]);
|
|
6081
7785
|
if (!productRef) return null;
|
|
6082
7786
|
const resolvedClassName = className ?? ctx.classNames.embeddedCheckout ?? "solvapay-paywall-embedded-checkout";
|
|
6083
7787
|
const headingClassName = ctx.classNames.heading ?? "solvapay-paywall-step-heading";
|
|
6084
7788
|
const messageClassName = ctx.classNames.message ?? "solvapay-paywall-step-message";
|
|
6085
|
-
return /* @__PURE__ */ (0,
|
|
7789
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(
|
|
6086
7790
|
CheckoutSteps.Root,
|
|
6087
7791
|
{
|
|
6088
7792
|
productRef,
|
|
@@ -6095,33 +7799,33 @@ function EmbeddedCheckout({ returnUrl, topupCurrency, className }) {
|
|
|
6095
7799
|
},
|
|
6096
7800
|
className: resolvedClassName,
|
|
6097
7801
|
children: [
|
|
6098
|
-
/* @__PURE__ */ (0,
|
|
6099
|
-
/* @__PURE__ */ (0,
|
|
6100
|
-
/* @__PURE__ */ (0,
|
|
6101
|
-
/* @__PURE__ */ (0,
|
|
6102
|
-
/* @__PURE__ */ (0,
|
|
6103
|
-
/* @__PURE__ */ (0,
|
|
6104
|
-
/* @__PURE__ */ (0,
|
|
7802
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.StepHeading, { className: headingClassName }),
|
|
7803
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.StepMessage, { className: messageClassName }),
|
|
7804
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(CheckoutSteps.IfStep, { step: "plan", children: [
|
|
7805
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.PlanGrid, {}),
|
|
7806
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.Loading, {}),
|
|
7807
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(PlanSelector.Error, {}),
|
|
7808
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.PlanContinueButton, {})
|
|
6105
7809
|
] }),
|
|
6106
|
-
/* @__PURE__ */ (0,
|
|
6107
|
-
/* @__PURE__ */ (0,
|
|
6108
|
-
/* @__PURE__ */ (0,
|
|
6109
|
-
/* @__PURE__ */ (0,
|
|
7810
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(CheckoutSteps.IfStep, { step: "amount", children: [
|
|
7811
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.BackLink, {}),
|
|
7812
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.AmountPicker, {}),
|
|
7813
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.AmountContinueButton, {})
|
|
6110
7814
|
] }),
|
|
6111
|
-
/* @__PURE__ */ (0,
|
|
6112
|
-
/* @__PURE__ */ (0,
|
|
6113
|
-
/* @__PURE__ */ (0,
|
|
7815
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsxs)(CheckoutSteps.IfStep, { step: "payment", children: [
|
|
7816
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.BackLink, {}),
|
|
7817
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.Payment, {})
|
|
6114
7818
|
] }),
|
|
6115
|
-
/* @__PURE__ */ (0,
|
|
7819
|
+
/* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.IfStep, { step: "success", children: /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(CheckoutSteps.Success, {}) })
|
|
6116
7820
|
]
|
|
6117
7821
|
}
|
|
6118
7822
|
);
|
|
6119
7823
|
}
|
|
6120
|
-
var Retry = (0,
|
|
7824
|
+
var Retry = (0, import_react38.forwardRef)(function PaywallNoticeRetry({ asChild, children, className, onClick, ...rest }, forwardedRef) {
|
|
6121
7825
|
const ctx = usePaywallNoticeCtx("Retry");
|
|
6122
7826
|
const copy = useCopy();
|
|
6123
7827
|
const Comp = asChild ? Slot : "button";
|
|
6124
|
-
return /* @__PURE__ */ (0,
|
|
7828
|
+
return /* @__PURE__ */ (0, import_jsx_runtime25.jsx)(
|
|
6125
7829
|
Comp,
|
|
6126
7830
|
{
|
|
6127
7831
|
ref: forwardedRef,
|
|
@@ -6139,8 +7843,8 @@ var Retry = (0, import_react36.forwardRef)(function PaywallNoticeRetry({ asChild
|
|
|
6139
7843
|
}
|
|
6140
7844
|
);
|
|
6141
7845
|
});
|
|
6142
|
-
var PaywallNotice = Object.assign(
|
|
6143
|
-
Root:
|
|
7846
|
+
var PaywallNotice = Object.assign(Root12, {
|
|
7847
|
+
Root: Root12,
|
|
6144
7848
|
Heading: Heading4,
|
|
6145
7849
|
Message,
|
|
6146
7850
|
ProductContext,
|
|
@@ -6154,14 +7858,14 @@ function usePaywallNotice() {
|
|
|
6154
7858
|
return usePaywallNoticeCtx("usePaywallNotice");
|
|
6155
7859
|
}
|
|
6156
7860
|
function usePaywallNoticeOptional() {
|
|
6157
|
-
return (0,
|
|
7861
|
+
return (0, import_react38.useContext)(PaywallNoticeContext);
|
|
6158
7862
|
}
|
|
6159
7863
|
|
|
6160
7864
|
// src/primitives/UsageMeter.tsx
|
|
6161
|
-
var
|
|
7865
|
+
var import_react40 = require("react");
|
|
6162
7866
|
|
|
6163
7867
|
// src/hooks/useUsage.ts
|
|
6164
|
-
var
|
|
7868
|
+
var import_react39 = require("react");
|
|
6165
7869
|
function deriveUsage(purchase) {
|
|
6166
7870
|
if (!purchase) return null;
|
|
6167
7871
|
const snap = purchase.planSnapshot;
|
|
@@ -6186,16 +7890,16 @@ function deriveUsage(purchase) {
|
|
|
6186
7890
|
function useUsage() {
|
|
6187
7891
|
const { activePurchase, refetch: refetchPurchase, loading: purchaseLoading } = usePurchase();
|
|
6188
7892
|
const transport = useTransport();
|
|
6189
|
-
const [override, setOverride] = (0,
|
|
6190
|
-
const [error, setError] = (0,
|
|
6191
|
-
const [transportLoading, setTransportLoading] = (0,
|
|
6192
|
-
const derived = (0,
|
|
7893
|
+
const [override, setOverride] = (0, import_react39.useState)(null);
|
|
7894
|
+
const [error, setError] = (0, import_react39.useState)(null);
|
|
7895
|
+
const [transportLoading, setTransportLoading] = (0, import_react39.useState)(false);
|
|
7896
|
+
const derived = (0, import_react39.useMemo)(() => deriveUsage(activePurchase ?? null), [activePurchase]);
|
|
6193
7897
|
const activePurchaseRef = activePurchase?.reference ?? null;
|
|
6194
|
-
(0,
|
|
7898
|
+
(0, import_react39.useEffect)(() => {
|
|
6195
7899
|
setOverride(null);
|
|
6196
7900
|
}, [activePurchaseRef]);
|
|
6197
7901
|
const usage = override ?? derived;
|
|
6198
|
-
const refetch = (0,
|
|
7902
|
+
const refetch = (0, import_react39.useCallback)(async () => {
|
|
6199
7903
|
setError(null);
|
|
6200
7904
|
if (typeof transport.getUsage === "function") {
|
|
6201
7905
|
setTransportLoading(true);
|
|
@@ -6233,16 +7937,16 @@ function useUsage() {
|
|
|
6233
7937
|
}
|
|
6234
7938
|
|
|
6235
7939
|
// src/primitives/UsageMeter.tsx
|
|
6236
|
-
var
|
|
6237
|
-
var UsageMeterContext = (0,
|
|
7940
|
+
var import_jsx_runtime26 = require("react/jsx-runtime");
|
|
7941
|
+
var UsageMeterContext = (0, import_react40.createContext)(null);
|
|
6238
7942
|
function useUsageMeterCtx(part) {
|
|
6239
|
-
const ctx = (0,
|
|
7943
|
+
const ctx = (0, import_react40.useContext)(UsageMeterContext);
|
|
6240
7944
|
if (!ctx) {
|
|
6241
7945
|
throw new Error(`UsageMeter.${part} must be rendered inside <UsageMeter.Root>.`);
|
|
6242
7946
|
}
|
|
6243
7947
|
return ctx;
|
|
6244
7948
|
}
|
|
6245
|
-
var
|
|
7949
|
+
var Root13 = (0, import_react40.forwardRef)(function UsageMeterRoot({
|
|
6246
7950
|
warningAt = 75,
|
|
6247
7951
|
criticalAt = 90,
|
|
6248
7952
|
classNames,
|
|
@@ -6257,7 +7961,7 @@ var Root12 = (0, import_react38.forwardRef)(function UsageMeterRoot({
|
|
|
6257
7961
|
const loading = hookResult.loading && !usage;
|
|
6258
7962
|
const percentUsed = usage?.percentUsed ?? null;
|
|
6259
7963
|
const state = loading ? "loading" : percentUsed === null ? "safe" : percentUsed >= criticalAt ? "critical" : percentUsed >= warningAt ? "warning" : "safe";
|
|
6260
|
-
const ctx = (0,
|
|
7964
|
+
const ctx = (0, import_react40.useMemo)(
|
|
6261
7965
|
() => ({
|
|
6262
7966
|
usage,
|
|
6263
7967
|
loading,
|
|
@@ -6285,7 +7989,7 @@ var Root12 = (0, import_react38.forwardRef)(function UsageMeterRoot({
|
|
|
6285
7989
|
);
|
|
6286
7990
|
const rootClass = [classNames?.root ?? "solvapay-usage-meter", className].filter(Boolean).join(" ");
|
|
6287
7991
|
const Comp = asChild ? Slot : "div";
|
|
6288
|
-
return /* @__PURE__ */ (0,
|
|
7992
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(UsageMeterContext.Provider, { value: ctx, children: /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
6289
7993
|
Comp,
|
|
6290
7994
|
{
|
|
6291
7995
|
ref: forwardedRef,
|
|
@@ -6297,10 +8001,10 @@ var Root12 = (0, import_react38.forwardRef)(function UsageMeterRoot({
|
|
|
6297
8001
|
}
|
|
6298
8002
|
) });
|
|
6299
8003
|
});
|
|
6300
|
-
var Bar = (0,
|
|
8004
|
+
var Bar = (0, import_react40.forwardRef)(function UsageMeterBar({ className, style, ...rest }, forwardedRef) {
|
|
6301
8005
|
const ctx = useUsageMeterCtx("Bar");
|
|
6302
8006
|
const width = ctx.percentUsed === null ? 0 : Math.max(0, Math.min(100, ctx.percentUsed));
|
|
6303
|
-
return /* @__PURE__ */ (0,
|
|
8007
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
6304
8008
|
"div",
|
|
6305
8009
|
{
|
|
6306
8010
|
ref: forwardedRef,
|
|
@@ -6321,12 +8025,12 @@ var Bar = (0, import_react38.forwardRef)(function UsageMeterBar({ className, sty
|
|
|
6321
8025
|
}
|
|
6322
8026
|
);
|
|
6323
8027
|
});
|
|
6324
|
-
var Label = (0,
|
|
8028
|
+
var Label = (0, import_react40.forwardRef)(function UsageMeterLabel({ className, children, ...rest }, forwardedRef) {
|
|
6325
8029
|
const ctx = useUsageMeterCtx("Label");
|
|
6326
8030
|
const copy = useCopy();
|
|
6327
8031
|
if (!ctx.usage) return null;
|
|
6328
8032
|
if (ctx.isUnlimited) {
|
|
6329
|
-
return /* @__PURE__ */ (0,
|
|
8033
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
6330
8034
|
"span",
|
|
6331
8035
|
{
|
|
6332
8036
|
ref: forwardedRef,
|
|
@@ -6346,7 +8050,7 @@ var Label = (0, import_react38.forwardRef)(function UsageMeterLabel({ className,
|
|
|
6346
8050
|
remaining: String(ctx.usage.remaining ?? 0),
|
|
6347
8051
|
unit
|
|
6348
8052
|
});
|
|
6349
|
-
return /* @__PURE__ */ (0,
|
|
8053
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
6350
8054
|
"span",
|
|
6351
8055
|
{
|
|
6352
8056
|
ref: forwardedRef,
|
|
@@ -6357,11 +8061,11 @@ var Label = (0, import_react38.forwardRef)(function UsageMeterLabel({ className,
|
|
|
6357
8061
|
}
|
|
6358
8062
|
);
|
|
6359
8063
|
});
|
|
6360
|
-
var Percentage = (0,
|
|
8064
|
+
var Percentage = (0, import_react40.forwardRef)(function UsageMeterPercentage({ className, children, ...rest }, forwardedRef) {
|
|
6361
8065
|
const ctx = useUsageMeterCtx("Percentage");
|
|
6362
8066
|
const copy = useCopy();
|
|
6363
8067
|
if (ctx.percentUsed === null) return null;
|
|
6364
|
-
return /* @__PURE__ */ (0,
|
|
8068
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
6365
8069
|
"span",
|
|
6366
8070
|
{
|
|
6367
8071
|
ref: forwardedRef,
|
|
@@ -6378,14 +8082,14 @@ function formatResetsIn(copy, periodEnd, nowMs = typeof performance !== "undefin
|
|
|
6378
8082
|
const daysLeft = Math.max(0, Math.ceil((end - nowMs) / (24 * 60 * 60 * 1e3)));
|
|
6379
8083
|
return daysLeft > 0 ? interpolate(copy.usage.resetsInLabel, { days: String(daysLeft) }) : interpolate(copy.usage.resetsOnLabel, { date: new Date(periodEnd).toLocaleDateString() });
|
|
6380
8084
|
}
|
|
6381
|
-
var ResetsIn = (0,
|
|
8085
|
+
var ResetsIn = (0, import_react40.forwardRef)(function UsageMeterResetsIn({ className, children, ...rest }, forwardedRef) {
|
|
6382
8086
|
const ctx = useUsageMeterCtx("ResetsIn");
|
|
6383
8087
|
const copy = useCopy();
|
|
6384
8088
|
const periodEnd = ctx.usage?.periodEnd;
|
|
6385
8089
|
if (!periodEnd) return null;
|
|
6386
8090
|
const label = formatResetsIn(copy, periodEnd);
|
|
6387
8091
|
if (!label) return null;
|
|
6388
|
-
return /* @__PURE__ */ (0,
|
|
8092
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
6389
8093
|
"span",
|
|
6390
8094
|
{
|
|
6391
8095
|
ref: forwardedRef,
|
|
@@ -6396,11 +8100,11 @@ var ResetsIn = (0, import_react38.forwardRef)(function UsageMeterResetsIn({ clas
|
|
|
6396
8100
|
}
|
|
6397
8101
|
);
|
|
6398
8102
|
});
|
|
6399
|
-
var
|
|
8103
|
+
var Loading8 = (0, import_react40.forwardRef)(function UsageMeterLoading({ className, children, ...rest }, forwardedRef) {
|
|
6400
8104
|
const ctx = useUsageMeterCtx("Loading");
|
|
6401
8105
|
const copy = useCopy();
|
|
6402
8106
|
if (ctx.state !== "loading") return null;
|
|
6403
|
-
return /* @__PURE__ */ (0,
|
|
8107
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
6404
8108
|
"div",
|
|
6405
8109
|
{
|
|
6406
8110
|
ref: forwardedRef,
|
|
@@ -6411,11 +8115,11 @@ var Loading7 = (0, import_react38.forwardRef)(function UsageMeterLoading({ class
|
|
|
6411
8115
|
}
|
|
6412
8116
|
);
|
|
6413
8117
|
});
|
|
6414
|
-
var Empty = (0,
|
|
8118
|
+
var Empty = (0, import_react40.forwardRef)(function UsageMeterEmpty({ className, children, ...rest }, forwardedRef) {
|
|
6415
8119
|
const ctx = useUsageMeterCtx("Empty");
|
|
6416
8120
|
const copy = useCopy();
|
|
6417
8121
|
if (ctx.loading || ctx.usage !== null) return null;
|
|
6418
|
-
return /* @__PURE__ */ (0,
|
|
8122
|
+
return /* @__PURE__ */ (0, import_jsx_runtime26.jsx)(
|
|
6419
8123
|
"div",
|
|
6420
8124
|
{
|
|
6421
8125
|
ref: forwardedRef,
|
|
@@ -6426,13 +8130,13 @@ var Empty = (0, import_react38.forwardRef)(function UsageMeterEmpty({ className,
|
|
|
6426
8130
|
}
|
|
6427
8131
|
);
|
|
6428
8132
|
});
|
|
6429
|
-
var UsageMeter = Object.assign(
|
|
6430
|
-
Root:
|
|
8133
|
+
var UsageMeter = Object.assign(Root13, {
|
|
8134
|
+
Root: Root13,
|
|
6431
8135
|
Bar,
|
|
6432
8136
|
Label,
|
|
6433
8137
|
Percentage,
|
|
6434
8138
|
ResetsIn,
|
|
6435
|
-
Loading:
|
|
8139
|
+
Loading: Loading8,
|
|
6436
8140
|
Empty
|
|
6437
8141
|
});
|
|
6438
8142
|
function useUsageMeter() {
|
|
@@ -6455,6 +8159,40 @@ function useUsageMeter() {
|
|
|
6455
8159
|
AmountPickerCustom,
|
|
6456
8160
|
AmountPickerOption,
|
|
6457
8161
|
AmountPickerRoot,
|
|
8162
|
+
AutoRecharge,
|
|
8163
|
+
AutoRechargeActions,
|
|
8164
|
+
AutoRechargeAmountField,
|
|
8165
|
+
AutoRechargeBody,
|
|
8166
|
+
AutoRechargeCancelButton,
|
|
8167
|
+
AutoRechargeCard,
|
|
8168
|
+
AutoRechargeCardHeading,
|
|
8169
|
+
AutoRechargeCardSetup,
|
|
8170
|
+
AutoRechargeCardSummary,
|
|
8171
|
+
AutoRechargeContent,
|
|
8172
|
+
AutoRechargeDescription,
|
|
8173
|
+
AutoRechargeDisableButton,
|
|
8174
|
+
AutoRechargeEnableQuestion,
|
|
8175
|
+
AutoRechargeEnableRow,
|
|
8176
|
+
AutoRechargeEnableSentence,
|
|
8177
|
+
AutoRechargeEnableSwitch,
|
|
8178
|
+
AutoRechargeError,
|
|
8179
|
+
AutoRechargeFields,
|
|
8180
|
+
AutoRechargeHeader,
|
|
8181
|
+
AutoRechargeHint,
|
|
8182
|
+
AutoRechargeLoading,
|
|
8183
|
+
AutoRechargeOverlay,
|
|
8184
|
+
AutoRechargeRoot,
|
|
8185
|
+
AutoRechargeSaveButton,
|
|
8186
|
+
AutoRechargeSetup,
|
|
8187
|
+
AutoRechargeStatus,
|
|
8188
|
+
AutoRechargeStatusMessage,
|
|
8189
|
+
AutoRechargeSummary,
|
|
8190
|
+
AutoRechargeThresholdField,
|
|
8191
|
+
AutoRechargeTitle,
|
|
8192
|
+
AutoRechargeTopupField,
|
|
8193
|
+
AutoRechargeTrigger,
|
|
8194
|
+
AutoRechargeUnitToggle,
|
|
8195
|
+
AutoRechargeValidationError,
|
|
6458
8196
|
BalanceBadge,
|
|
6459
8197
|
CancelPlanButton,
|
|
6460
8198
|
CancelledPlanNotice,
|
|
@@ -6560,6 +8298,7 @@ function useUsageMeter() {
|
|
|
6560
8298
|
useActivationFlow,
|
|
6561
8299
|
useAmountPicker,
|
|
6562
8300
|
useAmountPickerCopy,
|
|
8301
|
+
useAutoRechargeForm,
|
|
6563
8302
|
useCancelledPlanNotice,
|
|
6564
8303
|
useCheckoutStepsContext,
|
|
6565
8304
|
useCheckoutSummary,
|