@opengeni/react-native 1.4.5-canary.37615713321001

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.
Files changed (132) hide show
  1. package/LICENSE +190 -0
  2. package/README.md +74 -0
  3. package/dist/adapters.d.ts +53 -0
  4. package/dist/adapters.js +3 -0
  5. package/dist/adapters.js.map +1 -0
  6. package/dist/attachments.d.ts +75 -0
  7. package/dist/chunk-3VSZAQ7G.js +391 -0
  8. package/dist/chunk-3VSZAQ7G.js.map +1 -0
  9. package/dist/chunk-5ZVK7WKA.js +88 -0
  10. package/dist/chunk-5ZVK7WKA.js.map +1 -0
  11. package/dist/chunk-EEDIMY3L.js +240 -0
  12. package/dist/chunk-EEDIMY3L.js.map +1 -0
  13. package/dist/chunk-M23SDI4R.js +83 -0
  14. package/dist/chunk-M23SDI4R.js.map +1 -0
  15. package/dist/chunk-PHJBSAR3.js +2006 -0
  16. package/dist/chunk-PHJBSAR3.js.map +1 -0
  17. package/dist/environment.d.ts +19 -0
  18. package/dist/expo.d.ts +25 -0
  19. package/dist/expo.js +267 -0
  20. package/dist/expo.js.map +1 -0
  21. package/dist/index.d.ts +13 -0
  22. package/dist/index.js +3345 -0
  23. package/dist/index.js.map +1 -0
  24. package/dist/presentation.d.ts +262 -0
  25. package/dist/read-acknowledgement.d.ts +39 -0
  26. package/dist/realtime/call-events.d.ts +11 -0
  27. package/dist/realtime/call-view.d.ts +26 -0
  28. package/dist/realtime/expo-call.d.ts +11 -0
  29. package/dist/realtime/native-call.d.ts +104 -0
  30. package/dist/realtime/native-realtime.d.ts +35 -0
  31. package/dist/realtime/use-native-session-realtime.d.ts +25 -0
  32. package/dist/session-view.d.ts +87 -0
  33. package/dist/timeline/activity.d.ts +34 -0
  34. package/dist/timeline/composer.d.ts +86 -0
  35. package/dist/timeline/controls.d.ts +27 -0
  36. package/dist/timeline/decisions.d.ts +29 -0
  37. package/dist/timeline/feedback.d.ts +26 -0
  38. package/dist/timeline/icon-nodes.generated.d.ts +738 -0
  39. package/dist/timeline/icon.d.ts +11 -0
  40. package/dist/timeline/index.d.ts +32 -0
  41. package/dist/timeline/index.js +5419 -0
  42. package/dist/timeline/index.js.map +1 -0
  43. package/dist/timeline/markdown.d.ts +11 -0
  44. package/dist/timeline/markdown.js +415 -0
  45. package/dist/timeline/markdown.js.map +1 -0
  46. package/dist/timeline/message-attachments.d.ts +13 -0
  47. package/dist/timeline/message-timeline.d.ts +36 -0
  48. package/dist/timeline/model-picker.d.ts +17 -0
  49. package/dist/timeline/primitives.d.ts +85 -0
  50. package/dist/timeline/queue-dock.d.ts +19 -0
  51. package/dist/timeline/session-actions.d.ts +34 -0
  52. package/dist/timeline/session-list.d.ts +50 -0
  53. package/dist/timeline/session-screen.d.ts +35 -0
  54. package/dist/timeline/session-signals.d.ts +37 -0
  55. package/dist/timeline/sheet.d.ts +14 -0
  56. package/dist/timeline/theme.d.ts +58 -0
  57. package/dist/timeline/thinking-orb.d.ts +13 -0
  58. package/dist/timeline/turn.d.ts +80 -0
  59. package/dist/ui/attention.d.ts +14 -0
  60. package/dist/ui/cards.d.ts +21 -0
  61. package/dist/ui/composer.d.ts +21 -0
  62. package/dist/ui/format.d.ts +13 -0
  63. package/dist/ui/icons.d.ts +9 -0
  64. package/dist/ui/index.d.ts +12 -0
  65. package/dist/ui/index.js +1757 -0
  66. package/dist/ui/index.js.map +1 -0
  67. package/dist/ui/steps-sheet.d.ts +10 -0
  68. package/dist/ui/theme.d.ts +63 -0
  69. package/dist/ui/timeline.d.ts +48 -0
  70. package/dist/ui/web-tokens.gen.d.ts +90 -0
  71. package/dist/use-native-session.d.ts +40 -0
  72. package/dist/view-model.d.ts +52 -0
  73. package/dist/voice-input.d.ts +102 -0
  74. package/dist/webrtc.d.ts +9 -0
  75. package/dist/webrtc.js +19 -0
  76. package/dist/webrtc.js.map +1 -0
  77. package/expo-module.config.json +7 -0
  78. package/ios/OpenGeniCall.podspec +22 -0
  79. package/ios/OpenGeniCallAppDelegateSubscriber.swift +29 -0
  80. package/ios/OpenGeniCallCenter.swift +189 -0
  81. package/ios/OpenGeniCallModule.swift +64 -0
  82. package/package.json +93 -0
  83. package/src/adapters.ts +150 -0
  84. package/src/attachments.ts +396 -0
  85. package/src/environment.tsx +214 -0
  86. package/src/expo.ts +295 -0
  87. package/src/index.ts +98 -0
  88. package/src/presentation.ts +285 -0
  89. package/src/read-acknowledgement.ts +72 -0
  90. package/src/realtime/call-events.ts +41 -0
  91. package/src/realtime/call-view.tsx +220 -0
  92. package/src/realtime/expo-call.ts +49 -0
  93. package/src/realtime/native-call.ts +266 -0
  94. package/src/realtime/native-realtime.ts +115 -0
  95. package/src/realtime/use-native-session-realtime.ts +29 -0
  96. package/src/session-view.tsx +2251 -0
  97. package/src/timeline/activity.tsx +736 -0
  98. package/src/timeline/composer.tsx +686 -0
  99. package/src/timeline/controls.tsx +151 -0
  100. package/src/timeline/decisions.tsx +651 -0
  101. package/src/timeline/feedback.tsx +251 -0
  102. package/src/timeline/icon-nodes.generated.ts +1830 -0
  103. package/src/timeline/icon.tsx +44 -0
  104. package/src/timeline/index.ts +67 -0
  105. package/src/timeline/markdown.tsx +510 -0
  106. package/src/timeline/message-attachments.tsx +155 -0
  107. package/src/timeline/message-timeline.tsx +1042 -0
  108. package/src/timeline/model-picker.tsx +450 -0
  109. package/src/timeline/primitives.tsx +561 -0
  110. package/src/timeline/queue-dock.tsx +331 -0
  111. package/src/timeline/session-actions.tsx +379 -0
  112. package/src/timeline/session-list.tsx +338 -0
  113. package/src/timeline/session-screen.tsx +488 -0
  114. package/src/timeline/session-signals.tsx +312 -0
  115. package/src/timeline/sheet.tsx +153 -0
  116. package/src/timeline/theme.tsx +128 -0
  117. package/src/timeline/thinking-orb.tsx +93 -0
  118. package/src/timeline/turn.tsx +569 -0
  119. package/src/ui/attention.tsx +220 -0
  120. package/src/ui/cards.tsx +267 -0
  121. package/src/ui/composer.tsx +296 -0
  122. package/src/ui/format.ts +86 -0
  123. package/src/ui/icons.tsx +131 -0
  124. package/src/ui/index.ts +18 -0
  125. package/src/ui/steps-sheet.tsx +71 -0
  126. package/src/ui/theme.ts +261 -0
  127. package/src/ui/timeline.tsx +837 -0
  128. package/src/ui/web-tokens.gen.ts +94 -0
  129. package/src/use-native-session.ts +219 -0
  130. package/src/view-model.ts +485 -0
  131. package/src/voice-input.ts +382 -0
  132. package/src/webrtc.ts +30 -0
