@stigmer/react 3.1.13 → 3.1.15
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/agent/AgentDetailView.d.ts +9 -9
- package/agent/AgentDetailView.d.ts.map +1 -1
- package/agent/AgentDetailView.js +23 -31
- package/agent/AgentDetailView.js.map +1 -1
- package/agent-instance/AgentInstanceEmptyState.d.ts +4 -1
- package/agent-instance/AgentInstanceEmptyState.d.ts.map +1 -1
- package/agent-instance/AgentInstanceEmptyState.js +12 -5
- package/agent-instance/AgentInstanceEmptyState.js.map +1 -1
- package/agent-instance/AgentInstanceList.d.ts +13 -2
- package/agent-instance/AgentInstanceList.d.ts.map +1 -1
- package/agent-instance/AgentInstanceList.js +8 -4
- package/agent-instance/AgentInstanceList.js.map +1 -1
- package/agent-instance/useAgentInstances.d.ts +10 -3
- package/agent-instance/useAgentInstances.d.ts.map +1 -1
- package/agent-instance/useAgentInstances.js +12 -4
- package/agent-instance/useAgentInstances.js.map +1 -1
- package/button/Button.d.ts +54 -0
- package/button/Button.d.ts.map +1 -0
- package/button/Button.js +42 -0
- package/button/Button.js.map +1 -0
- package/button/index.d.ts +3 -0
- package/button/index.d.ts.map +1 -0
- package/button/index.js +2 -0
- package/button/index.js.map +1 -0
- package/empty-state/EmptyState.d.ts.map +1 -1
- package/empty-state/EmptyState.js +8 -3
- package/empty-state/EmptyState.js.map +1 -1
- package/empty-state/types.d.ts +2 -0
- package/empty-state/types.d.ts.map +1 -1
- package/execution/index.d.ts +1 -1
- package/execution/index.d.ts.map +1 -1
- package/execution/index.js.map +1 -1
- package/execution/useCreateAgentExecution.d.ts +81 -9
- package/execution/useCreateAgentExecution.d.ts.map +1 -1
- package/execution/useCreateAgentExecution.js +42 -4
- package/execution/useCreateAgentExecution.js.map +1 -1
- package/index.d.ts +5 -3
- package/index.d.ts.map +1 -1
- package/index.js +4 -2
- package/index.js.map +1 -1
- package/package.json +4 -4
- package/session/useNewSessionFlow.d.ts +6 -3
- package/session/useNewSessionFlow.d.ts.map +1 -1
- package/session/useNewSessionFlow.js +34 -35
- package/session/useNewSessionFlow.js.map +1 -1
- package/sharing/AgentShareList.d.ts +46 -0
- package/sharing/AgentShareList.d.ts.map +1 -0
- package/sharing/AgentShareList.js +159 -0
- package/sharing/AgentShareList.js.map +1 -0
- package/sharing/ShareAgentDialog.d.ts +38 -25
- package/sharing/ShareAgentDialog.d.ts.map +1 -1
- package/sharing/ShareAgentDialog.js +131 -62
- package/sharing/ShareAgentDialog.js.map +1 -1
- package/sharing/index.d.ts +10 -8
- package/sharing/index.d.ts.map +1 -1
- package/sharing/index.js +5 -4
- package/sharing/index.js.map +1 -1
- package/sharing/useAgentShares.d.ts +48 -0
- package/sharing/useAgentShares.d.ts.map +1 -0
- package/sharing/useAgentShares.js +44 -0
- package/sharing/useAgentShares.js.map +1 -0
- package/sharing/useCanCreateAgentShare.d.ts +43 -0
- package/sharing/useCanCreateAgentShare.d.ts.map +1 -0
- package/sharing/useCanCreateAgentShare.js +44 -0
- package/sharing/useCanCreateAgentShare.js.map +1 -0
- package/sharing/useDeleteAgentShare.d.ts +42 -0
- package/sharing/useDeleteAgentShare.d.ts.map +1 -0
- package/sharing/useDeleteAgentShare.js +45 -0
- package/sharing/useDeleteAgentShare.js.map +1 -0
- package/sharing/useSaveAgentShare.d.ts +43 -18
- package/sharing/useSaveAgentShare.d.ts.map +1 -1
- package/sharing/useSaveAgentShare.js +55 -22
- package/sharing/useSaveAgentShare.js.map +1 -1
- package/src/agent/AgentDetailView.tsx +37 -43
- package/src/agent-instance/AgentInstanceEmptyState.tsx +24 -43
- package/src/agent-instance/AgentInstanceList.tsx +29 -16
- package/src/agent-instance/__tests__/agent-instance-hooks.test.tsx +19 -0
- package/src/agent-instance/useAgentInstances.ts +12 -3
- package/src/button/Button.tsx +104 -0
- package/src/button/__tests__/Button.test.tsx +82 -0
- package/src/button/index.ts +2 -0
- package/src/empty-state/EmptyState.tsx +8 -10
- package/src/empty-state/types.ts +2 -0
- package/src/execution/__tests__/useCreateAgentExecution.test.tsx +92 -0
- package/src/execution/index.ts +2 -0
- package/src/execution/useCreateAgentExecution.ts +116 -10
- package/src/index.ts +17 -9
- package/src/session/__tests__/useNewSessionFlow.test.tsx +121 -52
- package/src/session/useNewSessionFlow.ts +38 -37
- package/src/sharing/AgentShareList.tsx +502 -0
- package/src/sharing/ShareAgentDialog.tsx +310 -112
- package/src/sharing/__tests__/AgentShareList.test.tsx +388 -0
- package/src/sharing/__tests__/ShareAgentDialog.test.tsx +311 -312
- package/src/sharing/__tests__/useAgentShares.test.tsx +186 -0
- package/src/sharing/__tests__/useCanCreateAgentShare.test.tsx +190 -0
- package/src/sharing/index.ts +10 -12
- package/src/sharing/useAgentShares.ts +74 -0
- package/src/sharing/useCanCreateAgentShare.ts +74 -0
- package/src/sharing/useDeleteAgentShare.ts +73 -0
- package/src/sharing/useSaveAgentShare.ts +73 -23
- package/src/workflow/WorkflowDetailView.tsx +9 -0
- package/src/workflow/instance/WorkflowInstanceEmptyState.tsx +24 -43
- package/src/workflow/instance/WorkflowInstanceList.tsx +29 -16
- package/src/workflow/useWorkflowInstances.ts +10 -3
- package/styles.css +1 -1
- package/workflow/WorkflowDetailView.d.ts +8 -1
- package/workflow/WorkflowDetailView.d.ts.map +1 -1
- package/workflow/WorkflowDetailView.js +2 -2
- package/workflow/WorkflowDetailView.js.map +1 -1
- package/workflow/instance/WorkflowInstanceEmptyState.d.ts +4 -1
- package/workflow/instance/WorkflowInstanceEmptyState.d.ts.map +1 -1
- package/workflow/instance/WorkflowInstanceEmptyState.js +12 -5
- package/workflow/instance/WorkflowInstanceEmptyState.js.map +1 -1
- package/workflow/instance/WorkflowInstanceList.d.ts +13 -2
- package/workflow/instance/WorkflowInstanceList.d.ts.map +1 -1
- package/workflow/instance/WorkflowInstanceList.js +8 -4
- package/workflow/instance/WorkflowInstanceList.js.map +1 -1
- package/workflow/useWorkflowInstances.d.ts +8 -3
- package/workflow/useWorkflowInstances.d.ts.map +1 -1
- package/workflow/useWorkflowInstances.js +10 -4
- package/workflow/useWorkflowInstances.js.map +1 -1
- package/sharing/useAgentShare.d.ts +0 -49
- package/sharing/useAgentShare.d.ts.map +0 -1
- package/sharing/useAgentShare.js +0 -64
- package/sharing/useAgentShare.js.map +0 -1
- package/sharing/useCreateExternalShareLink.d.ts +0 -90
- package/sharing/useCreateExternalShareLink.d.ts.map +0 -1
- package/sharing/useCreateExternalShareLink.js +0 -65
- package/sharing/useCreateExternalShareLink.js.map +0 -1
- package/sharing/useShareAgent.d.ts +0 -69
- package/sharing/useShareAgent.d.ts.map +0 -1
- package/sharing/useShareAgent.js +0 -42
- package/sharing/useShareAgent.js.map +0 -1
- package/src/sharing/__tests__/useAgentShare.test.tsx +0 -210
- package/src/sharing/__tests__/useCreateExternalShareLink.test.tsx +0 -194
- package/src/sharing/__tests__/useShareAgent.test.tsx +0 -131
- package/src/sharing/useAgentShare.ts +0 -105
- package/src/sharing/useCreateExternalShareLink.tsx +0 -141
- package/src/sharing/useShareAgent.tsx +0 -107
|
@@ -0,0 +1,159 @@
|
|
|
1
|
+
"use client";
|
|
2
|
+
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
3
|
+
import { useCallback, useState } from "react";
|
|
4
|
+
import { cn } from "@stigmer/theme";
|
|
5
|
+
import { appendLinkToken, chatPath, getUserMessage, } from "@stigmer/sdk";
|
|
6
|
+
import { toast } from "../feedback/toast.js";
|
|
7
|
+
import { Button } from "../button/Button.js";
|
|
8
|
+
import { EmptyState } from "../empty-state/EmptyState.js";
|
|
9
|
+
import { PermissionGate } from "../iam-policy/PermissionGate.js";
|
|
10
|
+
import { ConfirmDialog } from "../resource-detail/ConfirmDialog.js";
|
|
11
|
+
import { useConfirmAction } from "../resource-detail/useConfirmAction.js";
|
|
12
|
+
import { useCopyResource } from "../resource-detail/useCopyResource.js";
|
|
13
|
+
import { ShareAgentDialog } from "./ShareAgentDialog.js";
|
|
14
|
+
import { useAgentShares } from "./useAgentShares.js";
|
|
15
|
+
import { useCanCreateAgentShare } from "./useCanCreateAgentShare.js";
|
|
16
|
+
import { useDeleteAgentShare } from "./useDeleteAgentShare.js";
|
|
17
|
+
import { useRotateShareLink } from "./useRotateShareLink.js";
|
|
18
|
+
import { draftFromShare, sharingAudienceFromProto, useSaveAgentShare, } from "./useSaveAgentShare.js";
|
|
19
|
+
/**
|
|
20
|
+
* Management surface for an agent's {@link AgentShare} channels — the
|
|
21
|
+
* agent analog of {@link AgentInstanceList}, rendered in the agent
|
|
22
|
+
* detail view's Shares tab.
|
|
23
|
+
*
|
|
24
|
+
* Lists the viewer's active org's channels of the agent: `viewerOrg`
|
|
25
|
+
* scopes the `getByAgent` call server-side, so a member of several orgs
|
|
26
|
+
* sees exactly the current org context's channels — never a merged list
|
|
27
|
+
* of every org's (decision 013 amendment). Per-row actions: copy link,
|
|
28
|
+
* edit, pause/resume, reset link, delete. Creation goes through the same
|
|
29
|
+
* {@link ShareAgentDialog} and always lands in the viewer's active org;
|
|
30
|
+
* the create bar mirrors the server's via
|
|
31
|
+
* {@link useCanCreateAgentShare}, so the button never appears to a user
|
|
32
|
+
* whose create would be refused.
|
|
33
|
+
*
|
|
34
|
+
* Self-contained: owns its dialog, its confirmation prompts, and its
|
|
35
|
+
* refetch-after-mutation — hosts render it with just the agent and the
|
|
36
|
+
* URL builder.
|
|
37
|
+
*
|
|
38
|
+
* This is an SDK component (DD-001) — embeddable by platform builders.
|
|
39
|
+
*/
|
|
40
|
+
export function AgentShareList({ agent, viewerOrg, buildShareUrl, className, }) {
|
|
41
|
+
const agentId = agent.metadata?.id ?? "";
|
|
42
|
+
// Scope the list to the org whose context the viewer is in; when the
|
|
43
|
+
// host passes no viewerOrg the scope falls back to the agent's own org
|
|
44
|
+
// (the same-org owner flow), matching where creation would land.
|
|
45
|
+
const { shares, isLoading, error, refetch } = useAgentShares(agentId, viewerOrg || (agent.metadata?.org ?? ""));
|
|
46
|
+
const { allowed: canCreate, shareOrg } = useCanCreateAgentShare(agent, viewerOrg);
|
|
47
|
+
const { deleteShare } = useDeleteAgentShare();
|
|
48
|
+
const { confirmState, confirm, handleConfirm, handleCancel } = useConfirmAction();
|
|
49
|
+
// One dialog instance serves both flows: editing the chosen share, or
|
|
50
|
+
// creating a new one in the viewer's org.
|
|
51
|
+
const [editor, setEditor] = useState(null);
|
|
52
|
+
const handleDelete = useCallback(async (share) => {
|
|
53
|
+
const slug = share.metadata?.slug ?? "";
|
|
54
|
+
const confirmed = await confirm({
|
|
55
|
+
title: "Delete share?",
|
|
56
|
+
description: `The link /chat/${share.metadata?.org}/${slug} stops working ` +
|
|
57
|
+
"immediately — including for visitors mid-conversation — and its " +
|
|
58
|
+
"configuration (origins, messages, credential bindings) is gone. " +
|
|
59
|
+
"To stop serving while keeping the configuration, pause it instead.",
|
|
60
|
+
confirmLabel: "Delete",
|
|
61
|
+
variant: "destructive",
|
|
62
|
+
});
|
|
63
|
+
if (!confirmed)
|
|
64
|
+
return;
|
|
65
|
+
try {
|
|
66
|
+
await deleteShare(share.metadata?.id ?? "");
|
|
67
|
+
toast.success("Share deleted");
|
|
68
|
+
refetch();
|
|
69
|
+
}
|
|
70
|
+
catch (err) {
|
|
71
|
+
toast.error(getUserMessage(err));
|
|
72
|
+
}
|
|
73
|
+
}, [confirm, deleteShare, refetch]);
|
|
74
|
+
if (isLoading) {
|
|
75
|
+
return _jsx(LoadingSkeleton, {});
|
|
76
|
+
}
|
|
77
|
+
if (error) {
|
|
78
|
+
return (_jsx("div", { className: "py-8 text-center text-sm text-destructive", children: "Failed to load shares" }));
|
|
79
|
+
}
|
|
80
|
+
return (_jsxs("div", { className: cn("space-y-3", className), children: [shares.length === 0 ? (_jsx(ShareEmptyState, { canCreate: canCreate, onCreateClick: () => setEditor({ mode: "create" }) })) : (_jsxs(_Fragment, { children: [_jsxs("div", { className: "flex items-center justify-between", children: [_jsxs("h3", { className: "text-sm font-medium text-foreground", children: [shares.length, " ", shares.length === 1 ? "share" : "shares"] }), canCreate && (_jsx(Button, { variant: "outline", size: "xs", icon: _jsx(PlusIcon, {}), onClick: () => setEditor({ mode: "create" }), children: "Create share" }))] }), _jsx("div", { className: "overflow-hidden rounded-lg border border-border", children: _jsxs("table", { className: "w-full text-sm", children: [_jsx("thead", { children: _jsxs("tr", { className: "border-b border-border bg-muted-subtle", children: [_jsx("th", { className: "px-4 py-2 text-left font-medium text-muted-foreground", children: "Name" }), _jsx("th", { className: "px-4 py-2 text-left font-medium text-muted-foreground", children: "Link" }), _jsx("th", { className: "px-4 py-2 text-left font-medium text-muted-foreground", children: "Audience" }), _jsx("th", { className: "px-4 py-2 text-left font-medium text-muted-foreground", children: "Status" }), _jsx("th", { className: "px-4 py-2 text-right font-medium text-muted-foreground", children: "Actions" })] }) }), _jsx("tbody", { className: "divide-y divide-border", children: shares.map((share) => (_jsx(ShareRow, { share: share, agent: agent, buildShareUrl: buildShareUrl, onEditClick: (s) => setEditor({ mode: "edit", share: s }), onDeleteClick: handleDelete, refetch: refetch }, share.metadata?.id))) })] }) })] })), editor && (_jsx(ShareAgentDialog, { open: true, onOpenChange: (open) => {
|
|
81
|
+
if (!open)
|
|
82
|
+
setEditor(null);
|
|
83
|
+
}, agent: agent, share: editor.mode === "edit" ? editor.share : undefined, shareOrg: shareOrg, buildShareUrl: buildShareUrl, onSharingChanged: refetch })), _jsx(ConfirmDialog, { state: confirmState, onConfirm: handleConfirm, onCancel: handleCancel })] }));
|
|
84
|
+
}
|
|
85
|
+
function ShareRow({ share, agent, buildShareUrl, onEditClick, onDeleteClick, refetch, }) {
|
|
86
|
+
const meta = share.metadata;
|
|
87
|
+
const id = meta?.id ?? "";
|
|
88
|
+
const org = meta?.org ?? "";
|
|
89
|
+
const slug = meta?.slug ?? "";
|
|
90
|
+
const enabled = share.spec?.enabled ?? false;
|
|
91
|
+
const audience = sharingAudienceFromProto(share.spec?.audience);
|
|
92
|
+
const isCrossOrg = org !== (agent.metadata?.org ?? "");
|
|
93
|
+
const { copy } = useCopyResource();
|
|
94
|
+
const { save, isPending } = useSaveAgentShare(agent);
|
|
95
|
+
const { rotateShareLink, isPending: isRotating } = useRotateShareLink(id);
|
|
96
|
+
// The copyable URL carries the link token on public shares (org
|
|
97
|
+
// audience is gated by membership, not the token). The display stays
|
|
98
|
+
// the bare path — the token is a secret, not an address.
|
|
99
|
+
const displayPath = chatPath(org, slug);
|
|
100
|
+
const copyUrl = (() => {
|
|
101
|
+
const base = buildShareUrl ? buildShareUrl(org, slug) : displayPath;
|
|
102
|
+
return audience === "org"
|
|
103
|
+
? base
|
|
104
|
+
: appendLinkToken(base, share.status?.shareLinkToken ?? "");
|
|
105
|
+
})();
|
|
106
|
+
const handleCopyLink = useCallback(() => {
|
|
107
|
+
void copy(copyUrl, "Link");
|
|
108
|
+
}, [copy, copyUrl]);
|
|
109
|
+
// Pause/resume is a full-spec save with only `enabled` flipped —
|
|
110
|
+
// draftFromShare guarantees a toggle can never wipe origins, messages,
|
|
111
|
+
// or credential bindings (the fails-closed posture the CLI shares).
|
|
112
|
+
const handleToggleEnabled = useCallback(async () => {
|
|
113
|
+
try {
|
|
114
|
+
await save({ ...draftFromShare(share), enabled: !enabled }, share);
|
|
115
|
+
toast.success(enabled ? "Share paused" : "Share resumed");
|
|
116
|
+
refetch();
|
|
117
|
+
}
|
|
118
|
+
catch (err) {
|
|
119
|
+
toast.error(getUserMessage(err));
|
|
120
|
+
}
|
|
121
|
+
}, [save, share, enabled, refetch]);
|
|
122
|
+
const handleResetLink = useCallback(async () => {
|
|
123
|
+
try {
|
|
124
|
+
await rotateShareLink();
|
|
125
|
+
toast.success("Link reset — the old link no longer works");
|
|
126
|
+
refetch();
|
|
127
|
+
}
|
|
128
|
+
catch (err) {
|
|
129
|
+
toast.error(getUserMessage(err));
|
|
130
|
+
}
|
|
131
|
+
}, [rotateShareLink, refetch]);
|
|
132
|
+
return (_jsxs("tr", { className: "cursor-pointer transition-colors hover:bg-accent-hover", onClick: () => onEditClick(share), children: [_jsx("td", { className: "px-4 py-2.5", children: _jsxs("div", { className: "flex items-center gap-2", children: [_jsx("span", { className: "font-medium text-foreground", children: meta?.name || slug || "\u2014" }), isCrossOrg && (_jsx("span", { className: cn("inline-flex items-center rounded-md px-1.5 py-0.5", "text-[0.6rem] font-medium uppercase tracking-wide", "bg-muted text-muted-foreground border border-border"), title: `This share lives in ${org}; the agent lives in ${agent.metadata?.org}`, children: "Cross-org" }))] }) }), _jsx("td", { className: "px-4 py-2.5", onClick: (e) => e.stopPropagation(), children: _jsxs("div", { className: "flex items-center gap-1.5", children: [_jsx("code", { className: "max-w-56 truncate font-mono text-xs text-muted-foreground", title: displayPath, children: displayPath }), _jsx("button", { type: "button", onClick: handleCopyLink, "aria-label": `Copy link for ${meta?.name || slug}`, className: cn("rounded p-1 text-muted-foreground", "hover:bg-accent-hover hover:text-foreground", "focus:outline-none focus:ring-1 focus:ring-ring"), children: _jsx(CopyIcon, {}) })] }) }), _jsx("td", { className: "px-4 py-2.5", children: _jsx("span", { className: "text-xs text-muted-foreground", children: audience === "org" ? "Org members" : "Public" }) }), _jsx("td", { className: "px-4 py-2.5", children: _jsxs("span", { className: cn("inline-flex items-center gap-1.5 text-xs", enabled ? "text-foreground" : "text-muted-foreground"), children: [_jsx("span", { "aria-hidden": "true", className: cn("size-1.5 rounded-full", enabled ? "bg-success" : "bg-muted-foreground") }), enabled ? "Active" : "Paused"] }) }), _jsx("td", { className: "px-4 py-2.5 text-right", onClick: (e) => e.stopPropagation(), children: _jsxs("div", { className: "flex items-center justify-end gap-1", children: [_jsxs(PermissionGate, { resource: { kind: "agent_share", id }, relation: "can_edit", children: [_jsx("button", { type: "button", onClick: () => onEditClick(share), className: cn("rounded px-2 py-1 text-xs font-medium", "text-foreground hover:bg-accent-hover", "focus:outline-none focus:ring-1 focus:ring-ring"), children: "Edit" }), _jsx("button", { type: "button", onClick: () => void handleToggleEnabled(), disabled: isPending, className: cn("rounded px-2 py-1 text-xs font-medium", "text-foreground hover:bg-accent-hover", "focus:outline-none focus:ring-1 focus:ring-ring", "disabled:pointer-events-none disabled:opacity-50"), children: enabled ? "Pause" : "Resume" }), audience === "public" && (_jsx("button", { type: "button", onClick: () => void handleResetLink(), disabled: isRotating, className: cn("rounded px-2 py-1 text-xs font-medium", "text-foreground hover:bg-accent-hover", "focus:outline-none focus:ring-1 focus:ring-ring", "disabled:pointer-events-none disabled:opacity-50"), children: isRotating ? "Resetting…" : "Reset link" }))] }), _jsx(PermissionGate, { resource: { kind: "agent_share", id }, relation: "can_delete", children: _jsx("button", { type: "button", onClick: () => onDeleteClick(share), className: cn("rounded px-2 py-1 text-xs font-medium", "text-destructive hover:bg-destructive-subtle", "focus:outline-none focus:ring-1 focus:ring-ring"), children: "Delete" }) })] }) })] }));
|
|
133
|
+
}
|
|
134
|
+
// ---------------------------------------------------------------------------
|
|
135
|
+
// Empty state
|
|
136
|
+
// ---------------------------------------------------------------------------
|
|
137
|
+
function ShareEmptyState({ canCreate, onCreateClick, }) {
|
|
138
|
+
return (_jsx(EmptyState, { variant: "first-use", icon: _jsx(ShareIcon, { className: "size-10" }), title: "No shares yet", description: "A share gives this agent a hosted chat link you can send or embed — " +
|
|
139
|
+
"each share is its own channel with its own audience, embed origins, " +
|
|
140
|
+
"and tool credentials.", action: canCreate
|
|
141
|
+
? { label: "Create share", onClick: onCreateClick, icon: _jsx(PlusIcon, {}) }
|
|
142
|
+
: undefined }));
|
|
143
|
+
}
|
|
144
|
+
// ---------------------------------------------------------------------------
|
|
145
|
+
// Non-happy states + icons
|
|
146
|
+
// ---------------------------------------------------------------------------
|
|
147
|
+
function LoadingSkeleton() {
|
|
148
|
+
return (_jsx("div", { className: "space-y-2 py-4", children: [1, 2, 3].map((i) => (_jsx("div", { className: "h-12 animate-pulse rounded-md bg-muted-faint" }, i))) }));
|
|
149
|
+
}
|
|
150
|
+
function PlusIcon() {
|
|
151
|
+
return (_jsx("svg", { width: "12", height: "12", viewBox: "0 0 12 12", fill: "none", "aria-hidden": "true", children: _jsx("path", { d: "M6 2v8M2 6h8", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round" }) }));
|
|
152
|
+
}
|
|
153
|
+
function CopyIcon() {
|
|
154
|
+
return (_jsxs("svg", { width: "12", height: "12", viewBox: "0 0 16 16", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true", children: [_jsx("rect", { x: "5.5", y: "5.5", width: "8", height: "8", rx: "1.5" }), _jsx("path", { d: "M10.5 5.5v-2a1 1 0 0 0-1-1h-6a1 1 0 0 0-1 1v6a1 1 0 0 0 1 1h2" })] }));
|
|
155
|
+
}
|
|
156
|
+
function ShareIcon({ className }) {
|
|
157
|
+
return (_jsxs("svg", { className: className, viewBox: "0 0 16 16", fill: "none", stroke: "currentColor", strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round", "aria-hidden": "true", children: [_jsx("circle", { cx: "4", cy: "8", r: "2" }), _jsx("circle", { cx: "12", cy: "4", r: "2" }), _jsx("circle", { cx: "12", cy: "12", r: "2" }), _jsx("path", { d: "m5.8 7.1 4.4-2.2M5.8 8.9l4.4 2.2" })] }));
|
|
158
|
+
}
|
|
159
|
+
//# sourceMappingURL=AgentShareList.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"AgentShareList.js","sourceRoot":"","sources":["../../src/sharing/AgentShareList.tsx"],"names":[],"mappings":"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"}
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import type { Agent } from "@stigmer/protos/ai/stigmer/agentic/agent/v1/api_pb";
|
|
2
|
+
import type { AgentShare } from "@stigmer/protos/ai/stigmer/agentic/agentshare/v1/api_pb";
|
|
2
3
|
/** Props for {@link ShareAgentDialog}. */
|
|
3
4
|
export interface ShareAgentDialogProps {
|
|
4
5
|
/** Whether the dialog is open. */
|
|
@@ -7,6 +8,24 @@ export interface ShareAgentDialogProps {
|
|
|
7
8
|
readonly onOpenChange: (open: boolean) => void;
|
|
8
9
|
/** The agent whose sharing is managed. */
|
|
9
10
|
readonly agent: Agent;
|
|
11
|
+
/**
|
|
12
|
+
* The exact share to edit. When omitted, the dialog opens in **create
|
|
13
|
+
* mode**: a name/slug step creates a new share in `shareOrg`, then the
|
|
14
|
+
* dialog becomes its editor. The share's identity is immutable once
|
|
15
|
+
* created (decision 011 D2) — edit mode never renames.
|
|
16
|
+
*/
|
|
17
|
+
readonly share?: AgentShare | null;
|
|
18
|
+
/**
|
|
19
|
+
* The org that owns (and pays for) a share created by this dialog.
|
|
20
|
+
* Defaults to the agent's own org — the owner's channel. Pass the
|
|
21
|
+
* viewer's org to create a **cross-org share** of another org's
|
|
22
|
+
* marketplace-public agent (decision 013): the share, its billing,
|
|
23
|
+
* its credentials, and its hosted URL all belong to this org, while
|
|
24
|
+
* the agent stays live in its own. Cross-org shares are
|
|
25
|
+
* public-audience only, so the audience selector is hidden in that
|
|
26
|
+
* mode. Ignored in edit mode — an existing share knows its org.
|
|
27
|
+
*/
|
|
28
|
+
readonly shareOrg?: string;
|
|
10
29
|
/**
|
|
11
30
|
* Builds the absolute public chat URL for the shared agent. The host
|
|
12
31
|
* application owns URL construction (its configured public origin may
|
|
@@ -16,19 +35,9 @@ export interface ShareAgentDialogProps {
|
|
|
16
35
|
readonly buildShareUrl?: (org: string, slug: string) => string;
|
|
17
36
|
/**
|
|
18
37
|
* Called after any sharing change is persisted. Hosts typically pass
|
|
19
|
-
* the
|
|
38
|
+
* the share list's `refetch`.
|
|
20
39
|
*/
|
|
21
40
|
readonly onSharingChanged?: () => void;
|
|
22
|
-
/**
|
|
23
|
-
* The org that owns (and pays for) the share. Defaults to the agent's
|
|
24
|
-
* own org — the owner's channel. Pass the viewer's org to manage a
|
|
25
|
-
* **cross-org share** of another org's marketplace-public agent
|
|
26
|
-
* (decision 013): the share, its billing, its credentials, and its
|
|
27
|
-
* hosted URL all belong to this org, while the agent stays live in its
|
|
28
|
-
* own. Cross-org shares are public-audience only, so the audience
|
|
29
|
-
* selector is hidden in that mode.
|
|
30
|
-
*/
|
|
31
|
-
readonly shareOrg?: string;
|
|
32
41
|
/**
|
|
33
42
|
* When `false`, renders as an in-flow open dialog instead of a
|
|
34
43
|
* top-layer modal — no `showModal()`, no backdrop, no focus trap.
|
|
@@ -39,29 +48,33 @@ export interface ShareAgentDialogProps {
|
|
|
39
48
|
readonly modal?: boolean;
|
|
40
49
|
}
|
|
41
50
|
/**
|
|
42
|
-
* The Share dialog for
|
|
43
|
-
*
|
|
44
|
-
*
|
|
45
|
-
* and discover the PlatformClient
|
|
51
|
+
* The Share dialog for one agent share: create it (name/slug step), then
|
|
52
|
+
* toggle serving, copy the hosted chat link, copy an embeddable snippet,
|
|
53
|
+
* manage allowed embed origins, bind tool credentials for visitors,
|
|
54
|
+
* customize visitor refusal messages, and discover the PlatformClient
|
|
55
|
+
* SDK path.
|
|
46
56
|
*
|
|
47
57
|
* Sharing is a distinct consent from marketplace visibility: visibility
|
|
48
58
|
* governs who can *read* the blueprint; sharing governs who can *chat*
|
|
49
|
-
* with the running agent — billed to the
|
|
50
|
-
* who pays next to the toggle so
|
|
59
|
+
* with the running agent — billed to the org that owns the share. The
|
|
60
|
+
* dialog states who pays before creation and next to the toggle, so
|
|
61
|
+
* sharing never surprises.
|
|
51
62
|
*
|
|
52
|
-
* Sharing lives in its own **AgentShare resource** (decision 011),
|
|
53
|
-
*
|
|
54
|
-
*
|
|
55
|
-
*
|
|
56
|
-
*
|
|
57
|
-
*
|
|
63
|
+
* Sharing lives in its own **AgentShare resource** (decision 011), and
|
|
64
|
+
* an agent can carry N shares — each its own channel with its own URL,
|
|
65
|
+
* audience, origins, credentials, and link token (D3). The dialog edits
|
|
66
|
+
* exactly the share it is given; it never resolves "the" share of an
|
|
67
|
+
* agent. Every save is an idempotent `apply` of the complete
|
|
68
|
+
* configuration ({@link useSaveAgentShare}), and the local draft is
|
|
69
|
+
* refreshed from every returned share, so the dialog never drifts from
|
|
70
|
+
* the server.
|
|
58
71
|
*
|
|
59
72
|
* Built on the native `<dialog>` element for focus trapping and escape
|
|
60
73
|
* handling, matching the SDK's modal convention ({@link ManageAccessDialog}).
|
|
61
74
|
* All visual properties flow through `--stgm-*` design tokens.
|
|
62
75
|
*
|
|
63
|
-
* Most hosts mount it via {@link
|
|
76
|
+
* Most hosts mount it via {@link AgentShareList} (the Shares tab).
|
|
64
77
|
* Render it directly only when you own the open-state.
|
|
65
78
|
*/
|
|
66
|
-
export declare function ShareAgentDialog({ open, onOpenChange, agent, buildShareUrl, onSharingChanged,
|
|
79
|
+
export declare function ShareAgentDialog({ open, onOpenChange, agent, share, shareOrg, buildShareUrl, onSharingChanged, modal, }: ShareAgentDialogProps): import("react/jsx-runtime").JSX.Element;
|
|
67
80
|
//# sourceMappingURL=ShareAgentDialog.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ShareAgentDialog.d.ts","sourceRoot":"","sources":["../../src/sharing/ShareAgentDialog.tsx"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"ShareAgentDialog.d.ts","sourceRoot":"","sources":["../../src/sharing/ShareAgentDialog.tsx"],"names":[],"mappings":"AAeA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,oDAAoD,CAAC;AAChF,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,yDAAyD,CAAC;AAmC1F,0CAA0C;AAC1C,MAAM,WAAW,qBAAqB;IACpC,kCAAkC;IAClC,QAAQ,CAAC,IAAI,EAAE,OAAO,CAAC;IACvB,mDAAmD;IACnD,QAAQ,CAAC,YAAY,EAAE,CAAC,IAAI,EAAE,OAAO,KAAK,IAAI,CAAC;IAC/C,0CAA0C;IAC1C,QAAQ,CAAC,KAAK,EAAE,KAAK,CAAC;IACtB;;;;;OAKG;IACH,QAAQ,CAAC,KAAK,CAAC,EAAE,UAAU,GAAG,IAAI,CAAC;IACnC;;;;;;;;;OASG;IACH,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAC3B;;;;;OAKG;IACH,QAAQ,CAAC,aAAa,CAAC,EAAE,CAAC,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,KAAK,MAAM,CAAC;IAC/D;;;OAGG;IACH,QAAQ,CAAC,gBAAgB,CAAC,EAAE,MAAM,IAAI,CAAC;IACvC;;;;;;OAMG;IACH,QAAQ,CAAC,KAAK,CAAC,EAAE,OAAO,CAAC;CAC1B;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4BG;AACH,wBAAgB,gBAAgB,CAAC,EAC/B,IAAI,EACJ,YAAY,EACZ,KAAK,EACL,KAAK,EACL,QAAQ,EACR,aAAa,EACb,gBAAgB,EAChB,KAAY,GACb,EAAE,qBAAqB,2CAkDvB"}
|
|
@@ -2,8 +2,10 @@
|
|
|
2
2
|
import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
|
|
3
3
|
import { useCallback, useMemo, useRef, useState } from "react";
|
|
4
4
|
import { cn } from "@stigmer/theme";
|
|
5
|
-
import { MAX_ALLOWED_ORIGINS, appendLinkToken, buildEmbedSnippet, chatPath, getUserMessage, validateOrigin, } from "@stigmer/sdk";
|
|
5
|
+
import { MAX_ALLOWED_ORIGINS, StigmerError, appendLinkToken, buildEmbedSnippet, chatPath, getUserMessage, validateOrigin, } from "@stigmer/sdk";
|
|
6
|
+
import { create as createMessage } from "@bufbuild/protobuf";
|
|
6
7
|
import { ApiResourceVisibility } from "@stigmer/protos/ai/stigmer/commons/apiresource/enum_pb";
|
|
8
|
+
import { ApiResourceMetadataSchema } from "@stigmer/protos/ai/stigmer/commons/apiresource/metadata_pb";
|
|
7
9
|
import { Switch } from "../switch/Switch.js";
|
|
8
10
|
import { Tabs } from "../tabs/Tabs.js";
|
|
9
11
|
import { toast } from "../feedback/toast.js";
|
|
@@ -12,8 +14,9 @@ import { useDeploymentMode } from "../deployment-mode.js";
|
|
|
12
14
|
import { useBillingAccount } from "../billing/useBillingAccount.js";
|
|
13
15
|
import { formatCreditBalance } from "../billing/format.js";
|
|
14
16
|
import { EnvironmentPicker } from "../environment/EnvironmentPicker.js";
|
|
15
|
-
import {
|
|
16
|
-
import {
|
|
17
|
+
import { generateSlug } from "../internal/slug.js";
|
|
18
|
+
import { getFieldError, validateMessage } from "../internal/validate.js";
|
|
19
|
+
import { draftFromShare, useSaveAgentShare, } from "./useSaveAgentShare.js";
|
|
17
20
|
import { useRotateShareLink } from "./useRotateShareLink.js";
|
|
18
21
|
import { useShareToolReadiness } from "./useShareToolReadiness.js";
|
|
19
22
|
/** Maximum length of each visitor message (proto: `string.max_len = 300`). */
|
|
@@ -25,31 +28,35 @@ const SHARE_TABS = [
|
|
|
25
28
|
];
|
|
26
29
|
const PLATFORM_CLIENT_DOCS_URL = "https://docs.stigmer.ai/guides/authentication/platform-client/overview";
|
|
27
30
|
/**
|
|
28
|
-
* The Share dialog for
|
|
29
|
-
*
|
|
30
|
-
*
|
|
31
|
-
* and discover the PlatformClient
|
|
31
|
+
* The Share dialog for one agent share: create it (name/slug step), then
|
|
32
|
+
* toggle serving, copy the hosted chat link, copy an embeddable snippet,
|
|
33
|
+
* manage allowed embed origins, bind tool credentials for visitors,
|
|
34
|
+
* customize visitor refusal messages, and discover the PlatformClient
|
|
35
|
+
* SDK path.
|
|
32
36
|
*
|
|
33
37
|
* Sharing is a distinct consent from marketplace visibility: visibility
|
|
34
38
|
* governs who can *read* the blueprint; sharing governs who can *chat*
|
|
35
|
-
* with the running agent — billed to the
|
|
36
|
-
* who pays next to the toggle so
|
|
39
|
+
* with the running agent — billed to the org that owns the share. The
|
|
40
|
+
* dialog states who pays before creation and next to the toggle, so
|
|
41
|
+
* sharing never surprises.
|
|
37
42
|
*
|
|
38
|
-
* Sharing lives in its own **AgentShare resource** (decision 011),
|
|
39
|
-
*
|
|
40
|
-
*
|
|
41
|
-
*
|
|
42
|
-
*
|
|
43
|
-
*
|
|
43
|
+
* Sharing lives in its own **AgentShare resource** (decision 011), and
|
|
44
|
+
* an agent can carry N shares — each its own channel with its own URL,
|
|
45
|
+
* audience, origins, credentials, and link token (D3). The dialog edits
|
|
46
|
+
* exactly the share it is given; it never resolves "the" share of an
|
|
47
|
+
* agent. Every save is an idempotent `apply` of the complete
|
|
48
|
+
* configuration ({@link useSaveAgentShare}), and the local draft is
|
|
49
|
+
* refreshed from every returned share, so the dialog never drifts from
|
|
50
|
+
* the server.
|
|
44
51
|
*
|
|
45
52
|
* Built on the native `<dialog>` element for focus trapping and escape
|
|
46
53
|
* handling, matching the SDK's modal convention ({@link ManageAccessDialog}).
|
|
47
54
|
* All visual properties flow through `--stgm-*` design tokens.
|
|
48
55
|
*
|
|
49
|
-
* Most hosts mount it via {@link
|
|
56
|
+
* Most hosts mount it via {@link AgentShareList} (the Shares tab).
|
|
50
57
|
* Render it directly only when you own the open-state.
|
|
51
58
|
*/
|
|
52
|
-
export function ShareAgentDialog({ open, onOpenChange, agent, buildShareUrl, onSharingChanged,
|
|
59
|
+
export function ShareAgentDialog({ open, onOpenChange, agent, share, shareOrg, buildShareUrl, onSharingChanged, modal = true, }) {
|
|
53
60
|
const dialogRef = useRef(null);
|
|
54
61
|
const handleClose = useCallback(() => {
|
|
55
62
|
dialogRef.current?.close();
|
|
@@ -72,68 +79,130 @@ export function ShareAgentDialog({ open, onOpenChange, agent, buildShareUrl, onS
|
|
|
72
79
|
dialogRef.current.close();
|
|
73
80
|
}
|
|
74
81
|
}
|
|
75
|
-
return (_jsx("dialog", { ref: dialogRef, open: modal ? undefined : open, onClose: handleClose, className: cn("w-full max-w-lg rounded-xl border border-border bg-popover p-0 shadow-xl", modal ? "fixed inset-0 m-auto backdrop:bg-black/50" : "relative"), "aria-labelledby": "share-agent-title", children: open && (_jsx(ShareAgentDialogBody, { agent: agent, buildShareUrl: buildShareUrl, onSharingChanged: onSharingChanged,
|
|
82
|
+
return (_jsx("dialog", { ref: dialogRef, open: modal ? undefined : open, onClose: handleClose, className: cn("w-full max-w-lg rounded-xl border border-border bg-popover p-0 shadow-xl", modal ? "fixed inset-0 m-auto backdrop:bg-black/50" : "relative"), "aria-labelledby": "share-agent-title", children: open && (_jsx(ShareAgentDialogBody, { agent: agent, share: share ?? null, shareOrg: shareOrg, buildShareUrl: buildShareUrl, onSharingChanged: onSharingChanged, onClose: handleClose })) }));
|
|
76
83
|
}
|
|
77
84
|
// ---------------------------------------------------------------------------
|
|
78
|
-
// Dialog body —
|
|
85
|
+
// Dialog body — create step or editor, depending on the share it was given
|
|
79
86
|
// ---------------------------------------------------------------------------
|
|
80
87
|
/**
|
|
81
|
-
*
|
|
82
|
-
*
|
|
83
|
-
*
|
|
84
|
-
*
|
|
88
|
+
* Renders the create step (no share yet) or the editor (share in hand).
|
|
89
|
+
* A share persisted by the create step is adopted locally, so one dialog
|
|
90
|
+
* session flows create → edit without remounting — and the editor's
|
|
91
|
+
* draft seeding stays synchronous (`useState` initializer from the
|
|
92
|
+
* share): no hydrate-on-effect, no window where the switch shows a state
|
|
93
|
+
* the server never had.
|
|
85
94
|
*/
|
|
86
|
-
function ShareAgentDialogBody({ agent, buildShareUrl, onSharingChanged,
|
|
87
|
-
const
|
|
88
|
-
const
|
|
89
|
-
|
|
95
|
+
function ShareAgentDialogBody({ agent, share, shareOrg, buildShareUrl, onSharingChanged, onClose, }) {
|
|
96
|
+
const [created, setCreated] = useState(null);
|
|
97
|
+
const activeShare = share ?? created;
|
|
98
|
+
const isCreating = activeShare === null;
|
|
99
|
+
const resolvedShareOrg = activeShare?.metadata?.org || shareOrg || (agent.metadata?.org ?? "");
|
|
100
|
+
const isCrossOrg = resolvedShareOrg !== (agent.metadata?.org ?? "");
|
|
101
|
+
return (_jsxs("div", { className: "flex flex-col", children: [_jsxs("div", { className: "flex items-start justify-between border-b border-border px-6 py-4", children: [_jsxs("div", { className: "min-w-0", children: [_jsx("h2", { id: "share-agent-title", className: "text-base font-semibold text-foreground", children: isCreating ? "Create share" : "Share" }), _jsx("p", { className: "mt-0.5 truncate text-xs text-muted-foreground", children: isCrossOrg
|
|
90
102
|
? `${agent.metadata?.org}/${agent.metadata?.slug}`
|
|
91
|
-
: agent.metadata?.name || agent.metadata?.slug })] }), _jsx("button", { type: "button", onClick: onClose, "aria-label": "Close", className: cn("rounded-md p-1 text-muted-foreground", "hover:text-foreground hover:bg-accent-hover", "focus:outline-none focus:ring-2 focus:ring-ring"), children: _jsx(CloseIcon, {}) })] }),
|
|
103
|
+
: agent.metadata?.name || agent.metadata?.slug })] }), _jsx("button", { type: "button", onClick: onClose, "aria-label": "Close", className: cn("rounded-md p-1 text-muted-foreground", "hover:text-foreground hover:bg-accent-hover", "focus:outline-none focus:ring-2 focus:ring-ring"), children: _jsx(CloseIcon, {}) })] }), isCreating ? (_jsx(CreateShareForm, { agent: agent, shareOrg: resolvedShareOrg, onCreated: (persisted) => {
|
|
104
|
+
setCreated(persisted);
|
|
105
|
+
onSharingChanged?.();
|
|
106
|
+
} })) : (_jsx(ShareAgentForm, { agent: agent, initialShare: activeShare, buildShareUrl: buildShareUrl, onSharingChanged: onSharingChanged })), _jsx("div", { className: "flex items-center justify-end border-t border-border px-6 py-3", children: _jsx("button", { type: "button", onClick: onClose, className: cn("rounded-md px-3 py-1.5 text-sm font-medium", isCreating
|
|
107
|
+
? "border border-border text-foreground hover:bg-accent-hover"
|
|
108
|
+
: "bg-primary text-primary-foreground hover:bg-primary-hover", "focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2"), children: isCreating ? "Cancel" : "Done" }) })] }));
|
|
92
109
|
}
|
|
93
110
|
// ---------------------------------------------------------------------------
|
|
94
|
-
//
|
|
111
|
+
// Create step — the new share's identity and cost, before any channel exists
|
|
95
112
|
// ---------------------------------------------------------------------------
|
|
96
113
|
/**
|
|
97
|
-
*
|
|
98
|
-
*
|
|
99
|
-
*
|
|
100
|
-
*
|
|
114
|
+
* Names the new share and creates it live (`enabled: true`, public
|
|
115
|
+
* audience — the server's own defaults). Identity is set here because it
|
|
116
|
+
* is immutable afterward (decision 011 D2): the slug becomes the hosted
|
|
117
|
+
* URL `/chat/<org>/<slug>` in the sharing org's namespace.
|
|
118
|
+
*
|
|
119
|
+
* The slug auto-derives from the name until the user edits it (the
|
|
120
|
+
* {@link CreateOrganizationForm} pattern), validated by the same
|
|
121
|
+
* protovalidate rules the server enforces. An `(org, slug)` collision —
|
|
122
|
+
* the server's ALREADY_EXISTS — surfaces inline on the slug field with a
|
|
123
|
+
* pick-another-slug remedy instead of a generic failure toast.
|
|
101
124
|
*/
|
|
102
|
-
function
|
|
103
|
-
const
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
125
|
+
function CreateShareForm({ agent, shareOrg, onCreated, }) {
|
|
126
|
+
const agentName = agent.metadata?.name || (agent.metadata?.slug ?? "");
|
|
127
|
+
const isCrossOrg = shareOrg !== (agent.metadata?.org ?? "");
|
|
128
|
+
const [name, setName] = useState(agentName);
|
|
129
|
+
const [slug, setSlug] = useState(agent.metadata?.slug ?? "");
|
|
130
|
+
// Once the user manually edits the slug field, stop auto-deriving.
|
|
131
|
+
const slugTouchedRef = useRef(false);
|
|
132
|
+
// A server-side (org, slug) collision pins to the slug field until the
|
|
133
|
+
// slug changes — the remedy is picking another slug.
|
|
134
|
+
const [collisionError, setCollisionError] = useState(null);
|
|
135
|
+
const [submitError, setSubmitError] = useState(null);
|
|
136
|
+
const { save, isPending } = useSaveAgentShare(agent, shareOrg);
|
|
137
|
+
const trimmedName = name.trim();
|
|
138
|
+
const violations = slug.length > 0 || trimmedName.length > 0
|
|
139
|
+
? validateMessage(ApiResourceMetadataSchema, createMessage(ApiResourceMetadataSchema, {
|
|
140
|
+
...(slug.length > 0 && { slug }),
|
|
141
|
+
...(trimmedName.length > 0 && { name: trimmedName }),
|
|
142
|
+
}))
|
|
143
|
+
: [];
|
|
144
|
+
const slugError = collisionError ?? (slug.length > 0 ? getFieldError(violations, "slug") : null);
|
|
145
|
+
const nameError = trimmedName.length > 0 ? getFieldError(violations, "name") : null;
|
|
146
|
+
const canSubmit = trimmedName !== "" && slug.length > 0 && slugError === null &&
|
|
147
|
+
nameError === null && !isPending;
|
|
148
|
+
const handleNameChange = useCallback((value) => {
|
|
149
|
+
setName(value);
|
|
150
|
+
if (!slugTouchedRef.current) {
|
|
151
|
+
setSlug(generateSlug(value.trim()));
|
|
152
|
+
setCollisionError(null);
|
|
153
|
+
}
|
|
154
|
+
}, []);
|
|
155
|
+
const handleSlugChange = useCallback((value) => {
|
|
156
|
+
slugTouchedRef.current = true;
|
|
157
|
+
setSlug(value);
|
|
158
|
+
setCollisionError(null);
|
|
159
|
+
}, []);
|
|
160
|
+
const handleSubmit = useCallback(async (e) => {
|
|
161
|
+
e.preventDefault();
|
|
162
|
+
if (!canSubmit)
|
|
163
|
+
return;
|
|
164
|
+
setSubmitError(null);
|
|
165
|
+
try {
|
|
166
|
+
const persisted = await save(
|
|
167
|
+
// The server's create defaults, made explicit: live from the
|
|
168
|
+
// start (the user's one intent-click is "share it"), public
|
|
169
|
+
// audience, nothing else configured yet.
|
|
170
|
+
{ ...draftFromShare(null), enabled: true }, null, { name: trimmedName, slug });
|
|
171
|
+
if (persisted) {
|
|
172
|
+
toast.success("Share created — the link is live");
|
|
173
|
+
onCreated(persisted);
|
|
174
|
+
}
|
|
175
|
+
}
|
|
176
|
+
catch (err) {
|
|
177
|
+
if (err instanceof StigmerError && err.code === "already-exists") {
|
|
178
|
+
setCollisionError(`"${slug}" is already used by another share or resource in ${shareOrg} — pick a different slug`);
|
|
179
|
+
}
|
|
180
|
+
else {
|
|
181
|
+
// e.g. the cross-org FAILED_PRECONDITION naming non-public
|
|
182
|
+
// dependencies (decision 013 D5) — show the server's words.
|
|
183
|
+
setSubmitError(getUserMessage(err));
|
|
184
|
+
}
|
|
185
|
+
}
|
|
186
|
+
}, [canSubmit, save, trimmedName, slug, shareOrg, onCreated]);
|
|
187
|
+
return (_jsxs("form", { onSubmit: handleSubmit, className: "flex flex-col gap-4 px-6 py-4", children: [_jsxs("p", { className: "text-xs text-muted-foreground", children: ["A share is its own channel to this agent: a hosted chat link with its own audience, embed origins, tool credentials, and visitor messages.", " ", isCrossOrg && (_jsxs(_Fragment, { children: ["This one lives in your organization", " ", _jsx("span", { className: "font-medium", children: shareOrg }), " while the agent stays in ", _jsx("span", { className: "font-medium", children: agent.metadata?.org }), " ", "\u2014 updates to the agent apply live.", " "] })), "Visitors chat on ", _jsx("span", { className: "font-medium", children: shareOrg }), "'s credits."] }), _jsxs("div", { className: "space-y-1", children: [_jsx("label", { htmlFor: "stgm-new-share-name", className: "text-xs font-medium text-foreground", children: "Name" }), _jsx("input", { id: "stgm-new-share-name", type: "text", value: name, onChange: (e) => handleNameChange(e.target.value), disabled: isPending, required: true, maxLength: 63, className: cn("w-full rounded-md border bg-input-bg px-2.5 py-1.5 text-xs text-foreground", "placeholder:text-muted-foreground", "focus:outline-none focus:ring-2 focus:ring-ring", "disabled:pointer-events-none disabled:opacity-50", nameError ? "border-destructive" : "border-border") }), nameError ? (_jsx("p", { className: "text-[0.65rem] text-destructive", role: "alert", children: nameError })) : (_jsx("p", { className: "text-[0.65rem] text-muted-foreground", children: "A display name for this share \u2014 e.g. the site or campaign it serves." }))] }), _jsxs("div", { className: "space-y-1", children: [_jsx("label", { htmlFor: "stgm-new-share-slug", className: "text-xs font-medium text-foreground", children: "Slug" }), _jsx("input", { id: "stgm-new-share-slug", type: "text", value: slug, onChange: (e) => handleSlugChange(e.target.value), disabled: isPending, required: true, className: cn("w-full rounded-md border bg-input-bg px-2.5 py-1.5 font-mono text-xs text-foreground", "placeholder:text-muted-foreground", "focus:outline-none focus:ring-2 focus:ring-ring", "disabled:pointer-events-none disabled:opacity-50", slugError ? "border-destructive" : "border-border") }), slugError ? (_jsx("p", { className: "text-[0.65rem] text-destructive", role: "alert", children: slugError })) : (_jsxs("p", { className: "text-[0.65rem] text-muted-foreground", children: ["Becomes the share's address:", " ", _jsxs("code", { className: "font-mono", children: ["/chat/", shareOrg, "/", slug || "…"] }), ". Can't be changed later."] }))] }), submitError && (_jsx("p", { className: "text-xs text-destructive", role: "alert", children: submitError })), _jsx("div", { className: "flex items-center justify-end", children: _jsx("button", { type: "submit", disabled: !canSubmit, className: cn("rounded-md px-3 py-1.5 text-sm font-medium", "bg-primary text-primary-foreground hover:bg-primary-hover", "focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2", "disabled:pointer-events-none disabled:opacity-50"), children: isPending ? "Creating…" : "Create share" }) })] }));
|
|
118
188
|
}
|
|
119
|
-
|
|
189
|
+
// ---------------------------------------------------------------------------
|
|
190
|
+
// Form — owns the share draft for the session
|
|
191
|
+
// ---------------------------------------------------------------------------
|
|
192
|
+
function ShareAgentForm({ agent, initialShare, buildShareUrl, onSharingChanged, }) {
|
|
120
193
|
const agentName = agent.metadata?.name || (agent.metadata?.slug ?? "");
|
|
121
194
|
// The latest server share is the single baseline: the draft, the link
|
|
122
|
-
// token, and the share id for rotation all derive from it.
|
|
123
|
-
// until the first save creates the share.
|
|
195
|
+
// token, and the share id for rotation all derive from it.
|
|
124
196
|
const [share, setShare] = useState(initialShare);
|
|
125
197
|
const [draft, setDraft] = useState(() => draftFromShare(initialShare));
|
|
126
198
|
const [activeTab, setActiveTab] = useState("link");
|
|
127
|
-
const { save, isPending } = useSaveAgentShare(agent
|
|
128
|
-
const { rotateShareLink, isPending: isRotating } = useRotateShareLink(share
|
|
129
|
-
// The share's own org/slug
|
|
130
|
-
//
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
const org = share?.metadata?.org || shareOrg || (agent.metadata?.org ?? "");
|
|
135
|
-
const slug = share?.metadata?.slug || (agent.metadata?.slug ?? "");
|
|
136
|
-
const linkToken = share?.status?.shareLinkToken ?? "";
|
|
199
|
+
const { save, isPending } = useSaveAgentShare(agent);
|
|
200
|
+
const { rotateShareLink, isPending: isRotating } = useRotateShareLink(share.metadata?.id ?? null);
|
|
201
|
+
// The share's own org/slug are the hosted URL — for a cross-org share
|
|
202
|
+
// (decision 013) that org is the sharing org's, not the agent's.
|
|
203
|
+
const org = share.metadata?.org ?? "";
|
|
204
|
+
const slug = share.metadata?.slug ?? "";
|
|
205
|
+
const linkToken = share.status?.shareLinkToken ?? "";
|
|
137
206
|
// Cross-org shares are public-audience only (decision 013 D3) — the
|
|
138
207
|
// audience selector disappears rather than offering a choice the
|
|
139
208
|
// server would refuse.
|