@reevit/react 0.4.3 → 0.4.5
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/dist/index.d.mts +16 -8
- package/dist/index.d.ts +16 -8
- package/dist/index.js +90 -22
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +90 -22
- package/dist/index.mjs.map +1 -1
- package/dist/styles.css +29 -25
- package/package.json +1 -1
package/dist/index.mjs
CHANGED
|
@@ -132,8 +132,8 @@ function createPaymentError(response, errorData) {
|
|
|
132
132
|
}
|
|
133
133
|
var ReevitAPIClient = class {
|
|
134
134
|
constructor(config) {
|
|
135
|
-
this.publicKey = config.publicKey;
|
|
136
|
-
this.baseUrl = config.baseUrl || (isSandboxKey(config.publicKey) ? API_BASE_URL_SANDBOX : API_BASE_URL_PRODUCTION);
|
|
135
|
+
this.publicKey = config.publicKey || "";
|
|
136
|
+
this.baseUrl = config.baseUrl || (config.publicKey && isSandboxKey(config.publicKey) ? API_BASE_URL_SANDBOX : API_BASE_URL_PRODUCTION);
|
|
137
137
|
this.timeout = config.timeout || DEFAULT_TIMEOUT;
|
|
138
138
|
}
|
|
139
139
|
/**
|
|
@@ -144,10 +144,12 @@ var ReevitAPIClient = class {
|
|
|
144
144
|
const timeoutId = setTimeout(() => controller.abort(), this.timeout);
|
|
145
145
|
const headers = {
|
|
146
146
|
"Content-Type": "application/json",
|
|
147
|
-
"X-Reevit-Key": this.publicKey,
|
|
148
147
|
"X-Reevit-Client": "@reevit/react",
|
|
149
148
|
"X-Reevit-Client-Version": "0.3.2"
|
|
150
149
|
};
|
|
150
|
+
if (this.publicKey) {
|
|
151
|
+
headers["X-Reevit-Key"] = this.publicKey;
|
|
152
|
+
}
|
|
151
153
|
if (method === "POST" || method === "PATCH" || method === "PUT") {
|
|
152
154
|
headers["Idempotency-Key"] = `${Date.now()}-${Math.random().toString(36).substring(2, 15)}`;
|
|
153
155
|
}
|
|
@@ -208,12 +210,14 @@ var ReevitAPIClient = class {
|
|
|
208
210
|
const request = {
|
|
209
211
|
amount: config.amount,
|
|
210
212
|
currency: config.currency,
|
|
211
|
-
method: this.mapPaymentMethod(method),
|
|
212
213
|
country,
|
|
213
214
|
customer_id: config.email || config.metadata?.customerId,
|
|
214
215
|
phone: config.phone,
|
|
215
216
|
metadata
|
|
216
217
|
};
|
|
218
|
+
if (method) {
|
|
219
|
+
request.method = this.mapPaymentMethod(method);
|
|
220
|
+
}
|
|
217
221
|
if (options?.preferredProviders?.length || options?.allowedProviders?.length) {
|
|
218
222
|
request.policy = {
|
|
219
223
|
prefer: options?.preferredProviders,
|
|
@@ -254,8 +258,9 @@ var ReevitAPIClient = class {
|
|
|
254
258
|
* @param paymentId - The payment intent ID for Hubtel checkout
|
|
255
259
|
* @returns Hubtel session with token, merchant account, and expiry information
|
|
256
260
|
*/
|
|
257
|
-
async createHubtelSession(paymentId) {
|
|
258
|
-
|
|
261
|
+
async createHubtelSession(paymentId, clientSecret) {
|
|
262
|
+
const query = clientSecret ? `?client_secret=${encodeURIComponent(clientSecret)}` : "";
|
|
263
|
+
return this.request("POST", `/v1/payments/hubtel/sessions/${paymentId}${query}`);
|
|
259
264
|
}
|
|
260
265
|
/**
|
|
261
266
|
* Maps SDK payment method to backend format
|
|
@@ -285,6 +290,18 @@ var initialState = {
|
|
|
285
290
|
error: null,
|
|
286
291
|
result: null
|
|
287
292
|
};
|
|
293
|
+
var DEFAULT_PUBLIC_API_BASE_URL = "https://api.reevit.io";
|
|
294
|
+
function buildPaymentLinkError(response, data) {
|
|
295
|
+
return {
|
|
296
|
+
code: data?.code || "payment_link_error",
|
|
297
|
+
message: data?.message || "Payment link request failed",
|
|
298
|
+
recoverable: true,
|
|
299
|
+
details: {
|
|
300
|
+
httpStatus: response.status,
|
|
301
|
+
...data?.details || {}
|
|
302
|
+
}
|
|
303
|
+
};
|
|
304
|
+
}
|
|
288
305
|
function reevitReducer(state, action) {
|
|
289
306
|
switch (action.type) {
|
|
290
307
|
case "INIT_START":
|
|
@@ -407,16 +424,50 @@ function useReevit(options) {
|
|
|
407
424
|
}
|
|
408
425
|
const reference = config.reference || generateReference();
|
|
409
426
|
const country = detectCountryFromCurrency(config.currency);
|
|
410
|
-
const
|
|
411
|
-
const
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
415
|
-
|
|
416
|
-
|
|
417
|
-
|
|
427
|
+
const defaultMethod = config.paymentMethods && config.paymentMethods.length === 1 ? config.paymentMethods[0] : void 0;
|
|
428
|
+
const paymentMethod = method ?? defaultMethod;
|
|
429
|
+
let data;
|
|
430
|
+
let error;
|
|
431
|
+
if (config.paymentLinkCode) {
|
|
432
|
+
const response = await fetch(
|
|
433
|
+
`${apiBaseUrl || DEFAULT_PUBLIC_API_BASE_URL}/v1/pay/${config.paymentLinkCode}/pay`,
|
|
434
|
+
{
|
|
435
|
+
method: "POST",
|
|
436
|
+
headers: {
|
|
437
|
+
"Content-Type": "application/json",
|
|
438
|
+
"Idempotency-Key": `${Date.now()}-${Math.random().toString(36).substring(2, 15)}`
|
|
439
|
+
},
|
|
440
|
+
body: JSON.stringify({
|
|
441
|
+
amount: config.amount,
|
|
442
|
+
email: config.email || "",
|
|
443
|
+
name: config.customerName || "",
|
|
444
|
+
phone: config.phone || "",
|
|
445
|
+
method: paymentMethod,
|
|
446
|
+
country,
|
|
447
|
+
provider: options2?.preferredProvider || options2?.allowedProviders?.[0],
|
|
448
|
+
custom_fields: config.customFields
|
|
449
|
+
})
|
|
450
|
+
}
|
|
451
|
+
);
|
|
452
|
+
const responseData = await response.json().catch(() => ({}));
|
|
453
|
+
if (!response.ok) {
|
|
454
|
+
error = buildPaymentLinkError(response, responseData);
|
|
455
|
+
} else {
|
|
456
|
+
data = responseData;
|
|
418
457
|
}
|
|
419
|
-
|
|
458
|
+
} else {
|
|
459
|
+
const result = await apiClient.createPaymentIntent(
|
|
460
|
+
{ ...config, reference },
|
|
461
|
+
paymentMethod,
|
|
462
|
+
country,
|
|
463
|
+
{
|
|
464
|
+
preferredProviders: options2?.preferredProvider ? [options2.preferredProvider] : void 0,
|
|
465
|
+
allowedProviders: options2?.allowedProviders
|
|
466
|
+
}
|
|
467
|
+
);
|
|
468
|
+
data = result.data;
|
|
469
|
+
error = result.error;
|
|
470
|
+
}
|
|
420
471
|
if (error) {
|
|
421
472
|
dispatch({ type: "INIT_ERROR", payload: error });
|
|
422
473
|
onError?.(error);
|
|
@@ -1036,6 +1087,8 @@ function HubtelBridge({
|
|
|
1036
1087
|
phone,
|
|
1037
1088
|
description = "Payment",
|
|
1038
1089
|
callbackUrl,
|
|
1090
|
+
apiBaseUrl,
|
|
1091
|
+
clientSecret,
|
|
1039
1092
|
hubtelSessionToken,
|
|
1040
1093
|
basicAuth,
|
|
1041
1094
|
preferredMethod,
|
|
@@ -1048,13 +1101,17 @@ function HubtelBridge({
|
|
|
1048
1101
|
const checkoutRef = useRef(null);
|
|
1049
1102
|
const [authValue, setAuthValue] = useState("");
|
|
1050
1103
|
const [isLoading, setIsLoading] = useState(false);
|
|
1104
|
+
const [resolvedMerchantAccount, setResolvedMerchantAccount] = useState(merchantAccount);
|
|
1105
|
+
useEffect(() => {
|
|
1106
|
+
setResolvedMerchantAccount(merchantAccount);
|
|
1107
|
+
}, [merchantAccount]);
|
|
1051
1108
|
useEffect(() => {
|
|
1052
1109
|
const fetchAuth = async () => {
|
|
1053
1110
|
if (hubtelSessionToken) {
|
|
1054
1111
|
setIsLoading(true);
|
|
1055
1112
|
try {
|
|
1056
|
-
const client = createReevitClient({ publicKey });
|
|
1057
|
-
const { data, error } = await client.createHubtelSession(paymentId);
|
|
1113
|
+
const client = createReevitClient({ publicKey, baseUrl: apiBaseUrl });
|
|
1114
|
+
const { data, error } = await client.createHubtelSession(paymentId, clientSecret);
|
|
1058
1115
|
if (error) {
|
|
1059
1116
|
onError({
|
|
1060
1117
|
code: "SESSION_ERROR",
|
|
@@ -1065,6 +1122,9 @@ function HubtelBridge({
|
|
|
1065
1122
|
}
|
|
1066
1123
|
if (data) {
|
|
1067
1124
|
setAuthValue(data.token);
|
|
1125
|
+
if (data.merchantAccount) {
|
|
1126
|
+
setResolvedMerchantAccount(data.merchantAccount);
|
|
1127
|
+
}
|
|
1068
1128
|
}
|
|
1069
1129
|
} catch (err) {
|
|
1070
1130
|
onError({
|
|
@@ -1081,7 +1141,7 @@ function HubtelBridge({
|
|
|
1081
1141
|
}
|
|
1082
1142
|
};
|
|
1083
1143
|
fetchAuth();
|
|
1084
|
-
}, [paymentId, publicKey, hubtelSessionToken, basicAuth, onError]);
|
|
1144
|
+
}, [paymentId, publicKey, apiBaseUrl, clientSecret, hubtelSessionToken, basicAuth, onError]);
|
|
1085
1145
|
const startPayment = useCallback(async () => {
|
|
1086
1146
|
if (isLoading || !authValue) {
|
|
1087
1147
|
return;
|
|
@@ -1101,7 +1161,7 @@ function HubtelBridge({
|
|
|
1101
1161
|
const config = {
|
|
1102
1162
|
branding: "enabled",
|
|
1103
1163
|
callbackUrl: callbackUrl || window.location.href,
|
|
1104
|
-
merchantAccount: typeof
|
|
1164
|
+
merchantAccount: typeof resolvedMerchantAccount === "string" ? parseInt(resolvedMerchantAccount, 10) : resolvedMerchantAccount,
|
|
1105
1165
|
// Use session token or basicAuth for authentication
|
|
1106
1166
|
// Session tokens are base64-encoded credentials fetched securely from the server
|
|
1107
1167
|
basicAuth: authValue || "",
|
|
@@ -1884,8 +1944,11 @@ function ReevitCheckout({
|
|
|
1884
1944
|
currency,
|
|
1885
1945
|
email = "",
|
|
1886
1946
|
phone = "",
|
|
1947
|
+
customerName,
|
|
1887
1948
|
reference,
|
|
1888
1949
|
metadata,
|
|
1950
|
+
customFields,
|
|
1951
|
+
paymentLinkCode,
|
|
1889
1952
|
paymentMethods = ["card", "mobile_money"],
|
|
1890
1953
|
initialPaymentIntent,
|
|
1891
1954
|
// Callbacks
|
|
@@ -1936,8 +1999,11 @@ function ReevitCheckout({
|
|
|
1936
1999
|
currency,
|
|
1937
2000
|
email,
|
|
1938
2001
|
phone,
|
|
2002
|
+
customerName,
|
|
1939
2003
|
reference,
|
|
1940
2004
|
metadata,
|
|
2005
|
+
customFields,
|
|
2006
|
+
paymentLinkCode,
|
|
1941
2007
|
paymentMethods,
|
|
1942
2008
|
initialPaymentIntent
|
|
1943
2009
|
},
|
|
@@ -2145,7 +2211,7 @@ function ReevitCheckout({
|
|
|
2145
2211
|
const psp = selectedProvider || paymentIntent?.recommendedPsp || "paystack";
|
|
2146
2212
|
const pspLower = psp.toLowerCase();
|
|
2147
2213
|
if (showPSPBridge) {
|
|
2148
|
-
const pspKey = paymentIntent?.pspPublicKey || publicKey;
|
|
2214
|
+
const pspKey = paymentIntent?.pspPublicKey || publicKey || "";
|
|
2149
2215
|
const bridgeMetadata = {
|
|
2150
2216
|
...metadata,
|
|
2151
2217
|
payment_id: paymentIntent?.id,
|
|
@@ -2185,6 +2251,8 @@ function ReevitCheckout({
|
|
|
2185
2251
|
phone: momoData?.phone || phone,
|
|
2186
2252
|
description: `Payment ${paymentIntent?.reference || reference || ""}`,
|
|
2187
2253
|
hubtelSessionToken: paymentIntent?.id ? paymentIntent.id : void 0,
|
|
2254
|
+
clientSecret: paymentIntent?.clientSecret,
|
|
2255
|
+
apiBaseUrl,
|
|
2188
2256
|
preferredMethod: selectedMethod || void 0,
|
|
2189
2257
|
onSuccess: handlePSPSuccess,
|
|
2190
2258
|
onError: (err) => handlePSPError(err),
|
|
@@ -2235,7 +2303,7 @@ function ReevitCheckout({
|
|
|
2235
2303
|
currency: paymentIntent?.currency ?? currency,
|
|
2236
2304
|
reference: paymentIntent?.reference || reference || `mpesa_${Date.now()}`,
|
|
2237
2305
|
description: `Payment ${paymentIntent?.reference || reference || ""}`,
|
|
2238
|
-
headers: { "x-reevit-public-key": publicKey },
|
|
2306
|
+
headers: { "x-reevit-public-key": publicKey || "" },
|
|
2239
2307
|
onSuccess: handlePSPSuccess,
|
|
2240
2308
|
onError: handlePSPError
|
|
2241
2309
|
}
|
|
@@ -2328,7 +2396,7 @@ function ReevitCheckout({
|
|
|
2328
2396
|
] }) })
|
|
2329
2397
|
] });
|
|
2330
2398
|
};
|
|
2331
|
-
return /* @__PURE__ */ jsxs(ReevitContext.Provider, { value: { publicKey, amount, currency }, children: [
|
|
2399
|
+
return /* @__PURE__ */ jsxs(ReevitContext.Provider, { value: { publicKey: publicKey || "", amount, currency }, children: [
|
|
2332
2400
|
trigger,
|
|
2333
2401
|
isOpen && /* @__PURE__ */ jsx("div", { className: "reevit-overlay", onClick: handleClose, children: /* @__PURE__ */ jsxs(
|
|
2334
2402
|
"div",
|