@@ -0,0 +1,391 @@
1
+ import { useNativeTimelineTheme, fontStyle, Icon } from './chunk-PHJBSAR3.js';
2
+ import { stringifyPayload } from '@opengeni/react/timeline-model';
3
+ import { createContext, useContext, useEffect, useState } from 'react';
4
+ import { View, Text, Pressable, ScrollView } from 'react-native';
5
+ import Animated, { useSharedValue, withRepeat, withTiming, Easing, cancelAnimation, useAnimatedStyle, interpolateColor } from 'react-native-reanimated';
6
+ import { jsxs, jsx } from 'react/jsx-runtime';
7
+
8
+ var ReleaseFollowContext = createContext(() => void 0);
9
+ var ReleaseFollowProvider = ReleaseFollowContext.Provider;
10
+ function useReleaseFollow() {
11
+ return useContext(ReleaseFollowContext);
12
+ }
13
+ function iconToneColor(theme, tone) {
14
+ switch (tone) {
15
+ case "accent":
16
+ return theme.colors.accent;
17
+ case "failed":
18
+ return theme.colors["status-failed"];
19
+ case "running":
20
+ return theme.colors["status-running"];
21
+ default:
22
+ return theme.colors["fg-subtle"];
23
+ }
24
+ }
25
+ var ROW_MIN_HEIGHT = 44;
26
+ function Chip({ chip }) {
27
+ const theme = useNativeTimelineTheme();
28
+ const text = {
29
+ ...fontStyle(theme, 400, "mono"),
30
+ fontSize: theme.size.xs,
31
+ lineHeight: theme.size.xs + 2,
32
+ color: chip.tone === "bad" ? theme.colors["status-failed"] : theme.colors["fg-subtle"]
33
+ };
34
+ if (chip.tone === "bad") {
35
+ return /* @__PURE__ */ jsxs(View, { style: { flexDirection: "row", alignItems: "center", gap: chip.text ? 6 : 0 }, children: [
36
+ /* @__PURE__ */ jsx(
37
+ View,
38
+ {
39
+ style: {
40
+ width: 6,
41
+ height: 6,
42
+ borderRadius: 3,
43
+ backgroundColor: theme.colors["status-failed"]
44
+ }
45
+ }
46
+ ),
47
+ chip.text ? /* @__PURE__ */ jsx(Text, { style: text, children: chip.text }) : null
48
+ ] });
49
+ }
50
+ return /* @__PURE__ */ jsx(Text, { style: text, children: chip.text });
51
+ }
52
+ function PulseDot({ color, size = 6 }) {
53
+ const value = useSharedValue(1);
54
+ useEffect(() => {
55
+ value.value = withRepeat(
56
+ withTiming(0.35, { duration: 900, easing: Easing.inOut(Easing.ease) }),
57
+ -1,
58
+ true
59
+ );
60
+ return () => cancelAnimation(value);
61
+ }, [value]);
62
+ const style = useAnimatedStyle(() => ({ opacity: value.value }));
63
+ return /* @__PURE__ */ jsx(
64
+ Animated.View,
65
+ {
66
+ style: [{ width: size, height: size, borderRadius: size / 2, backgroundColor: color }, style]
67
+ }
68
+ );
69
+ }
70
+ function ShimmerText({
71
+ children,
72
+ style,
73
+ active = true,
74
+ numberOfLines
75
+ }) {
76
+ const theme = useNativeTimelineTheme();
77
+ const value = useSharedValue(0);
78
+ useEffect(() => {
79
+ if (!active) return;
80
+ value.value = withRepeat(
81
+ withTiming(1, { duration: 1400, easing: Easing.inOut(Easing.ease) }),
82
+ -1,
83
+ true
84
+ );
85
+ return () => cancelAnimation(value);
86
+ }, [active, value]);
87
+ const subtle = theme.colors["fg-subtle"];
88
+ const strong = theme.colors.fg;
89
+ const animated = useAnimatedStyle(() => ({
90
+ color: interpolateColor(value.value, [0, 1], [subtle, strong])
91
+ }));
92
+ if (!active) {
93
+ return /* @__PURE__ */ jsx(Text, { style, numberOfLines, children });
94
+ }
95
+ return /* @__PURE__ */ jsx(Animated.Text, { style: [style, animated], numberOfLines, children });
96
+ }
97
+ function ActivityDisclosure({
98
+ icon,
99
+ iconTone: iconToneProp = "muted",
100
+ title,
101
+ titleMono,
102
+ running,
103
+ preview,
104
+ media,
105
+ chip: chipProp,
106
+ failed,
107
+ cancelled,
108
+ expandable = true,
109
+ defaultOpen,
110
+ compact,
111
+ accessibilityLabel,
112
+ children
113
+ }) {
114
+ const theme = useNativeTimelineTheme();
115
+ const [open, setOpen] = useState(defaultOpen ?? false);
116
+ const releaseFollow = useReleaseFollow();
117
+ const iconTone = failed && iconToneProp === "muted" ? "failed" : iconToneProp;
118
+ const chip = chipProp ?? (failed ? { tone: "bad", text: "failed" } : cancelled ? { tone: "interrupted", text: "interrupted" } : void 0);
119
+ const tint = iconToneColor(theme, iconTone);
120
+ const iconNode = typeof icon === "string" ? /* @__PURE__ */ jsx(Icon, { name: icon, size: 14, color: tint }) : icon;
121
+ const titleStyle = titleMono ? {
122
+ ...fontStyle(theme, 400, "mono"),
123
+ fontSize: theme.size.sm,
124
+ lineHeight: 20,
125
+ color: theme.colors["fg-muted"]
126
+ } : {
127
+ ...fontStyle(theme, 500),
128
+ fontSize: theme.size.base,
129
+ lineHeight: 20,
130
+ color: theme.colors["fg-muted"]
131
+ };
132
+ const previewStyle = {
133
+ ...fontStyle(theme),
134
+ fontSize: theme.size.sm,
135
+ lineHeight: 18,
136
+ color: theme.colors["fg-subtle"]
137
+ };
138
+ const titleNode = typeof title === "string" ? /* @__PURE__ */ jsx(ShimmerText, { style: titleStyle, active: Boolean(running), numberOfLines: 1, children: title }) : title;
139
+ const previewNode = preview == null ? null : typeof preview === "string" ? /* @__PURE__ */ jsx(Text, { style: [previewStyle, { flexShrink: 1 }], numberOfLines: 1, children: preview }) : preview;
140
+ if (compact) {
141
+ const reelTitle = {
142
+ ...fontStyle(theme, 400),
143
+ fontSize: 13,
144
+ lineHeight: 20,
145
+ color: theme.colors["fg-muted"]
146
+ };
147
+ const reelPreview = {
148
+ ...fontStyle(theme, 400),
149
+ fontSize: 13,
150
+ lineHeight: 20,
151
+ color: theme.colors["fg-subtle"]
152
+ };
153
+ return /* @__PURE__ */ jsxs(View, { style: { flexDirection: "row", alignItems: "center", gap: 8, minWidth: 0, flex: 1 }, children: [
154
+ iconNode,
155
+ /* @__PURE__ */ jsx(View, { style: { flexShrink: 0, maxWidth: preview == null ? "100%" : "75%" }, children: typeof title === "string" ? /* @__PURE__ */ jsx(ShimmerText, { style: reelTitle, active: Boolean(running), numberOfLines: 1, children: title }) : title }),
156
+ preview == null ? null : /* @__PURE__ */ jsx(View, { style: { flex: 1, minWidth: 0 }, children: typeof preview === "string" ? /* @__PURE__ */ jsx(Text, { style: reelPreview, numberOfLines: 1, children: preview }) : preview })
157
+ ] });
158
+ }
159
+ const hasBody = expandable && children != null;
160
+ const row = /* @__PURE__ */ jsxs(
161
+ View,
162
+ {
163
+ style: {
164
+ flexDirection: "row",
165
+ alignItems: "center",
166
+ gap: 8,
167
+ minHeight: ROW_MIN_HEIGHT,
168
+ paddingHorizontal: 6,
169
+ paddingVertical: 10,
170
+ borderRadius: theme.radius.sm
171
+ },
172
+ children: [
173
+ hasBody ? /* @__PURE__ */ jsx(View, { style: { transform: [{ rotate: open ? "90deg" : "0deg" }] }, children: /* @__PURE__ */ jsx(Icon, { name: "chevron-right", size: 14, color: theme.colors["fg-subtle"] }) }) : /* @__PURE__ */ jsx(View, { style: { width: 14 } }),
174
+ iconNode,
175
+ /* @__PURE__ */ jsxs(View, { style: { flexDirection: "row", alignItems: "center", gap: 8, flex: 1, minWidth: 0 }, children: [
176
+ /* @__PURE__ */ jsx(View, { style: { flexShrink: 1, minWidth: 0 }, children: titleNode }),
177
+ previewNode && !open && media == null ? /* @__PURE__ */ jsx(View, { style: { flex: 1, minWidth: 0 }, children: previewNode }) : null
178
+ ] }),
179
+ media != null && !open ? /* @__PURE__ */ jsx(View, { style: { paddingLeft: 8, flexShrink: 0 }, children: media }) : chip && !open ? /* @__PURE__ */ jsx(View, { style: { paddingLeft: 8 }, children: /* @__PURE__ */ jsx(Chip, { chip }) }) : null
180
+ ]
181
+ }
182
+ );
183
+ if (!hasBody) return row;
184
+ return /* @__PURE__ */ jsxs(View, { children: [
185
+ /* @__PURE__ */ jsx(
186
+ Pressable,
187
+ {
188
+ accessibilityRole: "button",
189
+ accessibilityState: { expanded: open },
190
+ accessibilityLabel: accessibilityLabel ?? (typeof title === "string" ? title : void 0),
191
+ onPress: () => {
192
+ releaseFollow();
193
+ setOpen((value) => !value);
194
+ },
195
+ style: ({ pressed }) => ({
196
+ borderRadius: theme.radius.sm,
197
+ backgroundColor: pressed ? theme.colors.hover : "transparent"
198
+ }),
199
+ children: row
200
+ }
201
+ ),
202
+ open ? /* @__PURE__ */ jsx(View, { style: { marginLeft: 28, marginTop: 6, marginBottom: 8, gap: 8 }, children }) : null
203
+ ] });
204
+ }
205
+ function RunningPreview({ text, compact }) {
206
+ const theme = useNativeTimelineTheme();
207
+ return /* @__PURE__ */ jsxs(View, { style: { flexDirection: "row", alignItems: "center", gap: 6, minWidth: 0 }, children: [
208
+ compact ? null : /* @__PURE__ */ jsx(PulseDot, { color: theme.colors["status-running"] }),
209
+ /* @__PURE__ */ jsx(
210
+ Text,
211
+ {
212
+ numberOfLines: 1,
213
+ style: {
214
+ ...fontStyle(theme),
215
+ fontSize: compact ? 13 : theme.size.sm,
216
+ lineHeight: compact ? 20 : 18,
217
+ color: theme.colors["fg-subtle"],
218
+ flexShrink: 1
219
+ },
220
+ children: text
221
+ }
222
+ )
223
+ ] });
224
+ }
225
+ function RuledBlock({
226
+ tone,
227
+ children
228
+ }) {
229
+ const theme = useNativeTimelineTheme();
230
+ const borderColor = tone === "failed" ? withAlpha(theme.colors["status-failed"], 0.5) : tone === "live" ? withAlpha(theme.colors["status-running"], 0.5) : theme.colors.border;
231
+ return /* @__PURE__ */ jsx(
232
+ View,
233
+ {
234
+ style: { borderLeftWidth: 2, borderLeftColor: borderColor, paddingLeft: 12, minWidth: 0 },
235
+ children
236
+ }
237
+ );
238
+ }
239
+ function TermBlock({
240
+ command,
241
+ workdir,
242
+ output,
243
+ live,
244
+ failed,
245
+ tailLines = 12
246
+ }) {
247
+ const theme = useNativeTimelineTheme();
248
+ const [full, setFull] = useState(false);
249
+ const lines = output.split("\n");
250
+ const big = lines.length > tailLines + 4;
251
+ const shown = full || !big ? output : lines.slice(-tailLines).join("\n");
252
+ const mono = {
253
+ ...fontStyle(theme, 400, "mono"),
254
+ fontSize: theme.size.xs,
255
+ lineHeight: 20
256
+ };
257
+ const showHeader = command != null || Boolean(workdir);
258
+ return /* @__PURE__ */ jsxs(RuledBlock, { tone: failed ? "failed" : live ? "live" : "neutral", children: [
259
+ showHeader ? /* @__PURE__ */ jsxs(View, { style: { flexDirection: "row", alignItems: "center", gap: 8, paddingBottom: 4 }, children: [
260
+ /* @__PURE__ */ jsx(Text, { style: [mono, { color: theme.colors["status-idle"] }], children: "$" }),
261
+ /* @__PURE__ */ jsx(
262
+ Text,
263
+ {
264
+ style: [mono, { fontSize: theme.size.sm, color: theme.colors["fg-muted"], flex: 1 }],
265
+ numberOfLines: 1,
266
+ children: command ?? ""
267
+ }
268
+ ),
269
+ workdir ? /* @__PURE__ */ jsx(
270
+ Text,
271
+ {
272
+ style: [mono, { color: theme.colors["fg-subtle"], flexShrink: 1 }],
273
+ numberOfLines: 1,
274
+ children: workdir
275
+ }
276
+ ) : null
277
+ ] }) : null,
278
+ output.trim() === "" ? /* @__PURE__ */ jsx(Text, { style: [mono, { fontStyle: "italic", color: theme.colors["fg-subtle"] }], children: "(no output)" }) : /* @__PURE__ */ jsx(ScrollView, { style: { maxHeight: 288 }, nestedScrollEnabled: true, children: /* @__PURE__ */ jsx(Text, { selectable: true, style: [mono, { color: theme.colors["fg-muted"] }], children: shown }) }),
279
+ big && !full ? /* @__PURE__ */ jsx(Pressable, { onPress: () => setFull(true), accessibilityRole: "button", children: /* @__PURE__ */ jsxs(
280
+ Text,
281
+ {
282
+ style: {
283
+ ...fontStyle(theme),
284
+ marginTop: 4,
285
+ fontSize: theme.size.xs,
286
+ color: theme.colors["fg-subtle"]
287
+ },
288
+ children: [
289
+ "show full output (",
290
+ lines.length,
291
+ " lines)"
292
+ ]
293
+ }
294
+ ) }) : null
295
+ ] });
296
+ }
297
+ function PayloadBlock({
298
+ label,
299
+ value,
300
+ failed
301
+ }) {
302
+ const theme = useNativeTimelineTheme();
303
+ const text = typeof value === "string" ? value : stringifyPayload(value);
304
+ if (!text || text.trim() === "") return null;
305
+ return /* @__PURE__ */ jsxs(RuledBlock, { tone: failed ? "failed" : "neutral", children: [
306
+ /* @__PURE__ */ jsx(
307
+ Text,
308
+ {
309
+ style: {
310
+ ...fontStyle(theme, 500),
311
+ marginBottom: 4,
312
+ fontSize: theme.size.xs,
313
+ letterSpacing: theme.size.xs * 0.08,
314
+ textTransform: "uppercase",
315
+ color: theme.colors["fg-subtle"]
316
+ },
317
+ children: label
318
+ }
319
+ ),
320
+ /* @__PURE__ */ jsx(ScrollView, { style: { maxHeight: 256 }, nestedScrollEnabled: true, children: /* @__PURE__ */ jsx(
321
+ Text,
322
+ {
323
+ selectable: true,
324
+ style: {
325
+ ...fontStyle(theme, 400, "mono"),
326
+ fontSize: theme.size.xs,
327
+ lineHeight: 20,
328
+ color: failed ? theme.colors["status-failed"] : theme.colors["fg-muted"]
329
+ },
330
+ children: text
331
+ }
332
+ ) })
333
+ ] });
334
+ }
335
+ function BodyNote({ children, tone }) {
336
+ const theme = useNativeTimelineTheme();
337
+ if (tone === "error") {
338
+ return /* @__PURE__ */ jsx(RuledBlock, { tone: "failed", children: /* @__PURE__ */ jsx(
339
+ Text,
340
+ {
341
+ style: {
342
+ ...fontStyle(theme, 400, "mono"),
343
+ fontSize: theme.size.xs,
344
+ lineHeight: 20,
345
+ color: theme.colors["status-failed"]
346
+ },
347
+ children
348
+ }
349
+ ) });
350
+ }
351
+ return /* @__PURE__ */ jsx(
352
+ Text,
353
+ {
354
+ style: {
355
+ ...fontStyle(theme),
356
+ paddingHorizontal: 2,
357
+ fontSize: theme.size.sm,
358
+ lineHeight: 20,
359
+ fontStyle: "italic",
360
+ color: theme.colors["fg-subtle"]
361
+ },
362
+ children
363
+ }
364
+ );
365
+ }
366
+ function rgbOf(color) {
367
+ const rgb = color.match(/rgba?\(\s*(\d+)[,\s]+(\d+)[,\s]+(\d+)/);
368
+ if (rgb) return [Number(rgb[1]), Number(rgb[2]), Number(rgb[3])];
369
+ const hex = color.match(/^#([0-9a-f]{2})([0-9a-f]{2})([0-9a-f]{2})/i);
370
+ if (hex) return [parseInt(hex[1], 16), parseInt(hex[2], 16), parseInt(hex[3], 16)];
371
+ return null;
372
+ }
373
+ function blendOver(base, color, alpha) {
374
+ const under = rgbOf(base);
375
+ const over = rgbOf(color);
376
+ if (!under || !over) return withAlpha(color, alpha);
377
+ const mix = (index) => Math.round(under[index] * (1 - alpha) + over[index] * alpha);
378
+ return `rgb(${mix(0)}, ${mix(1)}, ${mix(2)})`;
379
+ }
380
+ function withAlpha(color, alpha) {
381
+ const rgb = color.match(/rgba?\(\s*(\d+)[,\s]+(\d+)[,\s]+(\d+)/);
382
+ if (rgb) return `rgba(${rgb[1]}, ${rgb[2]}, ${rgb[3]}, ${alpha})`;
383
+ const hex = color.match(/^#([0-9a-f]{2})([0-9a-f]{2})([0-9a-f]{2})/i);
384
+ if (hex)
385
+ return `rgba(${parseInt(hex[1], 16)}, ${parseInt(hex[2], 16)}, ${parseInt(hex[3], 16)}, ${alpha})`;
386
+ return color;
387
+ }
388
+
389
+ export { ActivityDisclosure, BodyNote, Chip, PayloadBlock, PulseDot, ROW_MIN_HEIGHT, ReleaseFollowProvider, RunningPreview, ShimmerText, TermBlock, blendOver, useReleaseFollow, withAlpha };
390
+ //# sourceMappingURL=chunk-3VSZAQ7G.js.map
391
+ //# sourceMappingURL=chunk-3VSZAQ7G.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/timeline/primitives.tsx"],"names":[],"mappings":"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","file":"chunk-3VSZAQ7G.js","sourcesContent":["import { stringifyPayload } from \"@opengeni/react/timeline-model\";\nimport { createContext, useContext, useEffect, useState, type ReactNode } from \"react\";\nimport { Pressable, ScrollView, Text, View, type TextStyle } from \"react-native\";\nimport Animated, {\n cancelAnimation,\n Easing,\n interpolateColor,\n useAnimatedStyle,\n useSharedValue,\n withRepeat,\n withTiming,\n} from \"react-native-reanimated\";\nimport { Icon, type NativeIconName } from \"./icon\";\nimport { fontStyle, useNativeTimelineTheme, type NativeTimelineTheme } from \"./theme\";\n\n/**\n * A reader opening or closing a disclosure owns the scroll position: the\n * timeline stops following the tip (web: an aria-expanded click releases pin).\n */\nconst ReleaseFollowContext = createContext<() => void>(() => undefined);\nexport const ReleaseFollowProvider = ReleaseFollowContext.Provider;\nexport function useReleaseFollow(): () => void {\n return useContext(ReleaseFollowContext);\n}\n\n/* ----------------------------------------------------------------------------\n Native counterparts of the web timeline primitives (timeline/shared.tsx).\n Same anatomy and tokens: chevron, tinted icon, title, quiet preview, at most\n one right-gutter chip; the body mounts only when expanded.\n -------------------------------------------------------------------------- */\n\nexport type DisclosureChip = { tone: \"ok\" | \"bad\" | \"muted\" | \"interrupted\"; text: string };\nexport type IconTone = \"accent\" | \"failed\" | \"running\" | \"muted\";\n\nexport function iconToneColor(theme: NativeTimelineTheme, tone: IconTone): string {\n switch (tone) {\n case \"accent\":\n return theme.colors.accent;\n case \"failed\":\n return theme.colors[\"status-failed\"];\n case \"running\":\n return theme.colors[\"status-running\"];\n default:\n return theme.colors[\"fg-subtle\"];\n }\n}\n\n/** Web `pointer-coarse:min-h-11`: every disclosure row is a 44pt touch target. */\nexport const ROW_MIN_HEIGHT = 44;\n\nexport function Chip({ chip }: { chip: DisclosureChip }) {\n const theme = useNativeTimelineTheme();\n const text: TextStyle = {\n ...fontStyle(theme, 400, \"mono\"),\n fontSize: theme.size.xs,\n lineHeight: theme.size.xs + 2,\n color: chip.tone === \"bad\" ? theme.colors[\"status-failed\"] : theme.colors[\"fg-subtle\"],\n };\n if (chip.tone === \"bad\") {\n return (\n <View style={{ flexDirection: \"row\", alignItems: \"center\", gap: chip.text ? 6 : 0 }}>\n <View\n style={{\n width: 6,\n height: 6,\n borderRadius: 3,\n backgroundColor: theme.colors[\"status-failed\"],\n }}\n />\n {chip.text ? <Text style={text}>{chip.text}</Text> : null}\n </View>\n );\n }\n return <Text style={text}>{chip.text}</Text>;\n}\n\n/** The web `animate-og-pulse` dot that rides a running preview. */\nexport function PulseDot({ color, size = 6 }: { color: string; size?: number }) {\n const value = useSharedValue(1);\n useEffect(() => {\n value.value = withRepeat(\n withTiming(0.35, { duration: 900, easing: Easing.inOut(Easing.ease) }),\n -1,\n true,\n );\n return () => cancelAnimation(value);\n }, [value]);\n const style = useAnimatedStyle(() => ({ opacity: value.value }));\n return (\n <Animated.View\n style={[{ width: size, height: size, borderRadius: size / 2, backgroundColor: color }, style]}\n />\n );\n}\n\n/**\n * The web `og-shimmer-text` (a moving fg-subtle → fg → fg-subtle gradient) as an\n * ink sweep between the same two tokens.\n */\nexport function ShimmerText({\n children,\n style,\n active = true,\n numberOfLines,\n}: {\n children: ReactNode;\n style?: TextStyle | TextStyle[];\n active?: boolean;\n numberOfLines?: number;\n}) {\n const theme = useNativeTimelineTheme();\n const value = useSharedValue(0);\n useEffect(() => {\n if (!active) return;\n value.value = withRepeat(\n withTiming(1, { duration: 1400, easing: Easing.inOut(Easing.ease) }),\n -1,\n true,\n );\n return () => cancelAnimation(value);\n }, [active, value]);\n const subtle = theme.colors[\"fg-subtle\"];\n const strong = theme.colors.fg;\n const animated = useAnimatedStyle(() => ({\n color: interpolateColor(value.value, [0, 1], [subtle, strong]),\n }));\n if (!active) {\n return (\n <Text style={style} numberOfLines={numberOfLines}>\n {children}\n </Text>\n );\n }\n return (\n <Animated.Text style={[style, animated]} numberOfLines={numberOfLines}>\n {children}\n </Animated.Text>\n );\n}\n\nexport interface ActivityDisclosureProps {\n icon: NativeIconName | ReactNode;\n iconTone?: IconTone | undefined;\n title: ReactNode;\n titleMono?: boolean | undefined;\n /** Title shimmer + preview pulse while in flight. */\n running?: boolean | undefined;\n preview?: ReactNode | undefined;\n /**\n * A small trailing element (a thumbnail, an open action) shown in the right\n * gutter in place of the preview and chip while collapsed, as on web.\n */\n media?: ReactNode | undefined;\n chip?: DisclosureChip | undefined;\n failed?: boolean | undefined;\n cancelled?: boolean | undefined;\n expandable?: boolean | undefined;\n defaultOpen?: boolean | undefined;\n /** Compact reel rendering for the rolling status (no chevron, no body). */\n compact?: boolean | undefined;\n accessibilityLabel?: string | undefined;\n children?: ReactNode | undefined;\n}\n\n/** The one row shape every activity uses, matching the web ActivityDisclosure. */\nexport function ActivityDisclosure({\n icon,\n iconTone: iconToneProp = \"muted\",\n title,\n titleMono,\n running,\n preview,\n media,\n chip: chipProp,\n failed,\n cancelled,\n expandable = true,\n defaultOpen,\n compact,\n accessibilityLabel,\n children,\n}: ActivityDisclosureProps) {\n const theme = useNativeTimelineTheme();\n const [open, setOpen] = useState(defaultOpen ?? false);\n const releaseFollow = useReleaseFollow();\n const iconTone = failed && iconToneProp === \"muted\" ? \"failed\" : iconToneProp;\n const chip =\n chipProp ??\n (failed\n ? ({ tone: \"bad\", text: \"failed\" } as const)\n : cancelled\n ? ({ tone: \"interrupted\", text: \"interrupted\" } as const)\n : undefined);\n const tint = iconToneColor(theme, iconTone);\n const iconNode =\n typeof icon === \"string\" ? <Icon name={icon as NativeIconName} size={14} color={tint} /> : icon;\n const titleStyle: TextStyle = titleMono\n ? {\n ...fontStyle(theme, 400, \"mono\"),\n fontSize: theme.size.sm,\n lineHeight: 20,\n color: theme.colors[\"fg-muted\"],\n }\n : {\n ...fontStyle(theme, 500),\n fontSize: theme.size.base,\n lineHeight: 20,\n color: theme.colors[\"fg-muted\"],\n };\n const previewStyle: TextStyle = {\n ...fontStyle(theme),\n fontSize: theme.size.sm,\n lineHeight: 18,\n color: theme.colors[\"fg-subtle\"],\n };\n const titleNode =\n typeof title === \"string\" ? (\n <ShimmerText style={titleStyle} active={Boolean(running)} numberOfLines={1}>\n {title}\n </ShimmerText>\n ) : (\n title\n );\n const previewNode =\n preview == null ? null : typeof preview === \"string\" ? (\n <Text style={[previewStyle, { flexShrink: 1 }]} numberOfLines={1}>\n {preview}\n </Text>\n ) : (\n preview\n );\n\n if (compact) {\n // Web `og-rolling-label`: 13px/450 muted title (never mono), subtle preview.\n const reelTitle: TextStyle = {\n ...fontStyle(theme, 400),\n fontSize: 13,\n lineHeight: 20,\n color: theme.colors[\"fg-muted\"],\n };\n const reelPreview: TextStyle = {\n ...fontStyle(theme, 400),\n fontSize: 13,\n lineHeight: 20,\n color: theme.colors[\"fg-subtle\"],\n };\n return (\n <View style={{ flexDirection: \"row\", alignItems: \"center\", gap: 8, minWidth: 0, flex: 1 }}>\n {iconNode}\n <View style={{ flexShrink: 0, maxWidth: preview == null ? \"100%\" : \"75%\" }}>\n {typeof title === \"string\" ? (\n <ShimmerText style={reelTitle} active={Boolean(running)} numberOfLines={1}>\n {title}\n </ShimmerText>\n ) : (\n title\n )}\n </View>\n {preview == null ? null : (\n <View style={{ flex: 1, minWidth: 0 }}>\n {typeof preview === \"string\" ? (\n <Text style={reelPreview} numberOfLines={1}>\n {preview}\n </Text>\n ) : (\n preview\n )}\n </View>\n )}\n </View>\n );\n }\n\n const hasBody = expandable && children != null;\n const row = (\n <View\n style={{\n flexDirection: \"row\",\n alignItems: \"center\",\n gap: 8,\n minHeight: ROW_MIN_HEIGHT,\n paddingHorizontal: 6,\n paddingVertical: 10,\n borderRadius: theme.radius.sm,\n }}\n >\n {hasBody ? (\n <View style={{ transform: [{ rotate: open ? \"90deg\" : \"0deg\" }] }}>\n <Icon name=\"chevron-right\" size={14} color={theme.colors[\"fg-subtle\"]} />\n </View>\n ) : (\n <View style={{ width: 14 }} />\n )}\n {iconNode}\n <View style={{ flexDirection: \"row\", alignItems: \"center\", gap: 8, flex: 1, minWidth: 0 }}>\n <View style={{ flexShrink: 1, minWidth: 0 }}>{titleNode}</View>\n {previewNode && !open && media == null ? (\n <View style={{ flex: 1, minWidth: 0 }}>{previewNode}</View>\n ) : null}\n </View>\n {media != null && !open ? (\n <View style={{ paddingLeft: 8, flexShrink: 0 }}>{media}</View>\n ) : chip && !open ? (\n <View style={{ paddingLeft: 8 }}>\n <Chip chip={chip} />\n </View>\n ) : null}\n </View>\n );\n if (!hasBody) return row;\n return (\n <View>\n <Pressable\n accessibilityRole=\"button\"\n accessibilityState={{ expanded: open }}\n accessibilityLabel={accessibilityLabel ?? (typeof title === \"string\" ? title : undefined)}\n onPress={() => {\n releaseFollow();\n setOpen((value) => !value);\n }}\n style={({ pressed }) => ({\n borderRadius: theme.radius.sm,\n backgroundColor: pressed ? theme.colors.hover : \"transparent\",\n })}\n >\n {row}\n </Pressable>\n {open ? (\n <View style={{ marginLeft: 28, marginTop: 6, marginBottom: 8, gap: 8 }}>{children}</View>\n ) : null}\n </View>\n );\n}\n\n/** A running preview: the pulse locus immediately left of the status words. */\nexport function RunningPreview({ text, compact }: { text: string; compact?: boolean }) {\n const theme = useNativeTimelineTheme();\n return (\n <View style={{ flexDirection: \"row\", alignItems: \"center\", gap: 6, minWidth: 0 }}>\n {compact ? null : <PulseDot color={theme.colors[\"status-running\"]} />}\n <Text\n numberOfLines={1}\n style={{\n ...fontStyle(theme),\n fontSize: compact ? 13 : theme.size.sm,\n lineHeight: compact ? 20 : 18,\n color: theme.colors[\"fg-subtle\"],\n flexShrink: 1,\n }}\n >\n {text}\n </Text>\n </View>\n );\n}\n\nfunction RuledBlock({\n tone,\n children,\n}: {\n tone: \"neutral\" | \"failed\" | \"live\";\n children: ReactNode;\n}) {\n const theme = useNativeTimelineTheme();\n const borderColor =\n tone === \"failed\"\n ? withAlpha(theme.colors[\"status-failed\"], 0.5)\n : tone === \"live\"\n ? withAlpha(theme.colors[\"status-running\"], 0.5)\n : theme.colors.border;\n return (\n <View\n style={{ borderLeftWidth: 2, borderLeftColor: borderColor, paddingLeft: 12, minWidth: 0 }}\n >\n {children}\n </View>\n );\n}\n\nexport function TermBlock({\n command,\n workdir,\n output,\n live,\n failed,\n tailLines = 12,\n}: {\n command: string | null;\n workdir?: string | null | undefined;\n output: string;\n live?: boolean | undefined;\n failed?: boolean | undefined;\n tailLines?: number;\n}) {\n const theme = useNativeTimelineTheme();\n const [full, setFull] = useState(false);\n const lines = output.split(\"\\n\");\n const big = lines.length > tailLines + 4;\n const shown = full || !big ? output : lines.slice(-tailLines).join(\"\\n\");\n const mono: TextStyle = {\n ...fontStyle(theme, 400, \"mono\"),\n fontSize: theme.size.xs,\n lineHeight: 20,\n };\n const showHeader = command != null || Boolean(workdir);\n return (\n <RuledBlock tone={failed ? \"failed\" : live ? \"live\" : \"neutral\"}>\n {showHeader ? (\n <View style={{ flexDirection: \"row\", alignItems: \"center\", gap: 8, paddingBottom: 4 }}>\n <Text style={[mono, { color: theme.colors[\"status-idle\"] }]}>$</Text>\n <Text\n style={[mono, { fontSize: theme.size.sm, color: theme.colors[\"fg-muted\"], flex: 1 }]}\n numberOfLines={1}\n >\n {command ?? \"\"}\n </Text>\n {workdir ? (\n <Text\n style={[mono, { color: theme.colors[\"fg-subtle\"], flexShrink: 1 }]}\n numberOfLines={1}\n >\n {workdir}\n </Text>\n ) : null}\n </View>\n ) : null}\n {output.trim() === \"\" ? (\n <Text style={[mono, { fontStyle: \"italic\", color: theme.colors[\"fg-subtle\"] }]}>\n (no output)\n </Text>\n ) : (\n <ScrollView style={{ maxHeight: 288 }} nestedScrollEnabled>\n <Text selectable style={[mono, { color: theme.colors[\"fg-muted\"] }]}>\n {shown}\n </Text>\n </ScrollView>\n )}\n {big && !full ? (\n <Pressable onPress={() => setFull(true)} accessibilityRole=\"button\">\n <Text\n style={{\n ...fontStyle(theme),\n marginTop: 4,\n fontSize: theme.size.xs,\n color: theme.colors[\"fg-subtle\"],\n }}\n >\n show full output ({lines.length} lines)\n </Text>\n </Pressable>\n ) : null}\n </RuledBlock>\n );\n}\n\nexport function PayloadBlock({\n label,\n value,\n failed,\n}: {\n label: string;\n value: unknown;\n failed?: boolean | undefined;\n}) {\n const theme = useNativeTimelineTheme();\n const text = typeof value === \"string\" ? value : stringifyPayload(value);\n if (!text || text.trim() === \"\") return null;\n return (\n <RuledBlock tone={failed ? \"failed\" : \"neutral\"}>\n <Text\n style={{\n ...fontStyle(theme, 500),\n marginBottom: 4,\n fontSize: theme.size.xs,\n letterSpacing: theme.size.xs * 0.08,\n textTransform: \"uppercase\",\n color: theme.colors[\"fg-subtle\"],\n }}\n >\n {label}\n </Text>\n <ScrollView style={{ maxHeight: 256 }} nestedScrollEnabled>\n <Text\n selectable\n style={{\n ...fontStyle(theme, 400, \"mono\"),\n fontSize: theme.size.xs,\n lineHeight: 20,\n color: failed ? theme.colors[\"status-failed\"] : theme.colors[\"fg-muted\"],\n }}\n >\n {text}\n </Text>\n </ScrollView>\n </RuledBlock>\n );\n}\n\nexport function BodyNote({ children, tone }: { children: ReactNode; tone?: \"error\" | undefined }) {\n const theme = useNativeTimelineTheme();\n if (tone === \"error\") {\n return (\n <RuledBlock tone=\"failed\">\n <Text\n style={{\n ...fontStyle(theme, 400, \"mono\"),\n fontSize: theme.size.xs,\n lineHeight: 20,\n color: theme.colors[\"status-failed\"],\n }}\n >\n {children}\n </Text>\n </RuledBlock>\n );\n }\n return (\n <Text\n style={{\n ...fontStyle(theme),\n paddingHorizontal: 2,\n fontSize: theme.size.sm,\n lineHeight: 20,\n fontStyle: \"italic\",\n color: theme.colors[\"fg-subtle\"],\n }}\n >\n {children}\n </Text>\n );\n}\n\n/** `rgb(r, g, b)` / `#rrggbb` → rgba with the given alpha (Tailwind `/50`). */\nfunction rgbOf(color: string): [number, number, number] | null {\n const rgb = color.match(/rgba?\\(\\s*(\\d+)[,\\s]+(\\d+)[,\\s]+(\\d+)/);\n if (rgb) return [Number(rgb[1]), Number(rgb[2]), Number(rgb[3])];\n const hex = color.match(/^#([0-9a-f]{2})([0-9a-f]{2})([0-9a-f]{2})/i);\n if (hex) return [parseInt(hex[1]!, 16), parseInt(hex[2]!, 16), parseInt(hex[3]!, 16)];\n return null;\n}\n\n/**\n * `color` at `alpha` composited over `base`, as an opaque color: a tinted\n * surface that stays solid when it floats over scrolling content.\n */\nexport function blendOver(base: string, color: string, alpha: number): string {\n const under = rgbOf(base);\n const over = rgbOf(color);\n if (!under || !over) return withAlpha(color, alpha);\n const mix = (index: number) => Math.round(under[index]! * (1 - alpha) + over[index]! * alpha);\n return `rgb(${mix(0)}, ${mix(1)}, ${mix(2)})`;\n}\n\nexport function withAlpha(color: string, alpha: number): string {\n const rgb = color.match(/rgba?\\(\\s*(\\d+)[,\\s]+(\\d+)[,\\s]+(\\d+)/);\n if (rgb) return `rgba(${rgb[1]}, ${rgb[2]}, ${rgb[3]}, ${alpha})`;\n const hex = color.match(/^#([0-9a-f]{2})([0-9a-f]{2})([0-9a-f]{2})/i);\n if (hex)\n return `rgba(${parseInt(hex[1]!, 16)}, ${parseInt(hex[2]!, 16)}, ${parseInt(hex[3]!, 16)}, ${alpha})`;\n return color;\n}\n"]}
@@ -0,0 +1,88 @@
1
+ // src/adapters.ts
2
+ function createHydratedPersistenceAdapter(storage, namespace) {
3
+ const prefix = `${namespace.replace(/:+$/, "")}:`;
4
+ const memory = /* @__PURE__ */ new Map();
5
+ let hydrated = false;
6
+ let hydration = null;
7
+ let active = true;
8
+ let mutations = Promise.resolve();
9
+ let invalidation = null;
10
+ const enqueueMutation = (operation) => {
11
+ mutations = mutations.then(operation, operation).catch(() => void 0);
12
+ };
13
+ const removePersistedNamespace = async () => {
14
+ const keys = (await storage.getAllKeys()).filter((key) => key.startsWith(prefix));
15
+ await Promise.all(keys.map((key) => storage.removeItem(key)));
16
+ };
17
+ return {
18
+ hydrate: async () => {
19
+ if (!active) return;
20
+ hydration ??= (async () => {
21
+ const keys = (await storage.getAllKeys()).filter((key) => key.startsWith(prefix));
22
+ const entries = keys.length > 0 ? await storage.multiGet(keys) : [];
23
+ if (!active) return;
24
+ memory.clear();
25
+ for (const [key, value] of entries) {
26
+ if (value !== null) memory.set(key.slice(prefix.length), value);
27
+ }
28
+ hydrated = true;
29
+ })();
30
+ await hydration;
31
+ },
32
+ getItem: (key) => {
33
+ if (!active || !hydrated) return null;
34
+ return memory.get(key) ?? null;
35
+ },
36
+ setItem: (key, value) => {
37
+ if (!active) return;
38
+ memory.set(key, value);
39
+ enqueueMutation(async () => {
40
+ if (!active) return;
41
+ await storage.setItem(`${prefix}${key}`, value);
42
+ });
43
+ },
44
+ removeItem: (key) => {
45
+ if (!active) return;
46
+ memory.delete(key);
47
+ enqueueMutation(async () => {
48
+ if (!active) return;
49
+ await storage.removeItem(`${prefix}${key}`);
50
+ });
51
+ },
52
+ clear: () => {
53
+ if (!active) return;
54
+ memory.clear();
55
+ enqueueMutation(async () => {
56
+ if (!active) return;
57
+ await removePersistedNamespace();
58
+ });
59
+ },
60
+ flush: async () => await mutations,
61
+ invalidate: () => {
62
+ if (invalidation) return invalidation;
63
+ active = false;
64
+ hydrated = false;
65
+ memory.clear();
66
+ invalidation = (async () => {
67
+ await hydration?.catch(() => void 0);
68
+ await mutations;
69
+ await removePersistedNamespace();
70
+ })();
71
+ return invalidation;
72
+ }
73
+ };
74
+ }
75
+ function sha256HexToArrayBuffer(hex) {
76
+ if (!/^[a-f\d]{64}$/i.test(hex)) {
77
+ throw new TypeError("SHA-256 adapter returned an invalid digest");
78
+ }
79
+ const bytes = new Uint8Array(32);
80
+ for (let index = 0; index < bytes.length; index += 1) {
81
+ bytes[index] = Number.parseInt(hex.slice(index * 2, index * 2 + 2), 16);
82
+ }
83
+ return bytes.buffer;
84
+ }
85
+
86
+ export { createHydratedPersistenceAdapter, sha256HexToArrayBuffer };
87
+ //# sourceMappingURL=chunk-5ZVK7WKA.js.map
88
+ //# sourceMappingURL=chunk-5ZVK7WKA.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../src/adapters.ts"],"names":[],"mappings":"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","file":"chunk-5ZVK7WKA.js","sourcesContent":["import type { FetchLike } from \"@opengeni/sdk\";\n\nexport type NativeLifecycleState = \"active\" | \"background\" | \"inactive\";\n\nexport interface NativeLifecycleAdapter {\n currentState(): NativeLifecycleState;\n subscribe(listener: (state: NativeLifecycleState) => void): () => void;\n}\n\nexport interface NativePersistenceAdapter {\n hydrate(): Promise<void>;\n getItem(key: string): string | null;\n setItem(key: string, value: string): void;\n removeItem(key: string): void;\n clear(): void;\n flush(): Promise<void>;\n invalidate(): Promise<void>;\n}\n\nexport interface AsyncKeyValueStorage {\n getAllKeys(): Promise<readonly string[]>;\n multiGet(keys: readonly string[]): Promise<readonly (readonly [string, string | null])[]>;\n setItem(key: string, value: string): Promise<void>;\n removeItem(key: string): Promise<void>;\n}\n\nexport interface NativeCryptoAdapter {\n randomUUID(): string;\n sha256Hex(bytes: Uint8Array): Promise<string>;\n}\n\nexport interface NativePickedFile {\n id: string;\n uri: string;\n name: string;\n contentType: string;\n sizeBytes: number | null;\n kind: \"document\" | \"image\";\n previewUri?: string;\n}\n\nexport interface NativeFileAdapter {\n pickDocuments(): Promise<NativePickedFile[]>;\n pickImages(): Promise<NativePickedFile[]>;\n readBytes(file: NativePickedFile): Promise<Uint8Array>;\n}\n\nexport interface OpenGeniReactNativeAdapters {\n lifecycle: NativeLifecycleAdapter;\n persistence: NativePersistenceAdapter;\n crypto: NativeCryptoAdapter;\n files: NativeFileAdapter;\n fetch: FetchLike;\n}\n\n/**\n * Build the synchronous storage facade required by the official composer from\n * an asynchronous native key/value store. Rendering waits for `hydrate`, so\n * reads never race the initial native load.\n */\nexport function createHydratedPersistenceAdapter(\n storage: AsyncKeyValueStorage,\n namespace: string,\n): NativePersistenceAdapter {\n const prefix = `${namespace.replace(/:+$/, \"\")}:`;\n const memory = new Map<string, string>();\n let hydrated = false;\n let hydration: Promise<void> | null = null;\n let active = true;\n let mutations = Promise.resolve();\n let invalidation: Promise<void> | null = null;\n\n const enqueueMutation = (operation: () => Promise<void>) => {\n mutations = mutations.then(operation, operation).catch(() => undefined);\n };\n\n const removePersistedNamespace = async () => {\n const keys = (await storage.getAllKeys()).filter((key) => key.startsWith(prefix));\n await Promise.all(keys.map((key) => storage.removeItem(key)));\n };\n\n return {\n hydrate: async () => {\n if (!active) return;\n hydration ??= (async () => {\n const keys = (await storage.getAllKeys()).filter((key) => key.startsWith(prefix));\n const entries = keys.length > 0 ? await storage.multiGet(keys) : [];\n if (!active) return;\n memory.clear();\n for (const [key, value] of entries) {\n if (value !== null) memory.set(key.slice(prefix.length), value);\n }\n hydrated = true;\n })();\n await hydration;\n },\n getItem: (key) => {\n if (!active || !hydrated) return null;\n return memory.get(key) ?? null;\n },\n setItem: (key, value) => {\n if (!active) return;\n memory.set(key, value);\n enqueueMutation(async () => {\n if (!active) return;\n await storage.setItem(`${prefix}${key}`, value);\n });\n },\n removeItem: (key) => {\n if (!active) return;\n memory.delete(key);\n enqueueMutation(async () => {\n if (!active) return;\n await storage.removeItem(`${prefix}${key}`);\n });\n },\n clear: () => {\n if (!active) return;\n memory.clear();\n enqueueMutation(async () => {\n if (!active) return;\n await removePersistedNamespace();\n });\n },\n flush: async () => await mutations,\n invalidate: () => {\n if (invalidation) return invalidation;\n active = false;\n hydrated = false;\n memory.clear();\n invalidation = (async () => {\n await hydration?.catch(() => undefined);\n await mutations;\n await removePersistedNamespace();\n })();\n return invalidation;\n },\n };\n}\n\nexport function sha256HexToArrayBuffer(hex: string): ArrayBuffer {\n if (!/^[a-f\\d]{64}$/i.test(hex)) {\n throw new TypeError(\"SHA-256 adapter returned an invalid digest\");\n }\n const bytes = new Uint8Array(32);\n for (let index = 0; index < bytes.length; index += 1) {\n bytes[index] = Number.parseInt(hex.slice(index * 2, index * 2 + 2), 16);\n }\n return bytes.buffer;\n}\n"]}