@opengeni/react 7.4.0-canary.36855269964001 → 7.4.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/README.md +3 -48
- package/dist/artifacts-document.js +2 -3
- package/dist/artifacts-presentation.js +2 -3
- package/dist/artifacts-spreadsheet.js +2 -2
- package/dist/artifacts.d.ts +0 -1
- package/dist/artifacts.js +1402 -505
- package/dist/artifacts.js.map +1 -1
- package/dist/{browser-viewer-R6KK5VKR.js → browser-viewer-2E6R2Y4W.js} +4 -4
- package/dist/{chunk-WUISZ3WU.js → chunk-3E2AITTZ.js} +28 -32
- package/dist/{chunk-WUISZ3WU.js.map → chunk-3E2AITTZ.js.map} +1 -1
- package/dist/{chunk-PWUILT2U.js → chunk-5AZSK6MV.js} +2 -2
- package/dist/{chunk-Y2PRMYLC.js → chunk-DUEBTL3N.js} +3 -4
- package/dist/{chunk-Y2PRMYLC.js.map → chunk-DUEBTL3N.js.map} +1 -1
- package/dist/{chunk-7UAMYXJY.js → chunk-KNDIXZN6.js} +18 -25
- package/dist/{chunk-7UAMYXJY.js.map → chunk-KNDIXZN6.js.map} +1 -1
- package/dist/{chunk-P4G6K2E2.js → chunk-L4OSXQ6H.js} +884 -1119
- package/dist/chunk-L4OSXQ6H.js.map +1 -0
- package/dist/{chunk-LLIH7Q4B.js → chunk-S5JQ4R22.js} +19 -47
- package/dist/chunk-S5JQ4R22.js.map +1 -0
- package/dist/{chunk-A4UJB2MM.js → chunk-SEEVCT36.js} +2 -2
- package/dist/{chunk-UXJCQ5GH.js → chunk-UDD6DLLT.js} +1 -6
- package/dist/chunk-UDD6DLLT.js.map +1 -0
- package/dist/chunk-UGMKPUEM.js +299 -0
- package/dist/chunk-UGMKPUEM.js.map +1 -0
- package/dist/{chunk-ZCZHKJKZ.js → chunk-USXVQACU.js} +3 -3
- package/dist/{chunk-VABBF52G.js → chunk-V2ABIVYJ.js} +6 -70
- package/dist/chunk-V2ABIVYJ.js.map +1 -0
- package/dist/{chunk-TVO6GXR6.js → chunk-X4HIN6TV.js} +162 -71
- package/dist/chunk-X4HIN6TV.js.map +1 -0
- package/dist/{chunk-IIDEIBMC.js → chunk-XEJEOAOV.js} +38 -49
- package/dist/chunk-XEJEOAOV.js.map +1 -0
- package/dist/{chunk-ZKLCPBWN.js → chunk-Y3QTZN2F.js} +5 -5
- package/dist/{chunk-73BUNGLF.js → chunk-YZ3YYMOM.js} +1 -1
- package/dist/components/artifacts/editable-artifact-ui.d.ts +1 -2
- package/dist/components/artifacts/index.d.ts +0 -7
- package/dist/components/browser-select-control.d.ts +1 -3
- package/dist/components/message-timeline.d.ts +1 -18
- package/dist/components/open-geni-links.d.ts +0 -16
- package/dist/components/session-conversation.d.ts +1 -20
- package/dist/composer.js +3 -3
- package/dist/{computer-viewer-DJHPSP2J.js → computer-viewer-WMJE6OA3.js} +3 -3
- package/dist/connect.js +6 -7
- package/dist/connect.js.map +1 -1
- package/dist/hooks/latest-question.d.ts +1 -1
- package/dist/index.d.ts +2 -5
- package/dist/index.js +28 -39
- package/dist/index.js.map +1 -1
- package/dist/interaction.js +4 -4
- package/dist/{latest-question-KGCDK3XX.js → latest-question-QB4EUCW5.js} +3 -3
- package/dist/lib/format.d.ts +0 -3
- package/dist/machines.js +2 -2
- package/dist/{markdown-table-layout-QXSLK4BY.js → markdown-table-layout-PFUEZ2U4.js} +5 -37
- package/dist/markdown-table-layout-PFUEZ2U4.js.map +1 -0
- package/dist/{sandbox-files-4PMXDSDV.js → sandbox-files-PXPIZAFG.js} +2 -2
- package/dist/session-ui.d.ts +2 -5
- package/dist/session-ui.js +13 -23
- package/dist/session-ui.js.map +1 -1
- package/dist/session.js +3 -3
- package/dist/sites.js +289 -4
- package/dist/sites.js.map +1 -1
- package/dist/timeline/types.d.ts +1 -7
- package/dist/{timeline-annotation-selection-DMLMM2TX.js → timeline-annotation-selection-ODLVF4OI.js} +1 -6
- package/dist/timeline-annotation-selection-ODLVF4OI.js.map +1 -0
- package/package.json +3 -7
- package/src/artifacts.ts +0 -37
- package/src/components/artifacts/editable-artifact-ui.tsx +1 -3
- package/src/components/artifacts/editable-artifact-workbench.tsx +2 -5
- package/src/components/artifacts/editable-document.tsx +36 -34
- package/src/components/artifacts/editable-presentation.tsx +16 -21
- package/src/components/artifacts/index.ts +0 -41
- package/src/components/browser-select-control.tsx +1 -4
- package/src/components/browser-viewer.tsx +22 -81
- package/src/components/computer-viewer.tsx +23 -51
- package/src/components/markdown-table-layout.ts +5 -49
- package/src/components/markdown.tsx +2 -5
- package/src/components/message-timeline.tsx +434 -515
- package/src/components/open-geni-links.tsx +0 -24
- package/src/components/session-conversation.tsx +20 -131
- package/src/components/timeline-annotation-selection.tsx +0 -7
- package/src/hooks/use-available-models.ts +1 -1
- package/src/index.ts +0 -9
- package/src/lib/format.ts +0 -13
- package/src/session-ui.ts +0 -9
- package/src/timeline/projection.ts +4 -78
- package/src/timeline/types.ts +0 -7
- package/styles/compiled.css +0 -325
- package/dist/chat-interactive-block-VAGABN7J.js +0 -11
- package/dist/chunk-5CVXZA3Y.js +0 -292
- package/dist/chunk-5CVXZA3Y.js.map +0 -1
- package/dist/chunk-B3V6TG77.js +0 -41
- package/dist/chunk-B3V6TG77.js.map +0 -1
- package/dist/chunk-IIDEIBMC.js.map +0 -1
- package/dist/chunk-LLIH7Q4B.js.map +0 -1
- package/dist/chunk-P4G6K2E2.js.map +0 -1
- package/dist/chunk-RAIQYITC.js +0 -1772
- package/dist/chunk-RAIQYITC.js.map +0 -1
- package/dist/chunk-SCOTPE2I.js +0 -589
- package/dist/chunk-SCOTPE2I.js.map +0 -1
- package/dist/chunk-TVO6GXR6.js.map +0 -1
- package/dist/chunk-UXJCQ5GH.js.map +0 -1
- package/dist/chunk-VABBF52G.js.map +0 -1
- package/dist/chunk-WEHMPOXK.js +0 -39
- package/dist/chunk-WEHMPOXK.js.map +0 -1
- package/dist/chunk-XCHWDJ22.js +0 -107
- package/dist/chunk-XCHWDJ22.js.map +0 -1
- package/dist/components/artifacts/artifact-chrome.d.ts +0 -120
- package/dist/components/artifacts/artifact-sandbox.d.ts +0 -27
- package/dist/components/artifacts/chat-interactive-block.d.ts +0 -29
- package/dist/components/artifacts/deferred-chat-media.d.ts +0 -15
- package/dist/components/artifacts/editable-artifact-view.d.ts +0 -46
- package/dist/components/artifacts/latest-task-runner.d.ts +0 -15
- package/dist/components/artifacts/session-artifact-viewer.d.ts +0 -39
- package/dist/components/artifacts/site-view.d.ts +0 -23
- package/dist/components/timeline-pill-geometry.d.ts +0 -6
- package/dist/components/timeline-pill-placement.d.ts +0 -18
- package/dist/components/usage-limit-notice.d.ts +0 -49
- package/dist/components/usage-member-list.d.ts +0 -91
- package/dist/components/usage-meter.d.ts +0 -73
- package/dist/hooks/use-usage.d.ts +0 -40
- package/dist/markdown-table-layout-QXSLK4BY.js.map +0 -1
- package/dist/sandbox-files-4PMXDSDV.js.map +0 -1
- package/dist/timeline/allowance-exhausted-row.d.ts +0 -24
- package/dist/timeline-annotation-selection-DMLMM2TX.js.map +0 -1
- package/dist/timeline-pill-geometry-2G6EK47V.js +0 -73
- package/dist/timeline-pill-geometry-2G6EK47V.js.map +0 -1
- package/dist/usage/allowance-copy.d.ts +0 -25
- package/dist/usage/summary.d.ts +0 -35
- package/dist/usage.d.ts +0 -13
- package/dist/usage.js +0 -1073
- package/dist/usage.js.map +0 -1
- package/src/components/artifacts/artifact-chrome.tsx +0 -413
- package/src/components/artifacts/artifact-sandbox.tsx +0 -185
- package/src/components/artifacts/chat-interactive-block.tsx +0 -260
- package/src/components/artifacts/deferred-chat-media.tsx +0 -67
- package/src/components/artifacts/editable-artifact-view.tsx +0 -187
- package/src/components/artifacts/latest-task-runner.ts +0 -49
- package/src/components/artifacts/session-artifact-viewer.tsx +0 -376
- package/src/components/artifacts/site-view.tsx +0 -116
- package/src/components/timeline-pill-geometry.ts +0 -112
- package/src/components/timeline-pill-placement.ts +0 -81
- package/src/components/usage-limit-notice.tsx +0 -179
- package/src/components/usage-member-list.tsx +0 -792
- package/src/components/usage-meter.tsx +0 -382
- package/src/hooks/use-usage.ts +0 -100
- package/src/timeline/allowance-exhausted-row.tsx +0 -86
- package/src/usage/allowance-copy.ts +0 -64
- package/src/usage/summary.ts +0 -93
- package/src/usage.ts +0 -50
- /package/dist/{browser-viewer-R6KK5VKR.js.map → browser-viewer-2E6R2Y4W.js.map} +0 -0
- /package/dist/{chunk-PWUILT2U.js.map → chunk-5AZSK6MV.js.map} +0 -0
- /package/dist/{chunk-A4UJB2MM.js.map → chunk-SEEVCT36.js.map} +0 -0
- /package/dist/{chunk-ZCZHKJKZ.js.map → chunk-USXVQACU.js.map} +0 -0
- /package/dist/{chunk-ZKLCPBWN.js.map → chunk-Y3QTZN2F.js.map} +0 -0
- /package/dist/{chunk-73BUNGLF.js.map → chunk-YZ3YYMOM.js.map} +0 -0
- /package/dist/{chat-interactive-block-VAGABN7J.js.map → computer-viewer-WMJE6OA3.js.map} +0 -0
- /package/dist/{latest-question-KGCDK3XX.js.map → latest-question-QB4EUCW5.js.map} +0 -0
- /package/dist/{computer-viewer-DJHPSP2J.js.map → sandbox-files-PXPIZAFG.js.map} +0 -0
|
@@ -153,27 +153,3 @@ export function sessionLinkResolver(input: {
|
|
|
153
153
|
return null;
|
|
154
154
|
};
|
|
155
155
|
}
|
|
156
|
-
|
|
157
|
-
/** An editable artifact or Site to open in a host-mounted viewer. */
|
|
158
|
-
export type OpenGeniViewerTarget = Readonly<{
|
|
159
|
-
kind: "editable-artifact" | "site";
|
|
160
|
-
artifactId: string;
|
|
161
|
-
/** The link text the agent wrote, until the viewer loads the real title. */
|
|
162
|
-
title?: string | undefined;
|
|
163
|
-
}>;
|
|
164
|
-
|
|
165
|
-
/**
|
|
166
|
-
* "Open in host viewer": resolve agent links to editable artifacts and Sites
|
|
167
|
-
* in this workspace to `open(target)`, for example to mount
|
|
168
|
-
* `SessionArtifactViewer` beside the conversation. Other targets fall through.
|
|
169
|
-
*/
|
|
170
|
-
export function viewerLinkResolver(input: {
|
|
171
|
-
workspaceId: string;
|
|
172
|
-
open: (target: OpenGeniViewerTarget) => void;
|
|
173
|
-
}): OpenGeniLinkResolver {
|
|
174
|
-
return (target) => {
|
|
175
|
-
if (target.kind !== "editable-artifact" && target.kind !== "site") return null;
|
|
176
|
-
if (target.workspaceId !== input.workspaceId) return null;
|
|
177
|
-
return { open: () => input.open({ kind: target.kind, artifactId: target.artifactId }) };
|
|
178
|
-
};
|
|
179
|
-
}
|
|
@@ -1,15 +1,5 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
lazy,
|
|
4
|
-
Suspense,
|
|
5
|
-
useCallback,
|
|
6
|
-
useEffect,
|
|
7
|
-
useMemo,
|
|
8
|
-
useRef,
|
|
9
|
-
useState,
|
|
10
|
-
type CSSProperties,
|
|
11
|
-
} from "react";
|
|
12
|
-
import type { SiteSnapshotClient } from "./artifacts/chat-interactive-block";
|
|
1
|
+
import type { SendMessageInput } from "@opengeni/sdk";
|
|
2
|
+
import { useEffect, useMemo, useRef, useState, type CSSProperties } from "react";
|
|
13
3
|
import { useOpenGeni, type ClientOverride } from "../session-context";
|
|
14
4
|
import { useWorkspaceModelCatalog } from "../hooks/use-available-models";
|
|
15
5
|
import { ModelPolicyPicker } from "./model-policy-picker";
|
|
@@ -30,9 +20,7 @@ import {
|
|
|
30
20
|
chainLinkResolvers,
|
|
31
21
|
sessionLinkResolver,
|
|
32
22
|
useOpenGeniLinkResolver,
|
|
33
|
-
viewerLinkResolver,
|
|
34
23
|
type OpenGeniLinkResolver,
|
|
35
|
-
type OpenGeniViewerTarget,
|
|
36
24
|
} from "./open-geni-links";
|
|
37
25
|
import type { UserMessageDisclosureLabels } from "./user-message-body";
|
|
38
26
|
import { conversationTimeline } from "../conversation-timeline";
|
|
@@ -49,27 +37,8 @@ export type SessionConversationProps = ClientOverride & {
|
|
|
49
37
|
* editable artifacts and Sites stay unavailable until the host resolves them.
|
|
50
38
|
*/
|
|
51
39
|
resolveLink?: OpenGeniLinkResolver | undefined;
|
|
52
|
-
/**
|
|
53
|
-
* Open agent links to editable artifacts and Sites in a host viewer, for
|
|
54
|
-
* example `SessionArtifactViewer` mounted beside the conversation. Asked
|
|
55
|
-
* after `resolveLink`.
|
|
56
|
-
*/
|
|
57
|
-
onOpenArtifact?: ((target: OpenGeniViewerTarget) => void) | undefined;
|
|
58
|
-
/**
|
|
59
|
-
* Inline previews for assistant `opengeni-site` / `opengeni-html` fences.
|
|
60
|
-
* Defaults to the OpenGeni preview (Site reads need the proxy's
|
|
61
|
-
* `artifacts` option); `false` shows the fence as code.
|
|
62
|
-
*/
|
|
63
|
-
renderInteractiveBlock?: MessageTimelineProps["renderInteractiveBlock"] | false;
|
|
64
40
|
/** Product-specific tool-call renderers; defaults to the built-in registry. */
|
|
65
41
|
toolRegistry?: MessageTimelineProps["toolRegistry"];
|
|
66
|
-
/**
|
|
67
|
-
* Replace the "usage limit reached" row for an `allowance_exhausted`
|
|
68
|
-
* refusal, for example to link your own plan or admin page.
|
|
69
|
-
*/
|
|
70
|
-
renderAllowanceExhausted?: MessageTimelineProps["renderAllowanceExhausted"];
|
|
71
|
-
/** Replace the words of the default "usage limit reached" row. */
|
|
72
|
-
allowanceExhaustedLabels?: MessageTimelineProps["allowanceExhaustedLabels"];
|
|
73
42
|
/**
|
|
74
43
|
* File attachments in the composer. Defaults to true; the attach control
|
|
75
44
|
* appears only when the deployment's client config enables file uploads.
|
|
@@ -103,11 +72,7 @@ function Conversation({
|
|
|
103
72
|
sessionId,
|
|
104
73
|
renderMessageText,
|
|
105
74
|
resolveLink,
|
|
106
|
-
onOpenArtifact,
|
|
107
|
-
renderInteractiveBlock,
|
|
108
75
|
toolRegistry,
|
|
109
|
-
renderAllowanceExhausted,
|
|
110
|
-
allowanceExhaustedLabels,
|
|
111
76
|
attachments: attachmentsRequested = true,
|
|
112
77
|
modelPicker,
|
|
113
78
|
userMessageDisclosureLabels,
|
|
@@ -164,11 +129,6 @@ function Conversation({
|
|
|
164
129
|
: {}),
|
|
165
130
|
});
|
|
166
131
|
const region = useRef<HTMLDivElement>(null);
|
|
167
|
-
const defaultInteractiveBlock = useDefaultInteractiveBlock(
|
|
168
|
-
context.client,
|
|
169
|
-
context.workspaceId,
|
|
170
|
-
sessionId,
|
|
171
|
-
);
|
|
172
132
|
const inheritedLinks = useOpenGeniLinkResolver();
|
|
173
133
|
const defaultLinks = useMemo(
|
|
174
134
|
() =>
|
|
@@ -180,22 +140,9 @@ function Conversation({
|
|
|
180
140
|
}),
|
|
181
141
|
[context.client, context.workspaceId, sessionId, config.sandboxFiles],
|
|
182
142
|
);
|
|
183
|
-
const onOpenArtifactRef = useRef(onOpenArtifact);
|
|
184
|
-
onOpenArtifactRef.current = onOpenArtifact;
|
|
185
|
-
const opensArtifacts = onOpenArtifact !== undefined;
|
|
186
|
-
const viewerLinks = useMemo(
|
|
187
|
-
() =>
|
|
188
|
-
opensArtifacts
|
|
189
|
-
? viewerLinkResolver({
|
|
190
|
-
workspaceId: context.workspaceId,
|
|
191
|
-
open: (target) => onOpenArtifactRef.current?.(target),
|
|
192
|
-
})
|
|
193
|
-
: null,
|
|
194
|
-
[context.workspaceId, opensArtifacts],
|
|
195
|
-
);
|
|
196
143
|
const links = useMemo(
|
|
197
|
-
() => chainLinkResolvers(resolveLink,
|
|
198
|
-
[resolveLink,
|
|
144
|
+
() => chainLinkResolvers(resolveLink, inheritedLinks, defaultLinks) ?? undefined,
|
|
145
|
+
[resolveLink, inheritedLinks, defaultLinks],
|
|
199
146
|
);
|
|
200
147
|
const error = detail.error ?? feed.error ?? human.error;
|
|
201
148
|
return (
|
|
@@ -212,14 +159,7 @@ function Conversation({
|
|
|
212
159
|
<MessageTimeline
|
|
213
160
|
renderMessageText={renderMessageText}
|
|
214
161
|
resolveLink={links}
|
|
215
|
-
renderInteractiveBlock={
|
|
216
|
-
renderInteractiveBlock === false
|
|
217
|
-
? undefined
|
|
218
|
-
: (renderInteractiveBlock ?? defaultInteractiveBlock)
|
|
219
|
-
}
|
|
220
162
|
userMessageDisclosureLabels={userMessageDisclosureLabels}
|
|
221
|
-
renderAllowanceExhausted={renderAllowanceExhausted}
|
|
222
|
-
allowanceExhaustedLabels={allowanceExhaustedLabels}
|
|
223
163
|
className="min-h-0 flex-1"
|
|
224
164
|
{...(toolRegistry ? { toolRegistry } : {})}
|
|
225
165
|
events={feed.events}
|
|
@@ -237,25 +177,22 @@ function Conversation({
|
|
|
237
177
|
}}
|
|
238
178
|
loadingOldest={feed.loadingOldest}
|
|
239
179
|
onJumpToLatest={feed.jumpToLatest}
|
|
240
|
-
onJumpToLatestQuestion={
|
|
241
|
-
feed.
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
},
|
|
257
|
-
})
|
|
258
|
-
: undefined
|
|
180
|
+
onJumpToLatestQuestion={() =>
|
|
181
|
+
feed.jumpToLatestQuestion({
|
|
182
|
+
onQueuedQuestion: async (turn, navigation) => {
|
|
183
|
+
await queue.refresh();
|
|
184
|
+
if (
|
|
185
|
+
!navigation.isCurrent() ||
|
|
186
|
+
scopeRef.current.client !== context.client ||
|
|
187
|
+
scopeRef.current.workspaceId !== context.workspaceId
|
|
188
|
+
)
|
|
189
|
+
return;
|
|
190
|
+
setQueueFocusTarget((previous) => ({
|
|
191
|
+
turnId: turn.id,
|
|
192
|
+
requestId: (previous?.requestId ?? 0) + 1,
|
|
193
|
+
}));
|
|
194
|
+
},
|
|
195
|
+
})
|
|
259
196
|
}
|
|
260
197
|
onAnnotate={composer.addAnnotation}
|
|
261
198
|
/>
|
|
@@ -338,54 +275,6 @@ function Conversation({
|
|
|
338
275
|
);
|
|
339
276
|
}
|
|
340
277
|
|
|
341
|
-
const LazyChatInteractiveBlock = lazy(() =>
|
|
342
|
-
import("./artifacts/chat-interactive-block").then((module) => ({
|
|
343
|
-
default: module.ChatInteractiveBlock,
|
|
344
|
-
})),
|
|
345
|
-
);
|
|
346
|
-
|
|
347
|
-
type ScopableClient = SiteSnapshotClient & {
|
|
348
|
-
withHeaders?: (headers: Readonly<Record<string, string>>) => SiteSnapshotClient;
|
|
349
|
-
};
|
|
350
|
-
|
|
351
|
-
/** Inline Site/HTML preview reading through this conversation's session scope. */
|
|
352
|
-
function useDefaultInteractiveBlock(
|
|
353
|
-
client: unknown,
|
|
354
|
-
workspaceId: string,
|
|
355
|
-
sessionId: string,
|
|
356
|
-
): NonNullable<MessageTimelineProps["renderInteractiveBlock"]> {
|
|
357
|
-
// Scope lazily: only a rendered preview reads, and some clients (a Site's
|
|
358
|
-
// own client) cannot add headers.
|
|
359
|
-
const scoped = useMemo((): SiteSnapshotClient => {
|
|
360
|
-
let resolved: SiteSnapshotClient | null = null;
|
|
361
|
-
const get = () => {
|
|
362
|
-
const candidate = client as ScopableClient;
|
|
363
|
-
resolved ??=
|
|
364
|
-
typeof candidate.withHeaders === "function"
|
|
365
|
-
? candidate.withHeaders({ [SESSION_SCOPE_HEADER]: sessionId })
|
|
366
|
-
: candidate;
|
|
367
|
-
return resolved;
|
|
368
|
-
};
|
|
369
|
-
return {
|
|
370
|
-
getWorkspaceArtifact: (...args) => get().getWorkspaceArtifact(...args),
|
|
371
|
-
getWorkspaceArtifactHtml: (...args) => get().getWorkspaceArtifactHtml(...args),
|
|
372
|
-
getWorkspaceArtifactContent: (...args) => {
|
|
373
|
-
const target = get();
|
|
374
|
-
if (!target.getWorkspaceArtifactContent) throw new Error("Site version unavailable");
|
|
375
|
-
return target.getWorkspaceArtifactContent(...args);
|
|
376
|
-
},
|
|
377
|
-
};
|
|
378
|
-
}, [client, sessionId]);
|
|
379
|
-
return useCallback(
|
|
380
|
-
(block) => (
|
|
381
|
-
<Suspense fallback={<span role="status">Loading preview…</span>}>
|
|
382
|
-
<LazyChatInteractiveBlock workspaceId={workspaceId} client={scoped} {...block} />
|
|
383
|
-
</Suspense>
|
|
384
|
-
),
|
|
385
|
-
[scoped, workspaceId],
|
|
386
|
-
);
|
|
387
|
-
}
|
|
388
|
-
|
|
389
278
|
/** Deployment/proxy flags from the client config: uploads, and whether model choice is open. */
|
|
390
279
|
function useClientConfigFlags(client: {
|
|
391
280
|
getClientConfig: () => Promise<{
|
|
@@ -163,7 +163,6 @@ export function TimelineAnnotationSelection({
|
|
|
163
163
|
}) {
|
|
164
164
|
const [candidate, setCandidate] = useState<SelectionCandidate | null>(null);
|
|
165
165
|
const buttonRef = useRef<HTMLButtonElement | null>(null);
|
|
166
|
-
const initialSelectionObservedRef = useRef(false);
|
|
167
166
|
const pointerOriginRef = useRef<"unset" | "inside" | "outside">("unset");
|
|
168
167
|
const portalStyle = usePortalTokenStyle(rootRef.current);
|
|
169
168
|
|
|
@@ -176,12 +175,6 @@ export function TimelineAnnotationSelection({
|
|
|
176
175
|
const update = (keyboard: boolean) => {
|
|
177
176
|
setCandidate(buildCandidate(root, sources, keyboard));
|
|
178
177
|
};
|
|
179
|
-
// A user may finish selecting text before this lazy component arrives.
|
|
180
|
-
// Reconcile once; later prop changes must not revive dismissed selections.
|
|
181
|
-
if (!initialSelectionObservedRef.current) {
|
|
182
|
-
initialSelectionObservedRef.current = true;
|
|
183
|
-
update(false);
|
|
184
|
-
}
|
|
185
178
|
const onRootPointerUp = (event: PointerEvent) => {
|
|
186
179
|
if (event.target instanceof Node && buttonRef.current?.contains(event.target)) return;
|
|
187
180
|
// Tests may fire only pointerup on the source. A real click that started
|
|
@@ -72,7 +72,7 @@ export function useWorkspaceModelCatalog(
|
|
|
72
72
|
}
|
|
73
73
|
const [catalog, config] = await Promise.all([
|
|
74
74
|
client.getWorkspaceModelCatalog(options.workspaceId, { signal }),
|
|
75
|
-
client.getClientConfig({ signal
|
|
75
|
+
client.getClientConfig({ signal }),
|
|
76
76
|
]);
|
|
77
77
|
return {
|
|
78
78
|
models: catalog.models,
|
package/src/index.ts
CHANGED
|
@@ -536,8 +536,6 @@ export { MessageTimeline, TimelineRow } from "./components/message-timeline";
|
|
|
536
536
|
export { GeneratedVideoPlayer } from "./components/generated-video-player";
|
|
537
537
|
export type { GeneratedVideoPlayerProps } from "./components/generated-video-player";
|
|
538
538
|
export type { MessageTimelineProps } from "./components/message-timeline";
|
|
539
|
-
export type { RenderAllowanceExhausted } from "./timeline/allowance-exhausted-row";
|
|
540
|
-
export type { AllowanceLabels, AllowanceScope } from "./usage/allowance-copy";
|
|
541
539
|
export type { TimelineSearchTarget } from "./components/timeline-search";
|
|
542
540
|
export { UserMessageBody, userMessageLikelyNeedsDisclosure } from "./components/user-message-body";
|
|
543
541
|
export type {
|
|
@@ -559,20 +557,13 @@ export {
|
|
|
559
557
|
chainLinkResolvers,
|
|
560
558
|
sessionLinkResolver,
|
|
561
559
|
useOpenGeniLinkResolver,
|
|
562
|
-
viewerLinkResolver,
|
|
563
560
|
} from "./components/open-geni-links";
|
|
564
561
|
export type {
|
|
565
562
|
OpenGeniLinkResolution,
|
|
566
563
|
OpenGeniLinkResolver,
|
|
567
564
|
OpenGeniLinkTarget,
|
|
568
|
-
OpenGeniViewerTarget,
|
|
569
565
|
} from "./components/open-geni-links";
|
|
570
566
|
export { parseOpenGeniLink } from "@opengeni/sdk";
|
|
571
|
-
export {
|
|
572
|
-
ArtifactLabelsProvider,
|
|
573
|
-
DEFAULT_ARTIFACT_LABELS,
|
|
574
|
-
type ArtifactLabels,
|
|
575
|
-
} from "./components/artifacts/artifact-chrome";
|
|
576
567
|
export { CopyButton, CopyHoverFrame } from "./components/copy-button";
|
|
577
568
|
export { copyTextToClipboard, tableElementToTsv } from "./lib/clipboard";
|
|
578
569
|
export { SessionStatus, StatusDot, SESSION_STATUS_META } from "./components/session-status";
|
package/src/lib/format.ts
CHANGED
|
@@ -111,12 +111,6 @@ export function tryParseJson(text: string): unknown {
|
|
|
111
111
|
export const CREDIT_EXHAUSTION_MESSAGE =
|
|
112
112
|
"Out of Opengeni credits — this workspace's balance is empty. Add credits to continue; the conversation is preserved.";
|
|
113
113
|
|
|
114
|
-
/** A usage ceiling refused the send; the default allowance wording, plus what is safe. */
|
|
115
|
-
export const COMPOSER_MEMBER_ALLOWANCE_MESSAGE =
|
|
116
|
-
"Usage limit reached. A workspace admin can raise this limit. Your draft is preserved.";
|
|
117
|
-
export const COMPOSER_WORKSPACE_ALLOWANCE_MESSAGE =
|
|
118
|
-
"Workspace usage limit reached. An organization admin can raise the workspace budget. Your draft is preserved.";
|
|
119
|
-
|
|
120
114
|
/**
|
|
121
115
|
* Actionable composer copy for an edge rejection before a turn is accepted.
|
|
122
116
|
* Unlike an in-flight credit exhaustion, this path has not consumed the
|
|
@@ -126,13 +120,6 @@ export const COMPOSER_PAYMENT_REQUIRED_MESSAGE =
|
|
|
126
120
|
"This turn requires Opengeni managed credits, but the account balance is empty. Add credits or choose a connected Codex subscription model, then retry. Your draft and attachments are preserved.";
|
|
127
121
|
|
|
128
122
|
export function composerSubmissionErrorMessage(error: Error): string {
|
|
129
|
-
if (error instanceof OpenGeniApiError && error.code === "allowance_exhausted") {
|
|
130
|
-
// OpenGeniAllowanceExhaustedError carries the scope; read it structurally
|
|
131
|
-
// so this startup-path helper adds no SDK or wording imports.
|
|
132
|
-
return (error as { scope?: unknown }).scope === "workspace"
|
|
133
|
-
? COMPOSER_WORKSPACE_ALLOWANCE_MESSAGE
|
|
134
|
-
: COMPOSER_MEMBER_ALLOWANCE_MESSAGE;
|
|
135
|
-
}
|
|
136
123
|
return error instanceof OpenGeniApiError &&
|
|
137
124
|
error.status === 402 &&
|
|
138
125
|
error.code === "payment_required"
|
package/src/session-ui.ts
CHANGED
|
@@ -13,27 +13,18 @@ export type { ApprovalSurfaceProps, ApprovalSurfaceMessages } from "./components
|
|
|
13
13
|
export type { HumanInputSurfaceProps } from "./components/human-input-surface";
|
|
14
14
|
export { MessageTimeline, TimelineRow } from "./components/message-timeline";
|
|
15
15
|
export type { MessageTimelineProps } from "./components/message-timeline";
|
|
16
|
-
export type { RenderAllowanceExhausted } from "./timeline/allowance-exhausted-row";
|
|
17
|
-
export type { AllowanceLabels, AllowanceScope } from "./usage/allowance-copy";
|
|
18
16
|
export {
|
|
19
17
|
OpenGeniLinkProvider,
|
|
20
18
|
chainLinkResolvers,
|
|
21
19
|
sessionLinkResolver,
|
|
22
20
|
useOpenGeniLinkResolver,
|
|
23
|
-
viewerLinkResolver,
|
|
24
21
|
} from "./components/open-geni-links";
|
|
25
22
|
export type {
|
|
26
23
|
OpenGeniLinkResolution,
|
|
27
24
|
OpenGeniLinkResolver,
|
|
28
25
|
OpenGeniLinkTarget,
|
|
29
|
-
OpenGeniViewerTarget,
|
|
30
26
|
} from "./components/open-geni-links";
|
|
31
27
|
export { parseOpenGeniLink } from "@opengeni/sdk";
|
|
32
|
-
export {
|
|
33
|
-
ArtifactLabelsProvider,
|
|
34
|
-
DEFAULT_ARTIFACT_LABELS,
|
|
35
|
-
type ArtifactLabels,
|
|
36
|
-
} from "./components/artifacts/artifact-chrome";
|
|
37
28
|
export type { TimelineSearchTarget } from "./components/timeline-search";
|
|
38
29
|
export { createOlderHistoryLoadReceipt } from "./older-history";
|
|
39
30
|
export type { OlderHistoryLoader, OlderHistoryLoadReceipt } from "./older-history";
|
|
@@ -1,8 +1,6 @@
|
|
|
1
1
|
import {
|
|
2
2
|
parseMediaGenerationResult,
|
|
3
3
|
parseToolDisplayMetadata,
|
|
4
|
-
EMPTY_FINAL_REPLY_NOTICE,
|
|
5
|
-
turnCompletedWithEmptyFinalReply,
|
|
6
4
|
type HumanInputAnswer,
|
|
7
5
|
type HumanInputQuestion,
|
|
8
6
|
type HumanInputResponse,
|
|
@@ -11,10 +9,6 @@ import {
|
|
|
11
9
|
type TimelineAnnotation,
|
|
12
10
|
} from "@opengeni/sdk";
|
|
13
11
|
import fleetDecisionItem from "./fleet-decision-projection";
|
|
14
|
-
import {
|
|
15
|
-
allowanceExhaustedMessage,
|
|
16
|
-
parseAllowanceExhaustedRefusal,
|
|
17
|
-
} from "@opengeni/sdk/allowance-refusal";
|
|
18
12
|
import {
|
|
19
13
|
CREDIT_EXHAUSTION_MESSAGE,
|
|
20
14
|
presentFailure,
|
|
@@ -151,34 +145,6 @@ export function buildTimeline(
|
|
|
151
145
|
options: { partialStart?: boolean } = {},
|
|
152
146
|
): TimelineItem[] {
|
|
153
147
|
const items: TimelineItem[] = [];
|
|
154
|
-
const allowanceNotices = new Set<string>();
|
|
155
|
-
const allowanceNotice = (event: SessionEvent, turnId: string | null) => {
|
|
156
|
-
const refusal = parseAllowanceExhaustedRefusal(event.payload);
|
|
157
|
-
if (!refusal) return null;
|
|
158
|
-
const text = allowanceExhaustedMessage(refusal);
|
|
159
|
-
const key = JSON.stringify([
|
|
160
|
-
turnId,
|
|
161
|
-
event.turnAttemptId,
|
|
162
|
-
startupRecoveryRevisionByTurn.get(turnId ?? "") ?? 0,
|
|
163
|
-
refusal.scope,
|
|
164
|
-
refusal.subjectId,
|
|
165
|
-
refusal.resetsAt,
|
|
166
|
-
]);
|
|
167
|
-
if (!allowanceNotices.has(key)) {
|
|
168
|
-
allowanceNotices.add(key);
|
|
169
|
-
items.push({
|
|
170
|
-
kind: "notice",
|
|
171
|
-
id: `${event.id}-allowance`,
|
|
172
|
-
tone: "failed",
|
|
173
|
-
text,
|
|
174
|
-
// The canonical sentence replaces upstream prose, so a host renderer
|
|
175
|
-
// reading `message` never shows a wrapper's private wording.
|
|
176
|
-
allowance: { ...refusal, message: text },
|
|
177
|
-
occurredAt: event.occurredAt,
|
|
178
|
-
});
|
|
179
|
-
}
|
|
180
|
-
return text;
|
|
181
|
-
};
|
|
182
148
|
const prescan = prescanTurnAnchors(events);
|
|
183
149
|
const ordered = orderTimelineEvents(events, prescan);
|
|
184
150
|
// A bounded replay can begin halfway through a message (including inside an
|
|
@@ -1234,11 +1200,6 @@ export function buildTimeline(
|
|
|
1234
1200
|
break;
|
|
1235
1201
|
}
|
|
1236
1202
|
|
|
1237
|
-
case "usage.exhausted": {
|
|
1238
|
-
allowanceNotice(event, turnId);
|
|
1239
|
-
break;
|
|
1240
|
-
}
|
|
1241
|
-
|
|
1242
1203
|
case "turn.completed": {
|
|
1243
1204
|
// A standalone manual compaction uses the turn ledger for fencing and
|
|
1244
1205
|
// recovery, but it is maintenance rather than a conversational turn.
|
|
@@ -1257,15 +1218,6 @@ export function buildTimeline(
|
|
|
1257
1218
|
// Rendering it as a clean "complete" turn is a lie that leaves the
|
|
1258
1219
|
// session looking healthy while every future turn silently dies, so it
|
|
1259
1220
|
// projects exactly like a failed turn plus an explicit notice.
|
|
1260
|
-
const allowance = parseAllowanceExhaustedRefusal(payload);
|
|
1261
|
-
if (allowance) {
|
|
1262
|
-
finalizeOpen(turnId, "complete", event.occurredAt);
|
|
1263
|
-
takeAgentResponse(turnId);
|
|
1264
|
-
takePendingWaitOutcome(turnId);
|
|
1265
|
-
items.push(turnEndItem(event, "failed", ALLOWANCE_TURN_END_TEXT));
|
|
1266
|
-
allowanceNotice(event, turnId);
|
|
1267
|
-
break;
|
|
1268
|
-
}
|
|
1269
1221
|
if (isCreditExhaustionPayload(payload)) {
|
|
1270
1222
|
finalizeOpen(turnId, "complete", event.occurredAt);
|
|
1271
1223
|
takeAgentResponse(turnId);
|
|
@@ -1331,16 +1283,6 @@ export function buildTimeline(
|
|
|
1331
1283
|
finalizeOpen(turnId, "complete", event.occurredAt);
|
|
1332
1284
|
const completedTurn = turnEndItem(event, "complete", null);
|
|
1333
1285
|
items.push(completedTurn);
|
|
1334
|
-
if (turnCompletedWithEmptyFinalReply(payload)) {
|
|
1335
|
-
items.push({
|
|
1336
|
-
kind: "notice",
|
|
1337
|
-
id: `${event.id}-empty-final-reply`,
|
|
1338
|
-
tone: "input",
|
|
1339
|
-
text: EMPTY_FINAL_REPLY_NOTICE,
|
|
1340
|
-
recordedOutcome: true,
|
|
1341
|
-
occurredAt: event.occurredAt,
|
|
1342
|
-
});
|
|
1343
|
-
}
|
|
1344
1286
|
const hasCompletedFinalResponse =
|
|
1345
1287
|
latestAgentResponse?.completed === true &&
|
|
1346
1288
|
latestAgentResponse.item.phase !== "commentary" &&
|
|
@@ -1375,21 +1317,16 @@ export function buildTimeline(
|
|
|
1375
1317
|
// Credit death can hide behind fields `failureMessage` doesn't read
|
|
1376
1318
|
// (detail/segmentLimit), so classify the whole payload before falling
|
|
1377
1319
|
// back to the generic error/message extraction.
|
|
1378
|
-
const
|
|
1379
|
-
|
|
1380
|
-
|
|
1381
|
-
: isCreditExhaustionPayload(payload)
|
|
1382
|
-
? CREDIT_EXHAUSTION_MESSAGE
|
|
1383
|
-
: failureMessage(payload);
|
|
1320
|
+
const failureText = isCreditExhaustionPayload(payload)
|
|
1321
|
+
? CREDIT_EXHAUSTION_MESSAGE
|
|
1322
|
+
: failureMessage(payload);
|
|
1384
1323
|
// The TURN failed — the in-flight items did not. Chip doctrine: red is
|
|
1385
1324
|
// spent once, on the turn-level outcome. Items caught mid-flight read
|
|
1386
1325
|
// as calm "interrupted" (same as turn.cancelled); an item that itself
|
|
1387
1326
|
// failed keeps its own failed status from its output event.
|
|
1388
1327
|
finalizeOpen(turnId, "cancelled", event.occurredAt);
|
|
1389
1328
|
items.push(turnEndItem(event, "failed", failureText));
|
|
1390
|
-
if (
|
|
1391
|
-
allowanceNotice(event, turnId);
|
|
1392
|
-
} else if (!hadActivity) {
|
|
1329
|
+
if (!hadActivity) {
|
|
1393
1330
|
items.push({
|
|
1394
1331
|
kind: "notice",
|
|
1395
1332
|
id: event.id,
|
|
@@ -1751,16 +1688,8 @@ export function stripOpaqueCitationTokens(text: string): string {
|
|
|
1751
1688
|
return text.replace(/\s*cite(?:[^]+)+/gu, "");
|
|
1752
1689
|
}
|
|
1753
1690
|
|
|
1754
|
-
/**
|
|
1755
|
-
* The turn summary's short outcome for a usage ceiling. The adjacent notice row
|
|
1756
|
-
* carries who can raise it and when it resets (and is host-customizable), so
|
|
1757
|
-
* the summary line stays a neutral fact instead of repeating remedy prose.
|
|
1758
|
-
*/
|
|
1759
|
-
const ALLOWANCE_TURN_END_TEXT = "Usage limit reached";
|
|
1760
|
-
|
|
1761
1691
|
/** The turn-end payload shape, as `isCreditExhaustion` wants it. */
|
|
1762
1692
|
function isCreditExhaustionPayload(payload: Record<string, unknown>): boolean {
|
|
1763
|
-
if (payload.code === "allowance_exhausted") return false;
|
|
1764
1693
|
return isCreditExhaustion({
|
|
1765
1694
|
error: typeof payload.error === "string" ? payload.error : null,
|
|
1766
1695
|
detail: typeof payload.detail === "string" ? payload.detail : null,
|
|
@@ -2419,9 +2348,6 @@ export function isTurnExecutionEvidence(type: string): boolean {
|
|
|
2419
2348
|
isAgentActivityEvent(type) ||
|
|
2420
2349
|
type === "turn.completed" ||
|
|
2421
2350
|
type === "turn.failed" ||
|
|
2422
|
-
// An admission refusal can settle a queued turn before it ever starts:
|
|
2423
|
-
// its prompt still belongs above the "usage limit reached" row.
|
|
2424
|
-
type === "usage.exhausted" ||
|
|
2425
2351
|
type === "turn.superseded" ||
|
|
2426
2352
|
type === "turn.recovery.requested" ||
|
|
2427
2353
|
type === "turn.capacity_waiting" ||
|
package/src/timeline/types.ts
CHANGED
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
import type {
|
|
2
|
-
AllowanceExhaustedRefusal,
|
|
3
2
|
HumanInputQuestion,
|
|
4
3
|
HumanInputResponse,
|
|
5
4
|
MediaGenerationResult,
|
|
@@ -392,12 +391,6 @@ export type NoticeItem = {
|
|
|
392
391
|
/** Optional evidence kept inspectable without overwhelming the main rail. */
|
|
393
392
|
details?: { label: string; value: unknown };
|
|
394
393
|
action?: { label: string; url: string };
|
|
395
|
-
/**
|
|
396
|
-
* A usage ceiling refused further work. `text` keeps the canonical sentence
|
|
397
|
-
* for plain-text consumers; `MessageTimeline` renders this structured row
|
|
398
|
-
* (customizable with `renderAllowanceExhausted` / `allowanceExhaustedLabels`).
|
|
399
|
-
*/
|
|
400
|
-
allowance?: AllowanceExhaustedRefusal;
|
|
401
394
|
occurredAt: string;
|
|
402
395
|
};
|
|
403
396
|
|