@paymanai/payman-ask-sdk 1.0.4 → 1.1.0
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 +39 -2
- package/dist/index.d.ts +39 -2
- package/dist/index.js +513 -10
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +504 -13
- package/dist/index.mjs.map +1 -1
- package/dist/index.native.js +496 -15
- package/dist/index.native.js.map +1 -1
- package/package.json +2 -2
package/dist/index.native.js
CHANGED
|
@@ -178,7 +178,7 @@ function AgentMessage({
|
|
|
178
178
|
agentName = "Assistant",
|
|
179
179
|
showAvatar = false,
|
|
180
180
|
layout = "full-width",
|
|
181
|
-
showTimestamp = false,
|
|
181
|
+
showTimestamp: _showTimestamp = false,
|
|
182
182
|
showExecutionSteps = false,
|
|
183
183
|
showStreamingDot = false,
|
|
184
184
|
streamingStepsText,
|
|
@@ -186,7 +186,7 @@ function AgentMessage({
|
|
|
186
186
|
onExecutionTraceClick
|
|
187
187
|
}) {
|
|
188
188
|
const isStreaming = message.isStreaming ?? false;
|
|
189
|
-
const hasSteps = message.steps && message.steps.length > 0;
|
|
189
|
+
const hasSteps = !!message.steps && message.steps.length > 0;
|
|
190
190
|
const hasTraceData = !!(message.tracingData || message.executionId) && !isStreaming;
|
|
191
191
|
const isError = message.isError ?? (message.streamProgress === "error" || !!message.errorDetails);
|
|
192
192
|
const isCancelled = message.isCancelled ?? false;
|
|
@@ -236,6 +236,13 @@ function AgentMessage({
|
|
|
236
236
|
layout === "centered" && styles2.messageContainerCentered
|
|
237
237
|
],
|
|
238
238
|
children: [
|
|
239
|
+
message.userActionResult && /* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style: styles2.badgeContainer, children: message.userActionResult === "approved" ? /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: [styles2.badge, styles2.badgeApproved], children: [
|
|
240
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.CheckCircle2, { size: 12, color: "#15803d" }),
|
|
241
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles2.badgeApprovedText, children: "OTP Verified" })
|
|
242
|
+
] }) : /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: [styles2.badge, styles2.badgeRejected], children: [
|
|
243
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.XCircle, { size: 12, color: "#b91c1c" }),
|
|
244
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles2.badgeRejectedText, children: "Rejected" })
|
|
245
|
+
] }) }),
|
|
239
246
|
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
240
247
|
reactNative.View,
|
|
241
248
|
{
|
|
@@ -278,7 +285,7 @@ function AgentMessage({
|
|
|
278
285
|
onPress: () => setIsStepsExpanded(!isStepsExpanded),
|
|
279
286
|
style: styles2.stepsButton,
|
|
280
287
|
children: [
|
|
281
|
-
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles2.stepsButtonText, children: getCompletedStepsText(isStepsExpanded) }),
|
|
288
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles2.stepsButtonText, children: getCompletedStepsText(!!isStepsExpanded) }),
|
|
282
289
|
isStepsExpanded ? /* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.ChevronUp, { size: 12, color: "#666" }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.ChevronDown, { size: 12, color: "#666" })
|
|
283
290
|
]
|
|
284
291
|
}
|
|
@@ -302,7 +309,13 @@ function AgentMessage({
|
|
|
302
309
|
step.status === "pending" && isCancelled && /* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.XCircle, { size: 12, color: "#666" }),
|
|
303
310
|
step.status === "pending" && !isCancelled && /* @__PURE__ */ jsxRuntime.jsx(AnimatedLoader, { size: 12, color: "#007AFF" }),
|
|
304
311
|
step.status === "in_progress" && !isCurrentlyExecuting && /* @__PURE__ */ jsxRuntime.jsx(AnimatedLoader, { size: 12, color: "#007AFF" }),
|
|
305
|
-
step.status === "completed" && /* @__PURE__ */ jsxRuntime.jsx(
|
|
312
|
+
step.status === "completed" && /* @__PURE__ */ jsxRuntime.jsx(
|
|
313
|
+
lucideReactNative.Check,
|
|
314
|
+
{
|
|
315
|
+
size: 12,
|
|
316
|
+
color: step.eventType === "USER_ACTION_SUCCESS" ? "#16a34a" : "#007AFF"
|
|
317
|
+
}
|
|
318
|
+
),
|
|
306
319
|
step.status === "error" && /* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.X, { size: 12, color: "#FF3B30" }),
|
|
307
320
|
/* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: styles2.stepContent, children: [
|
|
308
321
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
@@ -310,7 +323,8 @@ function AgentMessage({
|
|
|
310
323
|
{
|
|
311
324
|
style: [
|
|
312
325
|
styles2.stepText,
|
|
313
|
-
step.status === "error" && styles2.stepTextError
|
|
326
|
+
step.status === "error" && styles2.stepTextError,
|
|
327
|
+
step.eventType === "USER_ACTION_SUCCESS" && styles2.stepTextSuccess
|
|
314
328
|
],
|
|
315
329
|
children: step.message
|
|
316
330
|
}
|
|
@@ -346,7 +360,7 @@ function AgentMessage({
|
|
|
346
360
|
onPress: () => setIsStepsExpanded(!isStepsExpanded),
|
|
347
361
|
style: styles2.stepsButton,
|
|
348
362
|
children: [
|
|
349
|
-
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles2.stepsButtonText, children: getStreamingStepsText(isStepsExpanded) }),
|
|
363
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles2.stepsButtonText, children: getStreamingStepsText(!!isStepsExpanded) }),
|
|
350
364
|
isStepsExpanded ? /* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.ChevronUp, { size: 12, color: "#666" }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.ChevronDown, { size: 12, color: "#666" })
|
|
351
365
|
]
|
|
352
366
|
}
|
|
@@ -370,7 +384,13 @@ function AgentMessage({
|
|
|
370
384
|
step.status === "pending" && isCancelled && /* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.XCircle, { size: 12, color: "#666" }),
|
|
371
385
|
step.status === "pending" && !isCancelled && /* @__PURE__ */ jsxRuntime.jsx(AnimatedLoader, { size: 12, color: "#007AFF" }),
|
|
372
386
|
step.status === "in_progress" && !isCurrentlyExecuting && /* @__PURE__ */ jsxRuntime.jsx(AnimatedLoader, { size: 12, color: "#007AFF" }),
|
|
373
|
-
step.status === "completed" && /* @__PURE__ */ jsxRuntime.jsx(
|
|
387
|
+
step.status === "completed" && /* @__PURE__ */ jsxRuntime.jsx(
|
|
388
|
+
lucideReactNative.Check,
|
|
389
|
+
{
|
|
390
|
+
size: 12,
|
|
391
|
+
color: step.eventType === "USER_ACTION_SUCCESS" ? "#16a34a" : "#007AFF"
|
|
392
|
+
}
|
|
393
|
+
),
|
|
374
394
|
step.status === "error" && /* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.X, { size: 12, color: "#FF3B30" }),
|
|
375
395
|
/* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: styles2.stepContent, children: [
|
|
376
396
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
@@ -378,7 +398,8 @@ function AgentMessage({
|
|
|
378
398
|
{
|
|
379
399
|
style: [
|
|
380
400
|
styles2.stepText,
|
|
381
|
-
step.status === "error" && styles2.stepTextError
|
|
401
|
+
step.status === "error" && styles2.stepTextError,
|
|
402
|
+
step.eventType === "USER_ACTION_SUCCESS" && styles2.stepTextSuccess
|
|
382
403
|
],
|
|
383
404
|
children: step.message
|
|
384
405
|
}
|
|
@@ -410,7 +431,10 @@ function AgentMessage({
|
|
|
410
431
|
tracingData: message.tracingData,
|
|
411
432
|
executionId: message.executionId
|
|
412
433
|
}),
|
|
413
|
-
style:
|
|
434
|
+
style: [
|
|
435
|
+
styles2.traceButton,
|
|
436
|
+
message.userActionResult ? styles2.traceButtonWithBadge : void 0
|
|
437
|
+
],
|
|
414
438
|
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReactNative.Binoculars, { size: 16, color: "#007AFF" })
|
|
415
439
|
}
|
|
416
440
|
)
|
|
@@ -560,6 +584,9 @@ var styles2 = reactNative.StyleSheet.create({
|
|
|
560
584
|
stepTextError: {
|
|
561
585
|
color: "#FF3B30"
|
|
562
586
|
},
|
|
587
|
+
stepTextSuccess: {
|
|
588
|
+
color: "#16a34a"
|
|
589
|
+
},
|
|
563
590
|
stepTime: {
|
|
564
591
|
fontSize: 10,
|
|
565
592
|
opacity: 0.5,
|
|
@@ -572,6 +599,37 @@ var styles2 = reactNative.StyleSheet.create({
|
|
|
572
599
|
borderWidth: 1,
|
|
573
600
|
borderColor: "rgba(255,255,255,0.2)",
|
|
574
601
|
borderRadius: 8
|
|
602
|
+
},
|
|
603
|
+
traceButtonWithBadge: {
|
|
604
|
+
marginTop: 32
|
|
605
|
+
},
|
|
606
|
+
badgeContainer: {
|
|
607
|
+
marginBottom: 8
|
|
608
|
+
},
|
|
609
|
+
badge: {
|
|
610
|
+
flexDirection: "row",
|
|
611
|
+
alignItems: "center",
|
|
612
|
+
gap: 4,
|
|
613
|
+
paddingHorizontal: 8,
|
|
614
|
+
paddingVertical: 4,
|
|
615
|
+
borderRadius: 12,
|
|
616
|
+
alignSelf: "flex-start"
|
|
617
|
+
},
|
|
618
|
+
badgeApproved: {
|
|
619
|
+
backgroundColor: "#dcfce7"
|
|
620
|
+
},
|
|
621
|
+
badgeApprovedText: {
|
|
622
|
+
fontSize: 12,
|
|
623
|
+
fontWeight: "500",
|
|
624
|
+
color: "#15803d"
|
|
625
|
+
},
|
|
626
|
+
badgeRejected: {
|
|
627
|
+
backgroundColor: "#fee2e2"
|
|
628
|
+
},
|
|
629
|
+
badgeRejectedText: {
|
|
630
|
+
fontSize: 12,
|
|
631
|
+
fontWeight: "500",
|
|
632
|
+
color: "#b91c1c"
|
|
575
633
|
}
|
|
576
634
|
});
|
|
577
635
|
var markdownStyles = {
|
|
@@ -1001,6 +1059,400 @@ var styles5 = reactNative.StyleSheet.create({
|
|
|
1001
1059
|
width: "100%"
|
|
1002
1060
|
}
|
|
1003
1061
|
});
|
|
1062
|
+
var DEFAULT_MAX_LENGTH = 6;
|
|
1063
|
+
var MAX_SUPPORTED_LENGTH = 12;
|
|
1064
|
+
function OtpInput({ value, onChange, maxLength, disabled = false }) {
|
|
1065
|
+
const inputRefs = React.useRef([]);
|
|
1066
|
+
const safeMaxLength = Number.isInteger(maxLength) && maxLength > 0 ? Math.min(maxLength, MAX_SUPPORTED_LENGTH) : DEFAULT_MAX_LENGTH;
|
|
1067
|
+
const digits = value.split("").concat(Array(safeMaxLength).fill("")).slice(0, safeMaxLength);
|
|
1068
|
+
React.useEffect(() => {
|
|
1069
|
+
if (!disabled) {
|
|
1070
|
+
inputRefs.current[0]?.focus();
|
|
1071
|
+
}
|
|
1072
|
+
}, [disabled]);
|
|
1073
|
+
const focusInput = (index) => {
|
|
1074
|
+
if (index >= 0 && index < safeMaxLength) {
|
|
1075
|
+
inputRefs.current[index]?.focus();
|
|
1076
|
+
}
|
|
1077
|
+
};
|
|
1078
|
+
const updateValue = (newDigits) => {
|
|
1079
|
+
onChange(newDigits.join("").slice(0, safeMaxLength));
|
|
1080
|
+
};
|
|
1081
|
+
const handleChange = (index, text) => {
|
|
1082
|
+
const cleaned = text.replace(/\D/g, "");
|
|
1083
|
+
if (cleaned.length > 1) {
|
|
1084
|
+
const pasted = cleaned.slice(0, safeMaxLength);
|
|
1085
|
+
const newDigits2 = pasted.split("").concat(Array(safeMaxLength).fill("")).slice(0, safeMaxLength);
|
|
1086
|
+
updateValue(newDigits2);
|
|
1087
|
+
focusInput(Math.min(pasted.length, safeMaxLength - 1));
|
|
1088
|
+
return;
|
|
1089
|
+
}
|
|
1090
|
+
const char = cleaned.slice(-1);
|
|
1091
|
+
const newDigits = [...digits];
|
|
1092
|
+
newDigits[index] = char;
|
|
1093
|
+
updateValue(newDigits);
|
|
1094
|
+
if (char && index < safeMaxLength - 1) {
|
|
1095
|
+
focusInput(index + 1);
|
|
1096
|
+
}
|
|
1097
|
+
};
|
|
1098
|
+
const handleKeyPress = (index, key) => {
|
|
1099
|
+
if (key === "Backspace") {
|
|
1100
|
+
if (digits[index]) {
|
|
1101
|
+
const newDigits = [...digits];
|
|
1102
|
+
newDigits[index] = "";
|
|
1103
|
+
updateValue(newDigits);
|
|
1104
|
+
} else if (index > 0) {
|
|
1105
|
+
const newDigits = [...digits];
|
|
1106
|
+
newDigits[index - 1] = "";
|
|
1107
|
+
updateValue(newDigits);
|
|
1108
|
+
focusInput(index - 1);
|
|
1109
|
+
}
|
|
1110
|
+
}
|
|
1111
|
+
};
|
|
1112
|
+
return /* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style: styles6.container, children: digits.map((digit, i) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
1113
|
+
reactNative.TextInput,
|
|
1114
|
+
{
|
|
1115
|
+
ref: (el) => {
|
|
1116
|
+
inputRefs.current[i] = el;
|
|
1117
|
+
},
|
|
1118
|
+
value: digit,
|
|
1119
|
+
editable: !disabled,
|
|
1120
|
+
keyboardType: "number-pad",
|
|
1121
|
+
maxLength: 1,
|
|
1122
|
+
onChangeText: (text) => handleChange(i, text),
|
|
1123
|
+
onKeyPress: ({ nativeEvent }) => handleKeyPress(i, nativeEvent.key),
|
|
1124
|
+
onFocus: () => inputRefs.current[i]?.setNativeProps({ selection: { start: 0, end: 1 } }),
|
|
1125
|
+
style: [styles6.input, disabled && styles6.inputDisabled],
|
|
1126
|
+
accessibilityLabel: `Digit ${i + 1}`
|
|
1127
|
+
},
|
|
1128
|
+
i
|
|
1129
|
+
)) });
|
|
1130
|
+
}
|
|
1131
|
+
var styles6 = reactNative.StyleSheet.create({
|
|
1132
|
+
container: {
|
|
1133
|
+
flexDirection: "row",
|
|
1134
|
+
gap: 8,
|
|
1135
|
+
justifyContent: "center"
|
|
1136
|
+
},
|
|
1137
|
+
input: {
|
|
1138
|
+
width: 40,
|
|
1139
|
+
height: 48,
|
|
1140
|
+
textAlign: "center",
|
|
1141
|
+
fontSize: 20,
|
|
1142
|
+
fontWeight: "600",
|
|
1143
|
+
borderWidth: 1,
|
|
1144
|
+
borderColor: "#E5E5E5",
|
|
1145
|
+
borderRadius: 8,
|
|
1146
|
+
color: "#000"
|
|
1147
|
+
},
|
|
1148
|
+
inputDisabled: {
|
|
1149
|
+
backgroundColor: "#F5F5F5",
|
|
1150
|
+
opacity: 0.5
|
|
1151
|
+
}
|
|
1152
|
+
});
|
|
1153
|
+
|
|
1154
|
+
// src/components/UserActionModal/constants.ts
|
|
1155
|
+
var BUTTON_LABELS = {
|
|
1156
|
+
APPROVE: "Verify",
|
|
1157
|
+
REJECT: "Reject",
|
|
1158
|
+
RESEND: "Resend OTP"
|
|
1159
|
+
};
|
|
1160
|
+
var RESEND_OTP_COOLDOWN_SECONDS = 30;
|
|
1161
|
+
var DEFAULT_OTP_MAX_LENGTH = 6;
|
|
1162
|
+
var MIN_OTP_MAX_LENGTH = 1;
|
|
1163
|
+
var MAX_OTP_MAX_LENGTH = 12;
|
|
1164
|
+
var ACTION_PENDING_TIMEOUT_MS = 15e3;
|
|
1165
|
+
var MODAL_CONTENT = {
|
|
1166
|
+
TITLE: "Verification Required",
|
|
1167
|
+
LOADING_APPROVE: "Verifying...",
|
|
1168
|
+
LOADING_REJECT: "Rejecting...",
|
|
1169
|
+
LOADING_RESEND: "Resending...",
|
|
1170
|
+
RESEND_AVAILABLE_IN: "Resend OTP in"
|
|
1171
|
+
};
|
|
1172
|
+
|
|
1173
|
+
// src/components/UserActionModal/utils.ts
|
|
1174
|
+
function getOtpSchemaFromRequest(schema) {
|
|
1175
|
+
const properties = schema?.properties;
|
|
1176
|
+
const otp = properties?.otp;
|
|
1177
|
+
const maxLengthRaw = otp?.maxLength;
|
|
1178
|
+
const parsedMaxLength = Number.isInteger(maxLengthRaw) ? Number(maxLengthRaw) : DEFAULT_OTP_MAX_LENGTH;
|
|
1179
|
+
const clampedMaxLength = Math.min(
|
|
1180
|
+
MAX_OTP_MAX_LENGTH,
|
|
1181
|
+
Math.max(MIN_OTP_MAX_LENGTH, parsedMaxLength)
|
|
1182
|
+
);
|
|
1183
|
+
return {
|
|
1184
|
+
maxLength: clampedMaxLength
|
|
1185
|
+
};
|
|
1186
|
+
}
|
|
1187
|
+
function UserActionModal({
|
|
1188
|
+
isOpen,
|
|
1189
|
+
userActionRequest,
|
|
1190
|
+
onApprove,
|
|
1191
|
+
onReject,
|
|
1192
|
+
onResend,
|
|
1193
|
+
clearOtpTrigger
|
|
1194
|
+
}) {
|
|
1195
|
+
const [otp, setOtp] = React.useState("");
|
|
1196
|
+
const [actionType, setActionType] = React.useState(null);
|
|
1197
|
+
const [isSubmitting, setIsSubmitting] = React.useState(false);
|
|
1198
|
+
const [resendCooldownRemaining, setResendCooldownRemaining] = React.useState(0);
|
|
1199
|
+
const schema = getOtpSchemaFromRequest(userActionRequest?.requestedSchema);
|
|
1200
|
+
const resetActionState = React.useCallback(() => {
|
|
1201
|
+
setIsSubmitting(false);
|
|
1202
|
+
setActionType(null);
|
|
1203
|
+
}, []);
|
|
1204
|
+
React.useEffect(() => {
|
|
1205
|
+
if (isOpen) {
|
|
1206
|
+
setResendCooldownRemaining(RESEND_OTP_COOLDOWN_SECONDS);
|
|
1207
|
+
} else {
|
|
1208
|
+
setOtp("");
|
|
1209
|
+
resetActionState();
|
|
1210
|
+
setResendCooldownRemaining(0);
|
|
1211
|
+
}
|
|
1212
|
+
}, [isOpen, resetActionState]);
|
|
1213
|
+
React.useEffect(() => {
|
|
1214
|
+
if (resendCooldownRemaining <= 0) return;
|
|
1215
|
+
const timer = setTimeout(() => {
|
|
1216
|
+
setResendCooldownRemaining((prev) => prev - 1);
|
|
1217
|
+
}, 1e3);
|
|
1218
|
+
return () => clearTimeout(timer);
|
|
1219
|
+
}, [resendCooldownRemaining]);
|
|
1220
|
+
React.useEffect(() => {
|
|
1221
|
+
if (clearOtpTrigger > 0) {
|
|
1222
|
+
setOtp("");
|
|
1223
|
+
resetActionState();
|
|
1224
|
+
}
|
|
1225
|
+
}, [clearOtpTrigger, resetActionState]);
|
|
1226
|
+
React.useEffect(() => {
|
|
1227
|
+
if (!isOpen || !isSubmitting) return;
|
|
1228
|
+
if (actionType !== "approve" && actionType !== "reject") return;
|
|
1229
|
+
const timeout = setTimeout(() => {
|
|
1230
|
+
resetActionState();
|
|
1231
|
+
}, ACTION_PENDING_TIMEOUT_MS);
|
|
1232
|
+
return () => clearTimeout(timeout);
|
|
1233
|
+
}, [isOpen, isSubmitting, actionType, resetActionState]);
|
|
1234
|
+
const handleApprove = React.useCallback(async () => {
|
|
1235
|
+
if (otp.length !== schema.maxLength || !/^\d+$/.test(otp)) return;
|
|
1236
|
+
setIsSubmitting(true);
|
|
1237
|
+
setActionType("approve");
|
|
1238
|
+
try {
|
|
1239
|
+
await onApprove(otp);
|
|
1240
|
+
} catch {
|
|
1241
|
+
resetActionState();
|
|
1242
|
+
}
|
|
1243
|
+
}, [otp, schema.maxLength, onApprove, resetActionState]);
|
|
1244
|
+
const handleReject = React.useCallback(async () => {
|
|
1245
|
+
setIsSubmitting(true);
|
|
1246
|
+
setActionType("reject");
|
|
1247
|
+
try {
|
|
1248
|
+
await onReject();
|
|
1249
|
+
} catch {
|
|
1250
|
+
resetActionState();
|
|
1251
|
+
}
|
|
1252
|
+
}, [onReject, resetActionState]);
|
|
1253
|
+
const handleResend = React.useCallback(async () => {
|
|
1254
|
+
if (resendCooldownRemaining > 0) return;
|
|
1255
|
+
setIsSubmitting(true);
|
|
1256
|
+
setActionType("resend");
|
|
1257
|
+
try {
|
|
1258
|
+
await onResend();
|
|
1259
|
+
setResendCooldownRemaining(RESEND_OTP_COOLDOWN_SECONDS);
|
|
1260
|
+
} catch {
|
|
1261
|
+
} finally {
|
|
1262
|
+
setActionType(null);
|
|
1263
|
+
setIsSubmitting(false);
|
|
1264
|
+
}
|
|
1265
|
+
}, [resendCooldownRemaining, onResend]);
|
|
1266
|
+
if (!userActionRequest) return null;
|
|
1267
|
+
const isOtpValid = otp.length === schema.maxLength && /^\d+$/.test(otp);
|
|
1268
|
+
const getResendLabel = () => {
|
|
1269
|
+
if (actionType === "resend") return MODAL_CONTENT.LOADING_RESEND;
|
|
1270
|
+
if (resendCooldownRemaining > 0)
|
|
1271
|
+
return `${MODAL_CONTENT.RESEND_AVAILABLE_IN} ${resendCooldownRemaining}s`;
|
|
1272
|
+
return BUTTON_LABELS.RESEND;
|
|
1273
|
+
};
|
|
1274
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
1275
|
+
reactNative.Modal,
|
|
1276
|
+
{
|
|
1277
|
+
visible: isOpen,
|
|
1278
|
+
transparent: true,
|
|
1279
|
+
animationType: "fade",
|
|
1280
|
+
onRequestClose: () => {
|
|
1281
|
+
},
|
|
1282
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style: styles7.backdrop, children: /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: styles7.dialog, children: [
|
|
1283
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style: styles7.titleContainer, children: /* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles7.title, children: MODAL_CONTENT.TITLE }) }),
|
|
1284
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles7.description, children: userActionRequest.message }),
|
|
1285
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style: styles7.otpContainer, children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
1286
|
+
OtpInput,
|
|
1287
|
+
{
|
|
1288
|
+
value: otp,
|
|
1289
|
+
onChange: setOtp,
|
|
1290
|
+
maxLength: schema.maxLength,
|
|
1291
|
+
disabled: isSubmitting
|
|
1292
|
+
}
|
|
1293
|
+
) }),
|
|
1294
|
+
/* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: styles7.buttonsColumn, children: [
|
|
1295
|
+
/* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: styles7.primaryButtonsRow, children: [
|
|
1296
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
1297
|
+
reactNative.Pressable,
|
|
1298
|
+
{
|
|
1299
|
+
onPress: handleReject,
|
|
1300
|
+
disabled: isSubmitting,
|
|
1301
|
+
style: ({ pressed }) => [
|
|
1302
|
+
styles7.rejectButton,
|
|
1303
|
+
isSubmitting && styles7.buttonDisabled,
|
|
1304
|
+
pressed && styles7.rejectButtonPressed
|
|
1305
|
+
],
|
|
1306
|
+
children: [
|
|
1307
|
+
actionType === "reject" && /* @__PURE__ */ jsxRuntime.jsx(reactNative.ActivityIndicator, { size: "small", color: "#DC2626", style: styles7.spinner }),
|
|
1308
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles7.rejectButtonText, children: actionType === "reject" ? MODAL_CONTENT.LOADING_REJECT : BUTTON_LABELS.REJECT })
|
|
1309
|
+
]
|
|
1310
|
+
}
|
|
1311
|
+
),
|
|
1312
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
1313
|
+
reactNative.Pressable,
|
|
1314
|
+
{
|
|
1315
|
+
onPress: handleApprove,
|
|
1316
|
+
disabled: !isOtpValid || isSubmitting,
|
|
1317
|
+
style: ({ pressed }) => [
|
|
1318
|
+
styles7.approveButton,
|
|
1319
|
+
(!isOtpValid || isSubmitting) && styles7.buttonDisabled,
|
|
1320
|
+
pressed && styles7.approveButtonPressed
|
|
1321
|
+
],
|
|
1322
|
+
children: [
|
|
1323
|
+
actionType === "approve" && /* @__PURE__ */ jsxRuntime.jsx(reactNative.ActivityIndicator, { size: "small", color: "#FFF", style: styles7.spinner }),
|
|
1324
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles7.approveButtonText, children: actionType === "approve" ? MODAL_CONTENT.LOADING_APPROVE : BUTTON_LABELS.APPROVE })
|
|
1325
|
+
]
|
|
1326
|
+
}
|
|
1327
|
+
)
|
|
1328
|
+
] }),
|
|
1329
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
1330
|
+
reactNative.Pressable,
|
|
1331
|
+
{
|
|
1332
|
+
onPress: handleResend,
|
|
1333
|
+
disabled: isSubmitting || resendCooldownRemaining > 0,
|
|
1334
|
+
style: ({ pressed }) => [
|
|
1335
|
+
styles7.resendButton,
|
|
1336
|
+
(isSubmitting || resendCooldownRemaining > 0) && styles7.buttonDisabled,
|
|
1337
|
+
pressed && styles7.resendButtonPressed
|
|
1338
|
+
],
|
|
1339
|
+
children: [
|
|
1340
|
+
actionType === "resend" && /* @__PURE__ */ jsxRuntime.jsx(reactNative.ActivityIndicator, { size: "small", color: "#666", style: styles7.spinner }),
|
|
1341
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles7.resendButtonText, children: getResendLabel() })
|
|
1342
|
+
]
|
|
1343
|
+
}
|
|
1344
|
+
)
|
|
1345
|
+
] })
|
|
1346
|
+
] }) })
|
|
1347
|
+
}
|
|
1348
|
+
);
|
|
1349
|
+
}
|
|
1350
|
+
var styles7 = reactNative.StyleSheet.create({
|
|
1351
|
+
backdrop: {
|
|
1352
|
+
flex: 1,
|
|
1353
|
+
backgroundColor: "rgba(0, 0, 0, 0.5)",
|
|
1354
|
+
justifyContent: "center",
|
|
1355
|
+
alignItems: "center"
|
|
1356
|
+
},
|
|
1357
|
+
dialog: {
|
|
1358
|
+
backgroundColor: "#FFF",
|
|
1359
|
+
borderRadius: 12,
|
|
1360
|
+
padding: 24,
|
|
1361
|
+
width: "90%",
|
|
1362
|
+
maxWidth: 420
|
|
1363
|
+
},
|
|
1364
|
+
titleContainer: {
|
|
1365
|
+
alignItems: "center",
|
|
1366
|
+
marginBottom: 16
|
|
1367
|
+
},
|
|
1368
|
+
title: {
|
|
1369
|
+
fontSize: 18,
|
|
1370
|
+
fontWeight: "600",
|
|
1371
|
+
color: "#000"
|
|
1372
|
+
},
|
|
1373
|
+
description: {
|
|
1374
|
+
fontSize: 14,
|
|
1375
|
+
color: "#666",
|
|
1376
|
+
textAlign: "center",
|
|
1377
|
+
marginBottom: 24,
|
|
1378
|
+
lineHeight: 21
|
|
1379
|
+
},
|
|
1380
|
+
otpContainer: {
|
|
1381
|
+
marginBottom: 24
|
|
1382
|
+
},
|
|
1383
|
+
buttonsColumn: {
|
|
1384
|
+
gap: 10
|
|
1385
|
+
},
|
|
1386
|
+
primaryButtonsRow: {
|
|
1387
|
+
flexDirection: "row",
|
|
1388
|
+
gap: 8
|
|
1389
|
+
},
|
|
1390
|
+
resendButton: {
|
|
1391
|
+
borderRadius: 8,
|
|
1392
|
+
paddingVertical: 8,
|
|
1393
|
+
paddingHorizontal: 16,
|
|
1394
|
+
flexDirection: "row",
|
|
1395
|
+
alignItems: "center",
|
|
1396
|
+
justifyContent: "center"
|
|
1397
|
+
},
|
|
1398
|
+
resendButtonPressed: {
|
|
1399
|
+
opacity: 0.7
|
|
1400
|
+
},
|
|
1401
|
+
resendButtonText: {
|
|
1402
|
+
color: "#666",
|
|
1403
|
+
fontSize: 12,
|
|
1404
|
+
fontWeight: "500"
|
|
1405
|
+
},
|
|
1406
|
+
rejectButton: {
|
|
1407
|
+
flex: 1,
|
|
1408
|
+
borderRadius: 8,
|
|
1409
|
+
paddingVertical: 12,
|
|
1410
|
+
paddingHorizontal: 16,
|
|
1411
|
+
backgroundColor: "rgba(220, 38, 38, 0.1)",
|
|
1412
|
+
flexDirection: "row",
|
|
1413
|
+
alignItems: "center",
|
|
1414
|
+
justifyContent: "center"
|
|
1415
|
+
},
|
|
1416
|
+
rejectButtonPressed: {
|
|
1417
|
+
backgroundColor: "rgba(220, 38, 38, 0.2)"
|
|
1418
|
+
},
|
|
1419
|
+
rejectButtonText: {
|
|
1420
|
+
color: "#DC2626",
|
|
1421
|
+
fontSize: 14,
|
|
1422
|
+
fontWeight: "500"
|
|
1423
|
+
},
|
|
1424
|
+
approveButton: {
|
|
1425
|
+
flex: 1,
|
|
1426
|
+
borderRadius: 8,
|
|
1427
|
+
paddingVertical: 12,
|
|
1428
|
+
paddingHorizontal: 16,
|
|
1429
|
+
backgroundColor: "#007AFF",
|
|
1430
|
+
flexDirection: "row",
|
|
1431
|
+
alignItems: "center",
|
|
1432
|
+
justifyContent: "center"
|
|
1433
|
+
},
|
|
1434
|
+
approveButtonPressed: {
|
|
1435
|
+
backgroundColor: "#0066D6",
|
|
1436
|
+
opacity: 1
|
|
1437
|
+
},
|
|
1438
|
+
approveButtonText: {
|
|
1439
|
+
color: "#FFF",
|
|
1440
|
+
fontSize: 14,
|
|
1441
|
+
fontWeight: "600"
|
|
1442
|
+
},
|
|
1443
|
+
buttonDisabled: {
|
|
1444
|
+
opacity: 0.5
|
|
1445
|
+
},
|
|
1446
|
+
spinner: {
|
|
1447
|
+
marginRight: 8
|
|
1448
|
+
}
|
|
1449
|
+
});
|
|
1450
|
+
var DEFAULT_USER_ACTION_STATE = {
|
|
1451
|
+
request: null,
|
|
1452
|
+
clearOtpTrigger: 0
|
|
1453
|
+
};
|
|
1454
|
+
var NOOP_ASYNC = async () => {
|
|
1455
|
+
};
|
|
1004
1456
|
function PaymanChat({
|
|
1005
1457
|
config,
|
|
1006
1458
|
callbacks = {},
|
|
@@ -1009,6 +1461,7 @@ function PaymanChat({
|
|
|
1009
1461
|
children
|
|
1010
1462
|
}) {
|
|
1011
1463
|
const [inputValue, setInputValue] = React.useState("");
|
|
1464
|
+
const chat = paymanTypescriptAskSdk.useChat(config, callbacks);
|
|
1012
1465
|
const {
|
|
1013
1466
|
messages,
|
|
1014
1467
|
sendMessage,
|
|
@@ -1018,7 +1471,12 @@ function PaymanChat({
|
|
|
1018
1471
|
cancelStream,
|
|
1019
1472
|
getSessionId,
|
|
1020
1473
|
getMessages
|
|
1021
|
-
} =
|
|
1474
|
+
} = chat;
|
|
1475
|
+
const userActionState = chat.userActionState ?? DEFAULT_USER_ACTION_STATE;
|
|
1476
|
+
const approveUserAction = chat.approveUserAction ?? NOOP_ASYNC;
|
|
1477
|
+
const rejectUserAction = chat.rejectUserAction ?? NOOP_ASYNC;
|
|
1478
|
+
const resendOtp = chat.resendOtp ?? NOOP_ASYNC;
|
|
1479
|
+
const isUserActionSupported = typeof chat.approveUserAction === "function" && typeof chat.rejectUserAction === "function" && typeof chat.resendOtp === "function";
|
|
1022
1480
|
const contextValue = React.useMemo(
|
|
1023
1481
|
() => ({
|
|
1024
1482
|
resetSession,
|
|
@@ -1074,20 +1532,20 @@ function PaymanChat({
|
|
|
1074
1532
|
const isInputDisabled = isWaitingForResponse || !isSessionParamsConfigured || disableInput;
|
|
1075
1533
|
if (isChatDisabled) {
|
|
1076
1534
|
if (disabledComponent) {
|
|
1077
|
-
return /* @__PURE__ */ jsxRuntime.jsx(PaymanChatContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: [
|
|
1535
|
+
return /* @__PURE__ */ jsxRuntime.jsx(PaymanChatContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: [styles8.container, style], children: [
|
|
1078
1536
|
children,
|
|
1079
1537
|
disabledComponent
|
|
1080
1538
|
] }) });
|
|
1081
1539
|
}
|
|
1082
|
-
return /* @__PURE__ */ jsxRuntime.jsx(PaymanChatContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: [
|
|
1540
|
+
return /* @__PURE__ */ jsxRuntime.jsx(PaymanChatContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsxRuntime.jsxs(reactNative.View, { style: [styles8.container, style], children: [
|
|
1083
1541
|
children,
|
|
1084
|
-
/* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style:
|
|
1542
|
+
/* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style: styles8.disabledContainer, children: /* @__PURE__ */ jsxRuntime.jsx(reactNative.Text, { style: styles8.disabledText, children: "Chat is currently disabled" }) })
|
|
1085
1543
|
] }) });
|
|
1086
1544
|
}
|
|
1087
1545
|
return /* @__PURE__ */ jsxRuntime.jsx(PaymanChatContext.Provider, { value: contextValue, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
1088
1546
|
reactNative.KeyboardAvoidingView,
|
|
1089
1547
|
{
|
|
1090
|
-
style: [
|
|
1548
|
+
style: [styles8.container, style],
|
|
1091
1549
|
behavior: reactNative.Platform.OS === "ios" ? "padding" : "height",
|
|
1092
1550
|
keyboardVerticalOffset: reactNative.Platform.OS === "ios" ? 90 : 0,
|
|
1093
1551
|
children: [
|
|
@@ -1130,12 +1588,23 @@ function PaymanChat({
|
|
|
1130
1588
|
inputStyle,
|
|
1131
1589
|
layout
|
|
1132
1590
|
}
|
|
1591
|
+
),
|
|
1592
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
1593
|
+
UserActionModal,
|
|
1594
|
+
{
|
|
1595
|
+
isOpen: isUserActionSupported && userActionState.request !== null,
|
|
1596
|
+
userActionRequest: userActionState.request,
|
|
1597
|
+
onApprove: approveUserAction,
|
|
1598
|
+
onReject: rejectUserAction,
|
|
1599
|
+
onResend: resendOtp,
|
|
1600
|
+
clearOtpTrigger: userActionState.clearOtpTrigger
|
|
1601
|
+
}
|
|
1133
1602
|
)
|
|
1134
1603
|
]
|
|
1135
1604
|
}
|
|
1136
1605
|
) });
|
|
1137
1606
|
}
|
|
1138
|
-
var
|
|
1607
|
+
var styles8 = reactNative.StyleSheet.create({
|
|
1139
1608
|
container: {
|
|
1140
1609
|
flex: 1,
|
|
1141
1610
|
backgroundColor: "#FFF",
|
|
@@ -1157,14 +1626,26 @@ var styles6 = reactNative.StyleSheet.create({
|
|
|
1157
1626
|
}
|
|
1158
1627
|
});
|
|
1159
1628
|
|
|
1629
|
+
Object.defineProperty(exports, "cancelUserAction", {
|
|
1630
|
+
enumerable: true,
|
|
1631
|
+
get: function () { return paymanTypescriptAskSdk.cancelUserAction; }
|
|
1632
|
+
});
|
|
1160
1633
|
Object.defineProperty(exports, "generateId", {
|
|
1161
1634
|
enumerable: true,
|
|
1162
1635
|
get: function () { return paymanTypescriptAskSdk.generateId; }
|
|
1163
1636
|
});
|
|
1637
|
+
Object.defineProperty(exports, "resendUserAction", {
|
|
1638
|
+
enumerable: true,
|
|
1639
|
+
get: function () { return paymanTypescriptAskSdk.resendUserAction; }
|
|
1640
|
+
});
|
|
1164
1641
|
Object.defineProperty(exports, "streamWorkflowEvents", {
|
|
1165
1642
|
enumerable: true,
|
|
1166
1643
|
get: function () { return paymanTypescriptAskSdk.streamWorkflowEvents; }
|
|
1167
1644
|
});
|
|
1645
|
+
Object.defineProperty(exports, "submitUserAction", {
|
|
1646
|
+
enumerable: true,
|
|
1647
|
+
get: function () { return paymanTypescriptAskSdk.submitUserAction; }
|
|
1648
|
+
});
|
|
1168
1649
|
Object.defineProperty(exports, "useChat", {
|
|
1169
1650
|
enumerable: true,
|
|
1170
1651
|
get: function () { return paymanTypescriptAskSdk.useChat; }
|