@arbidocs/blocks 0.5.21 → 0.5.23
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/{ConnectedCallDock-ZWNWGEST.js → ConnectedCallDock-AQ33U57C.js} +7 -7
- package/dist/{ConnectedCallDock-ZWNWGEST.js.map → ConnectedCallDock-AQ33U57C.js.map} +1 -1
- package/dist/{ConnectedCallDock-7FPHYOMU.cjs → ConnectedCallDock-JRWGC6UT.cjs} +8 -8
- package/dist/{ConnectedCallDock-7FPHYOMU.cjs.map → ConnectedCallDock-JRWGC6UT.cjs.map} +1 -1
- package/dist/{ConnectedCallRoom-QAF3ZOEC.js → ConnectedCallRoom-5YNFPS6E.js} +7 -7
- package/dist/{ConnectedCallRoom-QAF3ZOEC.js.map → ConnectedCallRoom-5YNFPS6E.js.map} +1 -1
- package/dist/{ConnectedCallRoom-HSLYF6YL.cjs → ConnectedCallRoom-CCEIJAOG.cjs} +8 -8
- package/dist/{ConnectedCallRoom-HSLYF6YL.cjs.map → ConnectedCallRoom-CCEIJAOG.cjs.map} +1 -1
- package/dist/{ConnectedNativeDocxComparison-4X7H57LE.js → ConnectedNativeDocxComparison-GMQHSY3Z.js} +10 -10
- package/dist/{ConnectedNativeDocxComparison-4X7H57LE.js.map → ConnectedNativeDocxComparison-GMQHSY3Z.js.map} +1 -1
- package/dist/{ConnectedNativeDocxComparison-7WTVHEKI.cjs → ConnectedNativeDocxComparison-HH3PHNXU.cjs} +11 -11
- package/dist/{ConnectedNativeDocxComparison-7WTVHEKI.cjs.map → ConnectedNativeDocxComparison-HH3PHNXU.cjs.map} +1 -1
- package/dist/{ConnectedNativeDocxEditor-I6RQUSR3.js → ConnectedNativeDocxEditor-4IAKVBEF.js} +9 -9
- package/dist/{ConnectedNativeDocxEditor-I6RQUSR3.js.map → ConnectedNativeDocxEditor-4IAKVBEF.js.map} +1 -1
- package/dist/{ConnectedNativeDocxEditor-PZ2ASQO3.cjs → ConnectedNativeDocxEditor-JNHNZG3P.cjs} +11 -11
- package/dist/{ConnectedNativeDocxEditor-PZ2ASQO3.cjs.map → ConnectedNativeDocxEditor-JNHNZG3P.cjs.map} +1 -1
- package/dist/{ConnectedStreamedWordArtifact-Q5KC4W7O.cjs → ConnectedStreamedWordArtifact-CZZOH667.cjs} +11 -11
- package/dist/ConnectedStreamedWordArtifact-CZZOH667.cjs.map +1 -0
- package/dist/{ConnectedStreamedWordArtifact-KCYSJ3B2.js → ConnectedStreamedWordArtifact-GLJCJPTP.js} +10 -10
- package/dist/ConnectedStreamedWordArtifact-GLJCJPTP.js.map +1 -0
- package/dist/agents/index.cjs +328 -328
- package/dist/agents/index.js +6 -6
- package/dist/auth/index.cjs +47 -47
- package/dist/auth/index.js +2 -2
- package/dist/calls/index.cjs +39 -39
- package/dist/calls/index.js +7 -7
- package/dist/chat/index.cjs +145 -145
- package/dist/chat/index.js +4 -4
- package/dist/{chunk-R2HXGTVB.cjs → chunk-2QQUGL2V.cjs} +2 -2
- package/dist/{chunk-R2HXGTVB.cjs.map → chunk-2QQUGL2V.cjs.map} +1 -1
- package/dist/{chunk-DTENNALR.js → chunk-44FPFTU2.js} +6 -6
- package/dist/{chunk-DTENNALR.js.map → chunk-44FPFTU2.js.map} +1 -1
- package/dist/{chunk-MJT7KHHT.cjs → chunk-75UVQKQ5.cjs} +52 -52
- package/dist/{chunk-MJT7KHHT.cjs.map → chunk-75UVQKQ5.cjs.map} +1 -1
- package/dist/{chunk-GK2U3VU6.cjs → chunk-7DDMF3DZ.cjs} +4 -4
- package/dist/{chunk-GK2U3VU6.cjs.map → chunk-7DDMF3DZ.cjs.map} +1 -1
- package/dist/{chunk-JWUUGVQR.js → chunk-7JJ7LU3T.js} +5 -5
- package/dist/{chunk-JWUUGVQR.js.map → chunk-7JJ7LU3T.js.map} +1 -1
- package/dist/{chunk-YT5OOFK3.js → chunk-7S76Q5RK.js} +3 -3
- package/dist/{chunk-YT5OOFK3.js.map → chunk-7S76Q5RK.js.map} +1 -1
- package/dist/{chunk-S5XIMM27.cjs → chunk-7ZHPLTGK.cjs} +9 -9
- package/dist/{chunk-S5XIMM27.cjs.map → chunk-7ZHPLTGK.cjs.map} +1 -1
- package/dist/{chunk-F6LC2CRB.js → chunk-AAVFCPKD.js} +6 -6
- package/dist/{chunk-F6LC2CRB.js.map → chunk-AAVFCPKD.js.map} +1 -1
- package/dist/{chunk-ZMYK7XTS.js → chunk-AF24CV6J.js} +3 -3
- package/dist/{chunk-ZMYK7XTS.js.map → chunk-AF24CV6J.js.map} +1 -1
- package/dist/{chunk-EW2ZGGWH.cjs → chunk-ASTMGLHT.cjs} +7 -7
- package/dist/{chunk-EW2ZGGWH.cjs.map → chunk-ASTMGLHT.cjs.map} +1 -1
- package/dist/{chunk-T4OJYZSY.cjs → chunk-B26FXLMG.cjs} +5 -5
- package/dist/{chunk-T4OJYZSY.cjs.map → chunk-B26FXLMG.cjs.map} +1 -1
- package/dist/{chunk-PFVCOUU6.cjs → chunk-BL74GYSA.cjs} +26 -26
- package/dist/{chunk-PFVCOUU6.cjs.map → chunk-BL74GYSA.cjs.map} +1 -1
- package/dist/{chunk-K237IYOD.cjs → chunk-BYJUI4AT.cjs} +54 -2
- package/dist/chunk-BYJUI4AT.cjs.map +1 -0
- package/dist/{chunk-F7IQGPZH.js → chunk-C6P2QW36.js} +5 -5
- package/dist/{chunk-F7IQGPZH.js.map → chunk-C6P2QW36.js.map} +1 -1
- package/dist/{chunk-KILCORJ7.js → chunk-DHPEUC6H.js} +3 -3
- package/dist/{chunk-KILCORJ7.js.map → chunk-DHPEUC6H.js.map} +1 -1
- package/dist/{chunk-MSPNYW6Z.cjs → chunk-DTLVC6MN.cjs} +2 -53
- package/dist/chunk-DTLVC6MN.cjs.map +1 -0
- package/dist/{chunk-MSCDYRSA.cjs → chunk-DXO2RXVQ.cjs} +4 -4
- package/dist/{chunk-MSCDYRSA.cjs.map → chunk-DXO2RXVQ.cjs.map} +1 -1
- package/dist/{chunk-FOW7TRQR.js → chunk-ENAXJ63V.js} +3 -3
- package/dist/{chunk-FOW7TRQR.js.map → chunk-ENAXJ63V.js.map} +1 -1
- package/dist/{chunk-MCU4HJDM.cjs → chunk-EWWVKXEQ.cjs} +4 -4
- package/dist/{chunk-MCU4HJDM.cjs.map → chunk-EWWVKXEQ.cjs.map} +1 -1
- package/dist/{chunk-UEDM2NNI.cjs → chunk-FCWS7I5C.cjs} +9 -9
- package/dist/{chunk-UEDM2NNI.cjs.map → chunk-FCWS7I5C.cjs.map} +1 -1
- package/dist/{chunk-525U3M3N.js → chunk-FUOCCKE4.js} +3 -3
- package/dist/{chunk-525U3M3N.js.map → chunk-FUOCCKE4.js.map} +1 -1
- package/dist/{chunk-BQQTLZBN.js → chunk-GRT4EH76.js} +2 -2
- package/dist/{chunk-BQQTLZBN.js.map → chunk-GRT4EH76.js.map} +1 -1
- package/dist/{chunk-YRHQ7OLG.cjs → chunk-I5RK4WAE.cjs} +8 -8
- package/dist/{chunk-YRHQ7OLG.cjs.map → chunk-I5RK4WAE.cjs.map} +1 -1
- package/dist/{chunk-YFLXVKMR.js → chunk-IKTPM73F.js} +4 -4
- package/dist/{chunk-YFLXVKMR.js.map → chunk-IKTPM73F.js.map} +1 -1
- package/dist/{chunk-YQJOWQDJ.cjs → chunk-IWT4QVQL.cjs} +4 -4
- package/dist/{chunk-YQJOWQDJ.cjs.map → chunk-IWT4QVQL.cjs.map} +1 -1
- package/dist/{chunk-5ZU2XYXO.cjs → chunk-KJVDYWAM.cjs} +30 -4
- package/dist/chunk-KJVDYWAM.cjs.map +1 -0
- package/dist/{chunk-CQU37FNV.cjs → chunk-KKT53TZQ.cjs} +5 -5
- package/dist/{chunk-CQU37FNV.cjs.map → chunk-KKT53TZQ.cjs.map} +1 -1
- package/dist/{chunk-RJY5NX72.cjs → chunk-KXSXIQSW.cjs} +12 -12
- package/dist/{chunk-RJY5NX72.cjs.map → chunk-KXSXIQSW.cjs.map} +1 -1
- package/dist/{chunk-SPSODKUF.js → chunk-M4FLTGFM.js} +5 -5
- package/dist/{chunk-SPSODKUF.js.map → chunk-M4FLTGFM.js.map} +1 -1
- package/dist/{chunk-K35WQH42.js → chunk-MD2XJASR.js} +3 -3
- package/dist/{chunk-K35WQH42.js.map → chunk-MD2XJASR.js.map} +1 -1
- package/dist/{chunk-KMF3ORIV.js → chunk-MQEN62NR.js} +3 -3
- package/dist/{chunk-KMF3ORIV.js.map → chunk-MQEN62NR.js.map} +1 -1
- package/dist/{chunk-J5J5JRPL.js → chunk-MUF3RFJZ.js} +4 -4
- package/dist/{chunk-J5J5JRPL.js.map → chunk-MUF3RFJZ.js.map} +1 -1
- package/dist/{chunk-K4PGCNCI.cjs → chunk-O4TCX6PD.cjs} +5 -5
- package/dist/{chunk-K4PGCNCI.cjs.map → chunk-O4TCX6PD.cjs.map} +1 -1
- package/dist/{chunk-KL6XOSEN.js → chunk-PLAGIVFF.js} +4 -52
- package/dist/chunk-PLAGIVFF.js.map +1 -0
- package/dist/{chunk-D3BHUDOU.js → chunk-PZRTRYPD.js} +3 -3
- package/dist/{chunk-D3BHUDOU.js.map → chunk-PZRTRYPD.js.map} +1 -1
- package/dist/{chunk-4C2S3Z3I.cjs → chunk-QW3SVHGM.cjs} +4 -4
- package/dist/{chunk-4C2S3Z3I.cjs.map → chunk-QW3SVHGM.cjs.map} +1 -1
- package/dist/{chunk-F4AJTY45.cjs → chunk-R7M5LN7D.cjs} +4 -4
- package/dist/{chunk-F4AJTY45.cjs.map → chunk-R7M5LN7D.cjs.map} +1 -1
- package/dist/{chunk-UNZUM76L.js → chunk-RRIXIUYD.js} +3 -3
- package/dist/{chunk-UNZUM76L.js.map → chunk-RRIXIUYD.js.map} +1 -1
- package/dist/{chunk-FQIJICZE.cjs → chunk-S4G3DNMA.cjs} +18 -18
- package/dist/{chunk-FQIJICZE.cjs.map → chunk-S4G3DNMA.cjs.map} +1 -1
- package/dist/{chunk-ML62FUHZ.js → chunk-SUDPZ5IQ.js} +3 -3
- package/dist/{chunk-ML62FUHZ.js.map → chunk-SUDPZ5IQ.js.map} +1 -1
- package/dist/{chunk-I3G7DQJH.cjs → chunk-T3VDKPKH.cjs} +18 -18
- package/dist/{chunk-I3G7DQJH.cjs.map → chunk-T3VDKPKH.cjs.map} +1 -1
- package/dist/{chunk-G2XAACRG.cjs → chunk-TATPWHHN.cjs} +5 -5
- package/dist/{chunk-G2XAACRG.cjs.map → chunk-TATPWHHN.cjs.map} +1 -1
- package/dist/{chunk-IJQ5DIZT.cjs → chunk-TTJGCJWX.cjs} +5 -5
- package/dist/{chunk-IJQ5DIZT.cjs.map → chunk-TTJGCJWX.cjs.map} +1 -1
- package/dist/{chunk-WYUFBKQ4.js → chunk-V5HVPQP7.js} +3 -3
- package/dist/{chunk-WYUFBKQ4.js.map → chunk-V5HVPQP7.js.map} +1 -1
- package/dist/{chunk-IXBJEQH5.js → chunk-VN4FSGBR.js} +53 -4
- package/dist/chunk-VN4FSGBR.js.map +1 -0
- package/dist/{chunk-BITGO5LI.cjs → chunk-VNHLFS6T.cjs} +4 -4
- package/dist/{chunk-BITGO5LI.cjs.map → chunk-VNHLFS6T.cjs.map} +1 -1
- package/dist/{chunk-CHHE2UNJ.js → chunk-WNC5INOD.js} +4 -4
- package/dist/{chunk-CHHE2UNJ.js.map → chunk-WNC5INOD.js.map} +1 -1
- package/dist/{chunk-6EGWPMPU.cjs → chunk-WPOQLGKJ.cjs} +14 -14
- package/dist/{chunk-6EGWPMPU.cjs.map → chunk-WPOQLGKJ.cjs.map} +1 -1
- package/dist/{chunk-FERNQVSH.js → chunk-X4Y7ZHFB.js} +30 -5
- package/dist/chunk-X4Y7ZHFB.js.map +1 -0
- package/dist/{chunk-UAFP562F.js → chunk-XL55UDLO.js} +3 -3
- package/dist/{chunk-UAFP562F.js.map → chunk-XL55UDLO.js.map} +1 -1
- package/dist/{chunk-P3HSWP2P.js → chunk-XVGUR746.js} +3 -3
- package/dist/{chunk-P3HSWP2P.js.map → chunk-XVGUR746.js.map} +1 -1
- package/dist/{chunk-YVA6SCVO.js → chunk-Y5ER2GAU.js} +3 -3
- package/dist/{chunk-YVA6SCVO.js.map → chunk-Y5ER2GAU.js.map} +1 -1
- package/dist/{chunk-O3TAF4ZM.js → chunk-Y7DWW5XD.js} +3 -3
- package/dist/{chunk-O3TAF4ZM.js.map → chunk-Y7DWW5XD.js.map} +1 -1
- package/dist/{chunk-APVKLXM5.cjs → chunk-YBTKLOGG.cjs} +4 -4
- package/dist/{chunk-APVKLXM5.cjs.map → chunk-YBTKLOGG.cjs.map} +1 -1
- package/dist/{chunk-YVEMNMIA.cjs → chunk-YOMT5FFH.cjs} +6 -6
- package/dist/{chunk-YVEMNMIA.cjs.map → chunk-YOMT5FFH.cjs.map} +1 -1
- package/dist/{chunk-VFZLZSJ3.js → chunk-ZYGQFD5Y.js} +3 -3
- package/dist/{chunk-VFZLZSJ3.js.map → chunk-ZYGQFD5Y.js.map} +1 -1
- package/dist/citations/index.cjs +10 -10
- package/dist/citations/index.js +2 -2
- package/dist/connect/docx.cjs +13 -13
- package/dist/connect/docx.js +9 -9
- package/dist/connect/index.cjs +1393 -866
- package/dist/connect/index.cjs.map +1 -1
- package/dist/connect/index.d.ts +1 -0
- package/dist/connect/index.js +575 -57
- package/dist/connect/index.js.map +1 -1
- package/dist/connect/viewer.cjs +77 -77
- package/dist/connect/viewer.js +12 -12
- package/dist/connection/auth/support.d.ts +17 -0
- package/dist/connection/auth/useLoginActions.d.ts +5 -0
- package/dist/connection/billing/ConnectedQuotaDialog.d.ts +5 -13
- package/dist/connection/billing/ProjectUsageContent.d.ts +7 -4
- package/dist/connection/billing/index.d.ts +2 -1
- package/dist/connection/connectors/ConnectedSharePointAdminConsentPage.d.ts +26 -0
- package/dist/connection/connectors/index.d.ts +1 -0
- package/dist/connection/defaultHost.d.ts +1 -1
- package/dist/connection/entities/ConnectedProjectEntity.d.ts +8 -0
- package/dist/connection/entities/ConnectedUserEntity.d.ts +20 -0
- package/dist/connection/entities/ConnectedWorkspaceEntity.d.ts +31 -0
- package/dist/connection/entities/index.d.ts +5 -0
- package/dist/connection/entities/renderConnectedUser.d.ts +6 -0
- package/dist/connection/settings-page/ConnectedAccountSettings.d.ts +2 -1
- package/dist/connection/settings-page/ConnectedBoxPortalSection.d.ts +6 -0
- package/dist/connection/settings-page/index.d.ts +1 -0
- package/dist/connection/settings-page/sections.d.ts +44 -0
- package/dist/facts/index.cjs +3 -3
- package/dist/facts/index.js +2 -2
- package/dist/files/index.cjs +223 -223
- package/dist/files/index.js +3 -3
- package/dist/home/index.cjs +30 -30
- package/dist/home/index.js +5 -5
- package/dist/index.cjs +643 -643
- package/dist/index.js +18 -18
- package/dist/provider/environment.d.ts +2 -0
- package/dist/retrieval/index.cjs +4 -4
- package/dist/retrieval/index.js +2 -2
- package/dist/shell/index.cjs +46 -46
- package/dist/shell/index.js +3 -3
- package/dist/studio/index.cjs +14 -14
- package/dist/studio/index.js +6 -6
- package/dist/workflow-canvas/index.cjs +26 -26
- package/dist/workflow-canvas/index.js +8 -8
- package/dist/workspaces/WorkspaceTypeBadge.d.ts +14 -0
- package/dist/workspaces/index.cjs +32 -28
- package/dist/workspaces/index.d.ts +1 -0
- package/dist/workspaces/index.js +4 -4
- package/node_modules/@arbidocs/coedit/dist/encoding.cjs +54 -56
- package/node_modules/@arbidocs/coedit/dist/encoding.cjs.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/encoding.d.cts +50 -14
- package/node_modules/@arbidocs/coedit/dist/encoding.d.ts +50 -14
- package/node_modules/@arbidocs/coedit/dist/encoding.js +54 -57
- package/node_modules/@arbidocs/coedit/dist/encoding.js.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/hocuspocus.cjs +211 -109
- package/node_modules/@arbidocs/coedit/dist/hocuspocus.cjs.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/hocuspocus.js +211 -109
- package/node_modules/@arbidocs/coedit/dist/hocuspocus.js.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/index.cjs +210 -108
- package/node_modules/@arbidocs/coedit/dist/index.cjs.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/index.d.cts +1 -1
- package/node_modules/@arbidocs/coedit/dist/index.d.ts +1 -1
- package/node_modules/@arbidocs/coedit/dist/index.js +210 -108
- package/node_modules/@arbidocs/coedit/dist/index.js.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/server.cjs +214 -112
- package/node_modules/@arbidocs/coedit/dist/server.cjs.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/server.d.cts +1 -1
- package/node_modules/@arbidocs/coedit/dist/server.d.ts +1 -1
- package/node_modules/@arbidocs/coedit/dist/server.js +214 -112
- package/node_modules/@arbidocs/coedit/dist/server.js.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/template.cjs +3 -2
- package/node_modules/@arbidocs/coedit/dist/template.cjs.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/template.d.cts +5 -0
- package/node_modules/@arbidocs/coedit/dist/template.d.ts +5 -0
- package/node_modules/@arbidocs/coedit/dist/template.js +3 -2
- package/node_modules/@arbidocs/coedit/dist/template.js.map +1 -1
- package/node_modules/@arbidocs/coedit/dist/{versions-DXiFQMA6.d.ts → versions-XSYTVmOU.d.cts} +1 -1
- package/node_modules/@arbidocs/coedit/dist/{versions-DXiFQMA6.d.cts → versions-XSYTVmOU.d.ts} +1 -1
- package/node_modules/@arbidocs/coedit/package.json +1 -1
- package/package.json +5 -5
- package/dist/ConnectedStreamedWordArtifact-KCYSJ3B2.js.map +0 -1
- package/dist/ConnectedStreamedWordArtifact-Q5KC4W7O.cjs.map +0 -1
- package/dist/chunk-5ZU2XYXO.cjs.map +0 -1
- package/dist/chunk-FERNQVSH.js.map +0 -1
- package/dist/chunk-IXBJEQH5.js.map +0 -1
- package/dist/chunk-K237IYOD.cjs.map +0 -1
- package/dist/chunk-KL6XOSEN.js.map +0 -1
- package/dist/chunk-MSPNYW6Z.cjs.map +0 -1
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
'use strict';
|
|
3
3
|
|
|
4
|
-
var
|
|
5
|
-
var
|
|
4
|
+
var chunkB26FXLMG_cjs = require('./chunk-B26FXLMG.cjs');
|
|
5
|
+
var chunkIWT4QVQL_cjs = require('./chunk-IWT4QVQL.cjs');
|
|
6
6
|
var chunkMB3S2ETI_cjs = require('./chunk-MB3S2ETI.cjs');
|
|
7
7
|
var chunkZ2XZ2D4N_cjs = require('./chunk-Z2XZ2D4N.cjs');
|
|
8
8
|
var chunkCQ2YSHIF_cjs = require('./chunk-CQ2YSHIF.cjs');
|
|
9
|
-
var
|
|
9
|
+
var chunk2QQUGL2V_cjs = require('./chunk-2QQUGL2V.cjs');
|
|
10
10
|
var React = require('react');
|
|
11
11
|
var jsxRuntime = require('react/jsx-runtime');
|
|
12
12
|
var react = require('@arbidocs/react');
|
|
@@ -138,7 +138,7 @@ function WorkspaceDocumentReference({
|
|
|
138
138
|
children,
|
|
139
139
|
className = "inline-flex rounded-full border px-2 py-0.5 text-xs hover:bg-muted"
|
|
140
140
|
}) {
|
|
141
|
-
const { openDocument } =
|
|
141
|
+
const { openDocument } = chunk2QQUGL2V_cjs.useBlocksEnvironment();
|
|
142
142
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
143
143
|
"button",
|
|
144
144
|
{
|
|
@@ -165,19 +165,19 @@ function MentionLink({ kind, id, text }) {
|
|
|
165
165
|
);
|
|
166
166
|
}
|
|
167
167
|
function ExternalLink({ href, children }) {
|
|
168
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
168
|
+
return /* @__PURE__ */ jsxRuntime.jsx(chunkB26FXLMG_cjs.QuietLink, { href, kind: "external", children });
|
|
169
169
|
}
|
|
170
170
|
function InternalDocLink({
|
|
171
171
|
docId,
|
|
172
172
|
href,
|
|
173
173
|
children
|
|
174
174
|
}) {
|
|
175
|
-
const { openDocument } =
|
|
175
|
+
const { openDocument } = chunk2QQUGL2V_cjs.useBlocksEnvironment();
|
|
176
176
|
const workspaceId = useDocumentWorkspace();
|
|
177
177
|
if (workspaceId) {
|
|
178
178
|
return /* @__PURE__ */ jsxRuntime.jsx(WorkspaceDocumentReference, { workspaceId, docId, children });
|
|
179
179
|
}
|
|
180
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
180
|
+
return /* @__PURE__ */ jsxRuntime.jsx(chunkB26FXLMG_cjs.QuietLink, { href, kind: "document", onOpen: () => openDocument(docId), children });
|
|
181
181
|
}
|
|
182
182
|
function DocumentChip({ docId }) {
|
|
183
183
|
const render = react.useArbiHost().chat?.renderDocumentChip;
|
|
@@ -187,7 +187,7 @@ function DocumentChip({ docId }) {
|
|
|
187
187
|
}
|
|
188
188
|
function DefaultDocumentChip({ docId }) {
|
|
189
189
|
const { data: doc } = react.useDocument(docId);
|
|
190
|
-
const { openDocument } =
|
|
190
|
+
const { openDocument } = chunk2QQUGL2V_cjs.useBlocksEnvironment();
|
|
191
191
|
if (!doc)
|
|
192
192
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
193
193
|
ui.EntityPill,
|
|
@@ -220,13 +220,13 @@ var conversationMarkdownComponents = {
|
|
|
220
220
|
children,
|
|
221
221
|
...props
|
|
222
222
|
}) {
|
|
223
|
-
const deploymentDomain =
|
|
223
|
+
const deploymentDomain = chunk2QQUGL2V_cjs.useBlocksEnvironment().runtimeConfig.deploymentDomain;
|
|
224
224
|
const mention = shell.mentionFromHref(href);
|
|
225
225
|
if (mention) {
|
|
226
226
|
return /* @__PURE__ */ jsxRuntime.jsx(MentionLink, { kind: mention.kind, id: mention.id, text: childrenText(children) });
|
|
227
227
|
}
|
|
228
228
|
if (href?.startsWith("#") && !href.startsWith("#cite-")) {
|
|
229
|
-
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
229
|
+
return /* @__PURE__ */ jsxRuntime.jsx(chunkB26FXLMG_cjs.QuietLink, { href, kind: "anchor", children });
|
|
230
230
|
}
|
|
231
231
|
if (!href || href.startsWith("#") || href.startsWith("cite:")) {
|
|
232
232
|
return /* @__PURE__ */ jsxRuntime.jsx(ui.MarkdownLink, { href, ...props, children });
|
|
@@ -277,8 +277,8 @@ function OwnDocumentTools({ children }) {
|
|
|
277
277
|
const arbi = react.useArbi();
|
|
278
278
|
const queryClient = reactQuery.useQueryClient();
|
|
279
279
|
const host = chunkMB3S2ETI_cjs.useHost().documentTools;
|
|
280
|
-
const { user, ensureWorkspaceOpen } =
|
|
281
|
-
const { notify: environmentNotify, openDocument: openInHost } =
|
|
280
|
+
const { user, ensureWorkspaceOpen } = chunkIWT4QVQL_cjs.useConnectedWorkspace();
|
|
281
|
+
const { notify: environmentNotify, openDocument: openInHost } = chunk2QQUGL2V_cjs.useBlocksEnvironment();
|
|
282
282
|
const useEmailDocument = host?.useEmailDocument ?? NO_EMAIL;
|
|
283
283
|
const emailDocument = useEmailDocument();
|
|
284
284
|
const client = host?.client ?? (arbi.isLoggedIn ? arbi.getClient().fetch : null);
|
|
@@ -372,5 +372,5 @@ exports.useViewerDraftDocument = useViewerDraftDocument;
|
|
|
372
372
|
exports.useViewerIsDetached = useViewerIsDetached;
|
|
373
373
|
exports.useViewerPassageCitation = useViewerPassageCitation;
|
|
374
374
|
exports.useViewerStreamingDocument = useViewerStreamingDocument;
|
|
375
|
-
//# sourceMappingURL=chunk-
|
|
376
|
-
//# sourceMappingURL=chunk-
|
|
375
|
+
//# sourceMappingURL=chunk-WPOQLGKJ.cjs.map
|
|
376
|
+
//# sourceMappingURL=chunk-WPOQLGKJ.cjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/chat/mermaid-normalize.ts","../src/connection/conversation/MermaidDiagram.tsx","../src/connection/conversation/DocumentWorkspaceContext.tsx","../src/connection/conversation/ConnectedMarkdown.tsx","../src/connection/viewer/ConnectedDocumentToolsProvider.tsx","../src/connection/viewer/support.ts"],"names":["useState","useId","useEffect","jsxs","jsx","createContext","useContext","useBlocksEnvironment","React","useArbiSession","MentionChip","QuietLink","useArbiHost","Fragment","useDocument","EntityPill","FileText","DocumentEntity","Mail","mentionFromHref","MarkdownLink","workspaceDocIdFromHref","MarkdownStreamingContext","MarkdownCode","rehypeDocEntityPills","useMemo","KitMarkdownRenderer","useOptionalDocumentTools","useArbi","useQueryClient","useHost","useConnectedWorkspace","useCallback","refreshDocuments","arbiQueryKeys","documentBytesKey","clientUpload","DocumentToolsProvider"],"mappings":"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","file":"chunk-6EGWPMPU.cjs","sourcesContent":["/**\n * Defensive normalizer for single-line `graph` / `flowchart` Mermaid source.\n *\n * Some LLMs emit the entire diagram on one line. Mermaid's parser splits\n * statements on newlines, so a single-line graph fails outright. This helper\n * inserts newlines on safe statement boundaries so the diagram has a chance\n * of parsing. Only attempts normalization when:\n * 1. The source has no embedded newlines (i.e. is genuinely single-line), and\n * 2. The first directive is `graph` or `flowchart`.\n *\n * Other diagram types (sequenceDiagram, classDiagram, gantt, …) have very\n * different syntaxes — applying these heuristics to them would corrupt valid\n * input, so they're left untouched.\n *\n * Boundaries we split on:\n * - After the diagram-type header (`graph TD`, `flowchart LR`, …).\n * - Before each `style` / `classDef` / `class` / `linkStyle` / `click`\n * / `subgraph` keyword.\n * - Before/after `end` (closes a subgraph block).\n * - After a `]` (label close) that's followed by another node identifier\n * starting a new edge or node declaration.\n */\nexport function normalizeMermaidGraph(source: string): string {\n // Already multi-line — assume it's well-formed; don't touch it.\n if (/\\n/.test(source)) return source\n\n const headerMatch = source.match(/^\\s*(graph|flowchart)\\s+\\w+\\s+/)\n if (!headerMatch) return source\n\n const header = headerMatch[0].trimEnd()\n let body = source.slice(headerMatch[0].length)\n\n // Insert newline before keywords that always start a new statement.\n body = body.replace(/\\s+(style|classDef|class|linkStyle|click|subgraph)\\s/g, '\\n$1 ')\n\n // `end` closes a subgraph: put it on its own line, with a break after it\n // too so any trailing statements don't stay attached.\n body = body.replace(/\\s+end\\b\\s*/g, '\\nend\\n')\n\n // After a label close (`]`), if the next token looks like a Mermaid node id\n // followed by another `[` or `-->`, that's a new statement starting.\n body = body.replace(/\\]\\s+(?=[A-Za-z_][\\w-]*\\s*(?:\\[|-->))/g, ']\\n')\n\n // Collapse any accidental runs of blank lines we may have produced.\n body = body.replace(/\\n{2,}/g, '\\n')\n\n return `${header}\\n${body.trimStart()}`\n}\n","/**\n * MermaidDiagram Component\n *\n * Renders a Mermaid diagram from source code.\n * Used inside MarkdownRenderer to handle ```mermaid code blocks.\n * Lazy-loads the mermaid library to avoid bloating the initial bundle.\n */\n\nimport { useState, useEffect, useId } from 'react'\nimport { normalizeMermaidGraph } from '../../chat/mermaid-normalize'\n\ninterface MermaidDiagramProps {\n /** Mermaid diagram source code */\n chart: string\n}\n\n// Lazy-load and initialize mermaid once\nlet mermaidInstance: typeof import('mermaid').default | null = null\nlet mermaidLoadPromise: Promise<typeof import('mermaid').default> | null = null\n\nasync function getMermaid() {\n if (mermaidInstance) return mermaidInstance\n if (!mermaidLoadPromise) {\n mermaidLoadPromise = import('mermaid').then((mod) => {\n const m = mod.default\n m.initialize({\n startOnLoad: false,\n theme: 'default',\n securityLevel: 'strict',\n flowchart: { useMaxWidth: true, curve: 'basis' },\n })\n mermaidInstance = m\n return m\n })\n }\n return mermaidLoadPromise\n}\n\nexport function MermaidDiagram({ chart }: MermaidDiagramProps) {\n const [svg, setSvg] = useState<string | null>(null)\n const [error, setError] = useState<string | null>(null)\n const uniqueId = useId().replace(/:/g, '-')\n\n useEffect(() => {\n let cancelled = false\n\n async function render() {\n const mermaid = await getMermaid()\n const diagramId = `mermaid${uniqueId}`\n\n // Validate with parse() before render(). In Mermaid v11 a render() with\n // bad source can return a \"Syntax error in text\" bomb SVG instead of\n // throwing — and it appends DOM side-effects of its own — so a try/catch\n // around render() doesn't reliably catch failures and the bomb leaks\n // into the page (especially under React StrictMode where effects run\n // twice). parse() throws cleanly with no DOM side-effects.\n //\n // Defensive rescue: some LLMs emit single-line `graph`/`flowchart`\n // source. If the original parse fails, try a normalized variant. The\n // normalizer is a no-op on already-multi-line source and on non-graph\n // diagram types, so this only helps the bad-source case and never\n // corrupts valid input.\n let validSource: string | null = null\n let firstErr: unknown\n try {\n await mermaid.parse(chart)\n validSource = chart\n } catch (err) {\n firstErr = err\n const normalized = normalizeMermaidGraph(chart)\n if (normalized !== chart) {\n try {\n await mermaid.parse(normalized)\n validSource = normalized\n } catch (retryErr) {\n console.warn('Mermaid normalized parse also failed', retryErr)\n }\n }\n }\n\n if (cancelled) return\n\n if (!validSource) {\n console.warn('Mermaid parse failed, showing source', firstErr)\n setError('Failed to render diagram')\n setSvg(null)\n return\n }\n\n try {\n const { svg: renderedSvg } = await mermaid.render(diagramId, validSource)\n if (!cancelled) {\n setSvg(renderedSvg)\n setError(null)\n }\n } catch (renderErr) {\n if (!cancelled) {\n console.warn('Mermaid render failed despite parse success', renderErr)\n setError('Failed to render diagram')\n setSvg(null)\n }\n }\n }\n\n render()\n return () => {\n cancelled = true\n }\n }, [chart, uniqueId])\n\n if (error) {\n // Fall back to showing the raw source in a code block\n return (\n <div className=\"code-block\" data-testid=\"mermaid-error\">\n <div className=\"text-sm text-muted-foreground mb-1\">{error}</div>\n <code className=\"language-mermaid\">{chart}</code>\n </div>\n )\n }\n\n if (!svg) {\n return (\n <div\n className=\"flex items-center justify-center py-8 text-muted-foreground text-sm\"\n data-testid=\"mermaid-loading\"\n >\n Rendering diagram...\n </div>\n )\n }\n\n return (\n <div\n className=\"mermaid-diagram my-4 overflow-x-auto rounded-md border border-border bg-background p-4\"\n data-testid=\"mermaid-diagram\"\n dangerouslySetInnerHTML={{ __html: svg }}\n />\n )\n}\n","/**\n * The workspace a conversation's document references belong to, when it is not the open one: an\n * agent's direct-message thread runs in the agent's workspace, so the documents it names are there.\n * A reference then opens that workspace first (`openDocument(id, { workspaceId })`).\n */\n\nimport { createContext, useContext, type ReactNode } from 'react'\nimport { useBlocksEnvironment } from '../../provider/environment'\n\n/** The workspace of the documents referenced inside it (null: the open workspace). */\nexport const DocumentWorkspaceContext = createContext<string | null>(null)\nexport const useDocumentWorkspace = () => useContext(DocumentWorkspaceContext)\n\n/** A reference to a document of another workspace: opening it opens that workspace first. */\nexport function WorkspaceDocumentReference({\n workspaceId,\n docId,\n children,\n className = 'inline-flex rounded-full border px-2 py-0.5 text-xs hover:bg-muted',\n}: {\n workspaceId: string\n docId: string\n children?: ReactNode\n className?: string\n}) {\n const { openDocument } = useBlocksEnvironment()\n return (\n <button\n type=\"button\"\n className={className}\n onClick={() => openDocument(docId, { workspaceId })}\n >\n {children ?? docId}\n </button>\n )\n}\n","/**\n * The conversation's markdown: the kit's `MarkdownRenderer` (`@arbidocs/react`: sanitised HTML,\n * slugs, lazy KaTeX, streaming blocks, tables, code) with what a conversation adds: @mention chips,\n * workspace documents opening in the viewer, quiet external links, document and email pills (the\n * host's chips, `ArbiChatHost.renderDocumentChip` / `renderMailChip`) and Mermaid diagrams.\n */\nimport { useArbiHost, useArbiSession, useDocument } from '@arbidocs/react'\nimport { mentionFromHref, type MentionKind } from '@arbidocs/react/shell'\nimport {\n EntityPill,\n MarkdownCode,\n MarkdownLink,\n MarkdownRenderer as KitMarkdownRenderer,\n MarkdownStreamingContext,\n type MarkdownRendererProps as KitMarkdownRendererProps,\n DocumentEntity,\n} from '@arbidocs/react/ui'\nimport React, { useContext, useMemo } from 'react'\nimport { FileText, Mail } from 'lucide-react'\n\n/** The markdown element overrides, as the kit's renderer takes them. */\ntype Components = NonNullable<KitMarkdownRendererProps['components']>\nimport { MentionChip } from '../../chat/MentionMenu'\nimport { QuietLink } from '../../citations/QuietMarks'\nimport { rehypeDocEntityPills } from '../../chat/rehype-doc-entity-pills'\nimport { workspaceDocIdFromHref } from '../../chat/doc-links'\nimport { useBlocksEnvironment } from '../../provider/environment'\nimport { MermaidDiagram } from './MermaidDiagram'\nimport { useDocumentWorkspace, WorkspaceDocumentReference } from './DocumentWorkspaceContext'\n\n/** Plain text of a link's children (the `@Label` of a mention link). */\nfunction childrenText(children: React.ReactNode): string {\n return React.Children.toArray(children)\n .map((child) => (typeof child === 'string' || typeof child === 'number' ? String(child) : ''))\n .join('')\n}\n\n/** A mention chip; a mention of the reader stands out. */\nfunction MentionLink({ kind, id, text }: { kind: MentionKind; id: string; text: string }) {\n const currentUserId = useArbiSession().user?.external_id\n return (\n <MentionChip\n kind={kind}\n id={id}\n label={text.replace(/^@/, '')}\n isSelf={kind === 'user' && id === currentUserId}\n />\n )\n}\n\n/**\n * A link to elsewhere, as quiet text. Its menu (Open link / Copy link) is the deliberate step\n * the old confirmation dialog used to be; nothing opens until the menu's primary row is chosen.\n */\nexport function ExternalLink({ href, children }: React.ComponentPropsWithoutRef<'a'>) {\n return (\n <QuietLink href={href} kind=\"external\">\n {children}\n </QuietLink>\n )\n}\n\n/**\n * A workspace document referenced by a link's href rather than by its text.\n *\n * `rehypeDocEntityPills` turns a bare `doc-…` id into a pill, but it only walks\n * TEXT nodes — so `[NVDA DCF Valuation Report](…doc-abc12345…)`, which is how an\n * answer links an artifact it just saved, keeps the id in the href where the\n * plugin never looks. The link then fell through to `ExternalLink`, and opening\n * your own workspace document asked you to confirm an \"external link\" and\n * launched a new tab. It opens in the document viewer, like the pill and the\n * artifact card already do.\n */\nexport function InternalDocLink({\n docId,\n href,\n children,\n}: React.ComponentPropsWithoutRef<'a'> & { docId: string }) {\n const { openDocument } = useBlocksEnvironment()\n const workspaceId = useDocumentWorkspace()\n if (workspaceId) {\n return (\n <WorkspaceDocumentReference workspaceId={workspaceId} docId={docId}>\n {children}\n </WorkspaceDocumentReference>\n )\n }\n\n return (\n <QuietLink href={href} kind=\"document\" onOpen={() => openDocument(docId)}>\n {children}\n </QuietLink>\n )\n}\n\n/** A document of the workspace, as a pill: the host's chip, else the document entity. */\nexport function DocumentChip({ docId }: { docId: string }) {\n const render = useArbiHost().chat?.renderDocumentChip\n const workspaceId = useDocumentWorkspace()\n if (workspaceId) return <WorkspaceDocumentReference workspaceId={workspaceId} docId={docId} />\n return render ? <>{render(docId)}</> : <DefaultDocumentChip docId={docId} />\n}\n\nfunction DefaultDocumentChip({ docId }: { docId: string }) {\n const { data: doc } = useDocument(docId)\n const { openDocument } = useBlocksEnvironment()\n if (!doc)\n return (\n <EntityPill\n icon={<FileText className=\"w-3.5 h-3.5 flex-shrink-0\" />}\n label={docId}\n size=\"sm\"\n onClick={() => openDocument(docId)}\n data-testid=\"doc-entity-pill\"\n />\n )\n return (\n <DocumentEntity doc={doc} onClick={() => openDocument(docId)} data-testid=\"doc-entity-pill\" />\n )\n}\n\n/** An email of the person's mailbox, as a pill: the host's chip, else a plain \"Email\". */\nexport function MailChip({ mailId }: { mailId: string }) {\n const render = useArbiHost().chat?.renderMailChip\n if (render) return <>{render(mailId)}</>\n return (\n <EntityPill\n icon={<Mail className=\"w-3.5 h-3.5 flex-shrink-0\" />}\n label=\"Email\"\n size=\"sm\"\n data-testid=\"mail-entity-pill\"\n />\n )\n}\n\n/**\n * The conversation's overrides, layered on the kit's defaults. Module scope, so the reference is stable\n * and memoised markdown blocks do not re-parse.\n */\nconst conversationMarkdownComponents: Partial<Components> = {\n a: function ConversationMarkdownLink({\n href,\n children,\n ...props\n }: React.ComponentPropsWithoutRef<'a'>) {\n const deploymentDomain = useBlocksEnvironment().runtimeConfig.deploymentDomain\n // @mentions: `linkMentions` turned them into `#mention-<id>` links; draw them as chips.\n const mention = mentionFromHref(href)\n if (mention) {\n return <MentionLink kind={mention.kind} id={mention.id} text={childrenText(children)} />\n }\n // Bookmarks: in-page anchors are near-invisible text; the menu jumps or copies the place.\n if (href?.startsWith('#') && !href.startsWith('#cite-')) {\n return (\n <QuietLink href={href} kind=\"anchor\">\n {children}\n </QuietLink>\n )\n }\n // Citations, `cite:` references and bare links: the kit's link.\n if (!href || href.startsWith('#') || href.startsWith('cite:')) {\n return (\n <MarkdownLink href={href} {...props}>\n {children}\n </MarkdownLink>\n )\n }\n // A workspace document is not an external link, wherever it is hosted: it opens in the viewer.\n const docId = workspaceDocIdFromHref(href, deploymentDomain)\n if (docId) {\n return (\n <InternalDocLink docId={docId} href={href} {...props}>\n {children}\n </InternalDocLink>\n )\n }\n return (\n <ExternalLink href={href} {...props}>\n {children}\n </ExternalLink>\n )\n },\n code: function ConversationMarkdownCode(\n props: React.ComponentPropsWithoutRef<'code'> & { inline?: boolean }\n ) {\n const isStreaming = useContext(MarkdownStreamingContext)\n const { className, children } = props\n const language = /language-(\\w+)/.exec(className || '')?.[1]\n if (!language) {\n // Answers often backtick a bare doc id (`doc-f7b3eeb5`). The text-node pass skips code, so\n // the id would stay monospace text; show it as the document pill. Only a whole id (eight\n // alphanumerics): while streaming, a partial one (\"doc-e\") would be looked up and 404.\n const codeText = typeof children === 'string' ? children.trim() : ''\n if (/^doc-[a-zA-Z0-9]{8}$/.test(codeText)) return <DocumentChip docId={codeText} />\n if (/^eml-[a-zA-Z0-9]{8}$/.test(codeText)) return <MailChip mailId={codeText} />\n }\n // Mermaid lazy-loads its own bundle and re-renders SVG on every change. While streaming the\n // fence is almost always partial, so it stays a code block until generation completes.\n if (language === 'mermaid' && !isStreaming) {\n return <MermaidDiagram chart={String(children).replace(/\\n$/, '')} />\n }\n return <MarkdownCode {...props} />\n },\n span: ({ children, className, ...props }: React.ComponentPropsWithoutRef<'span'>) => {\n const docId = (props as Record<string, unknown>)['data-doc-id'] as string | undefined\n if (docId) return <DocumentChip docId={docId} />\n const mailId = (props as Record<string, unknown>)['data-mail-id'] as string | undefined\n if (mailId) return <MailChip mailId={mailId} />\n return (\n <span className={className} {...props}>\n {children}\n </span>\n )\n },\n}\n\n/** Bare `doc-…` / `eml-…` ids in text become `<span data-doc-id>` / `<span data-mail-id>` pills. */\nconst conversationRehypePlugins = [rehypeDocEntityPills]\n\nexport type ConnectedMarkdownProps = Omit<KitMarkdownRendererProps, 'rehypePlugins'>\n\n/**\n * The kit's renderer with the conversation's overrides; a caller's `components` (e.g. the citation\n * core's) still win over both.\n */\nfunction ConnectedMarkdownComponent({ components, ...props }: ConnectedMarkdownProps) {\n const merged = useMemo(\n () =>\n components\n ? { ...conversationMarkdownComponents, ...components }\n : conversationMarkdownComponents,\n [components]\n )\n return (\n <KitMarkdownRenderer {...props} components={merged} rehypePlugins={conversationRehypePlugins} />\n )\n}\n\nexport const ConnectedMarkdown = React.memo(ConnectedMarkdownComponent)\n","/**\n * The PDF document tools (markup, Freeze, signing, signature requests, productions) on the\n * signed-in session, for any host: the API client, the signed-in user, the host's notices and\n * document opening (`BlocksEnvironment`), and the shared caches a change refreshes. A host with its\n * own binding (its own lists to refresh, an XHR upload with progress, Mail) gives it as the host\n * configuration's `documentTools`, field by field. An enclosing `DocumentToolsProvider` (a dialog\n * with its own client) wins.\n */\n\nimport { useCallback, useMemo, type ReactNode } from 'react'\nimport { useQueryClient } from '@tanstack/react-query'\nimport { arbiQueryKeys, refreshDocuments, useArbi } from '@arbidocs/react'\nimport {\n DocumentToolsProvider,\n clientUpload,\n documentBytesKey,\n useOptionalDocumentTools,\n type DocumentChange,\n type DocumentToolsClient,\n type DocumentToolsEnvironment,\n type DocumentToolsNotify,\n type DocumentUploadRequest,\n} from '@arbidocs/react/document-tools'\nimport { useBlocksEnvironment } from '../../provider/environment'\nimport { useHost } from '../../provider/host'\nimport { useConnectedWorkspace } from '../ConnectionProvider'\n\n/** What a host binds of the document tools itself; each absent field is the kit's own. */\nexport interface DocumentToolsHost {\n /** The API client the tools call. Default: the host `arbi`'s. */\n client?: DocumentToolsClient\n /** The deployment domain keys are derived for (signing). Default: the host `arbi`'s. */\n deploymentDomain?: string\n /** Open a document or a version the tools made. Default: the environment's `openDocument`. */\n openDocument?: (documentRef: string) => void\n /** Refresh the host's lists after a change. Default: the shared document caches. */\n onDocumentsChanged?: DocumentToolsEnvironment['onDocumentsChanged']\n /** Upload a derived copy. Default: through the API client, into the open workspace. */\n uploadDocument?: DocumentToolsEnvironment['uploadDocument']\n /**\n * Where \"View certificate\" goes for a signature `reference` (e.g. the site's own verify page).\n * Default: the certificate link the API returns (on the deployment domain).\n */\n certificateUrl?: (reference: string) => string\n /** Email a document (a hook): absent, or returning nothing, when mail is not offered. */\n useEmailDocument?: () => ((documentRef: string) => void) | undefined\n}\n\nconst NO_EMAIL = () => undefined\n\nexport function ConnectedDocumentToolsProvider({ children }: { children: ReactNode }) {\n const enclosing = useOptionalDocumentTools()\n return enclosing ? <>{children}</> : <OwnDocumentTools>{children}</OwnDocumentTools>\n}\n\nfunction OwnDocumentTools({ children }: { children: ReactNode }) {\n const arbi = useArbi()\n const queryClient = useQueryClient()\n const host = useHost().documentTools\n const { user, ensureWorkspaceOpen } = useConnectedWorkspace()\n const { notify: environmentNotify, openDocument: openInHost } = useBlocksEnvironment()\n const useEmailDocument = host?.useEmailDocument ?? NO_EMAIL\n const emailDocument = useEmailDocument()\n const client = host?.client ?? (arbi.isLoggedIn ? arbi.getClient().fetch : null)\n const signer = useMemo(\n () => (user ? { name: user.name, email: user.email, externalId: user.externalId } : null),\n [user]\n )\n const notify = useCallback<DocumentToolsNotify>(\n (message, kind, options) =>\n environmentNotify(message, kind, {\n description: options?.description,\n action: options?.action,\n }),\n [environmentNotify]\n )\n const ownDocumentsChanged = useCallback(\n async (ids: string[], change: DocumentChange) => {\n // The list carries each version's markup count and the copies; a signature or a saved\n // version is a new current version, with new versions and a new rendered PDF.\n const refresh: Promise<unknown>[] = [refreshDocuments(queryClient, arbi, ids)]\n if (change === 'signed' || change === 'version')\n for (const id of ids)\n refresh.push(\n queryClient.invalidateQueries({ queryKey: arbiQueryKeys.documentVersions(id) }),\n queryClient.invalidateQueries({ queryKey: documentBytesKey(id) })\n )\n await Promise.all(refresh)\n },\n [queryClient, arbi]\n )\n // The server files an upload in the session's open workspace: re-assert it first.\n const ownUpload = useCallback(\n async (request: DocumentUploadRequest) => {\n if (!client) throw new Error('Sign in to save a copy.')\n await ensureWorkspaceOpen()\n return clientUpload(client)(request)\n },\n [client, ensureWorkspaceOpen]\n )\n const ownOpenDocument = useCallback((ref: string) => openInHost(ref), [openInHost])\n if (!client) return <>{children}</>\n return (\n <DocumentToolsProvider\n client={client}\n deploymentDomain={host?.deploymentDomain}\n user={signer}\n notify={notify}\n openDocument={host?.openDocument ?? ownOpenDocument}\n onDocumentsChanged={host?.onDocumentsChanged ?? ownDocumentsChanged}\n uploadDocument={host?.uploadDocument ?? ownUpload}\n emailDocument={emailDocument}\n certificateUrl={host?.certificateUrl}\n >\n {children}\n </DocumentToolsProvider>\n )\n}\n","/**\n * What a host adds to the connected document viewer. The viewer reads documents, versions, PDFs,\n * markup and signatures on the signed-in session by itself; these are the host's own things it\n * cannot know: documents the host makes on the client (an artifact streaming in from a chat, an\n * unsaved draft), the host's dialogs and workflows a document action opens, and how the host lays\n * the viewer out. It is the host configuration's `viewer`. Every field is optional: without one the\n * viewer offers less (no Translate button, no draft controls), never something that does nothing.\n * What changes while the viewer is open is read through hooks (`use…`).\n */\n\nimport type { ReactNode } from 'react'\nimport type { components } from '@arbidocs/client'\nimport { useHost } from '../../provider/host'\n\n/** A document's record, as the viewer reads it. */\nexport type ViewerDocumentRecord = components['schemas']['DocResponse']\n\n/** An artifact being generated in a chat, shown in the viewer as it streams. */\nexport interface ViewerStreamingDocument {\n title?: string | null\n /** The content so far (Markdown, or the html/react source of a live artifact). */\n content: string\n /** How it is carried: a document draft, a live `html` / `react` artifact, an `image`. */\n mode?: string | null\n isComplete: boolean\n}\n\n/** A document the user started on the client, with no backend record until it is saved. */\nexport interface ViewerDraftDocument {\n kind: 'text' | 'audio' | 'photo' | 'video'\n title?: string | null\n /** A text draft's starting content. */\n content?: string | null\n}\n\nexport interface DocumentViewerSupport {\n /** The artifact streaming in as this document, if one is (a hook). */\n useStreamingDocument?: (documentId: string) => ViewerStreamingDocument | undefined\n /** The unsaved draft with this client id, if there is one (a hook). */\n useDraftDocument?: (draftId: string) => ViewerDraftDocument | undefined\n /** A draft's kind (text, photo, audio, video), in place of the tabs. */\n renderDraftKind?: (draftId: string) => ReactNode\n /** A draft's name (editable), in place of the title. */\n renderDraftTitle?: (draftId: string) => ReactNode\n /** The recorder of a photo, audio or video draft: the whole body of the viewer. */\n renderCaptureDraft?: (draftId: string) => ReactNode\n /** A text draft was saved as `documentId`; the viewer shows it next. */\n onDraftSaved?: (draftId: string, documentId: string) => void\n /** The copy of a document kept on this device, for when the network is down. */\n loadOfflineCopy?: (document: ViewerDocumentRecord) => Promise<Blob | undefined>\n /** Documents related to the one open (near duplicates), beside its name. */\n renderRelated?: (document: ViewerDocumentRecord) => ReactNode\n /** A document as a pill (the comparison's other side). Default: its name. */\n renderDocumentPill?: (documentId: string) => ReactNode\n /** Open the host's share dialog for the document. Default: share it with the workspace. */\n share?: (document: { id: string; name: string | undefined; isPrivate: boolean }) => void\n /** Ask the assistant about a version (`doc-…@v2`) open read-only. Absent: not offered. */\n askAboutVersion?: (versionRef: string) => void\n /** Translate the document (or the version) on screen. Absent: not offered. */\n translate?: (documentRef: string) => void\n /** Start an image generation from the image on screen. Absent: not offered. */\n useImageAsReference?: (documentId: string) => void\n /**\n * A citation being edited elsewhere (a fact's sources, a field's) picks its passages in the text\n * view: clicks and selections there are handed to it (a hook). Absent: passages are not pickable.\n */\n usePassageCitation?: () => PassageCitation | undefined\n /** Open the document's passages in the host's navigator (a passage's menu). Absent: not offered. */\n openInNavigator?: (documentId: string) => void\n /** Start a new label or field in the host's editor (the passage tagging panel). Absent: not offered. */\n createTag?: () => void\n /** How dates read (versions, signatures). Default: `fmtDate`. */\n formatDate?: (iso: string) => string\n /** Whether the viewer is shown in another window, where PDF pages render without the page's web\n * fonts (a hook). */\n useIsDetached?: () => boolean\n}\n\n/** A passage picked for a citation: its chunk and, when known, its page. */\nexport interface PickedPassage {\n chunk_id: string\n page?: number\n}\n\n/** The citation a host is editing, as the text view sees it. */\nexport interface PassageCitation {\n /** The citation picking passages now, and the document it picks in; null when none is. */\n active: { documentId: string; key: string | null } | null\n /** Passages to light (a fact's cited passages while its sources are open). */\n highlighted: readonly string[]\n /** Passages added to the citation. */\n pick: (passages: PickedPassage[]) => void\n /** Passages taken off it. */\n unpick: (chunkIds: string[]) => void\n}\n\nconst NO_SUPPORT: DocumentViewerSupport = {}\n\nexport function useDocumentViewerSupport(): DocumentViewerSupport {\n return useHost().viewer ?? NO_SUPPORT\n}\n\nconst NONE = () => undefined\nconst ATTACHED = () => false\n\n/** The artifact streaming in as this document (none without the host's). */\nexport function useViewerStreamingDocument(\n documentId: string\n): ViewerStreamingDocument | undefined {\n const useStreaming = useDocumentViewerSupport().useStreamingDocument ?? NONE\n return useStreaming(documentId)\n}\n\n/** The unsaved draft with this id (none without the host's). */\nexport function useViewerDraftDocument(draftId: string): ViewerDraftDocument | undefined {\n const useDraft = useDocumentViewerSupport().useDraftDocument ?? NONE\n return useDraft(draftId)\n}\n\n/** The citation picking passages (none without the host's). */\nexport function useViewerPassageCitation(): PassageCitation | undefined {\n const useCitation = useDocumentViewerSupport().usePassageCitation ?? NONE\n return useCitation()\n}\n\n/** Whether the viewer is in another window (never without the host's). */\nexport function useViewerIsDetached(): boolean {\n const useDetached = useDocumentViewerSupport().useIsDetached ?? ATTACHED\n return useDetached()\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/chat/mermaid-normalize.ts","../src/connection/conversation/MermaidDiagram.tsx","../src/connection/conversation/DocumentWorkspaceContext.tsx","../src/connection/conversation/ConnectedMarkdown.tsx","../src/connection/viewer/ConnectedDocumentToolsProvider.tsx","../src/connection/viewer/support.ts"],"names":["useState","useId","useEffect","jsxs","jsx","createContext","useContext","useBlocksEnvironment","React","useArbiSession","MentionChip","QuietLink","useArbiHost","Fragment","useDocument","EntityPill","FileText","DocumentEntity","Mail","mentionFromHref","MarkdownLink","workspaceDocIdFromHref","MarkdownStreamingContext","MarkdownCode","rehypeDocEntityPills","useMemo","KitMarkdownRenderer","useOptionalDocumentTools","useArbi","useQueryClient","useHost","useConnectedWorkspace","useCallback","refreshDocuments","arbiQueryKeys","documentBytesKey","clientUpload","DocumentToolsProvider"],"mappings":"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","file":"chunk-WPOQLGKJ.cjs","sourcesContent":["/**\n * Defensive normalizer for single-line `graph` / `flowchart` Mermaid source.\n *\n * Some LLMs emit the entire diagram on one line. Mermaid's parser splits\n * statements on newlines, so a single-line graph fails outright. This helper\n * inserts newlines on safe statement boundaries so the diagram has a chance\n * of parsing. Only attempts normalization when:\n * 1. The source has no embedded newlines (i.e. is genuinely single-line), and\n * 2. The first directive is `graph` or `flowchart`.\n *\n * Other diagram types (sequenceDiagram, classDiagram, gantt, …) have very\n * different syntaxes — applying these heuristics to them would corrupt valid\n * input, so they're left untouched.\n *\n * Boundaries we split on:\n * - After the diagram-type header (`graph TD`, `flowchart LR`, …).\n * - Before each `style` / `classDef` / `class` / `linkStyle` / `click`\n * / `subgraph` keyword.\n * - Before/after `end` (closes a subgraph block).\n * - After a `]` (label close) that's followed by another node identifier\n * starting a new edge or node declaration.\n */\nexport function normalizeMermaidGraph(source: string): string {\n // Already multi-line — assume it's well-formed; don't touch it.\n if (/\\n/.test(source)) return source\n\n const headerMatch = source.match(/^\\s*(graph|flowchart)\\s+\\w+\\s+/)\n if (!headerMatch) return source\n\n const header = headerMatch[0].trimEnd()\n let body = source.slice(headerMatch[0].length)\n\n // Insert newline before keywords that always start a new statement.\n body = body.replace(/\\s+(style|classDef|class|linkStyle|click|subgraph)\\s/g, '\\n$1 ')\n\n // `end` closes a subgraph: put it on its own line, with a break after it\n // too so any trailing statements don't stay attached.\n body = body.replace(/\\s+end\\b\\s*/g, '\\nend\\n')\n\n // After a label close (`]`), if the next token looks like a Mermaid node id\n // followed by another `[` or `-->`, that's a new statement starting.\n body = body.replace(/\\]\\s+(?=[A-Za-z_][\\w-]*\\s*(?:\\[|-->))/g, ']\\n')\n\n // Collapse any accidental runs of blank lines we may have produced.\n body = body.replace(/\\n{2,}/g, '\\n')\n\n return `${header}\\n${body.trimStart()}`\n}\n","/**\n * MermaidDiagram Component\n *\n * Renders a Mermaid diagram from source code.\n * Used inside MarkdownRenderer to handle ```mermaid code blocks.\n * Lazy-loads the mermaid library to avoid bloating the initial bundle.\n */\n\nimport { useState, useEffect, useId } from 'react'\nimport { normalizeMermaidGraph } from '../../chat/mermaid-normalize'\n\ninterface MermaidDiagramProps {\n /** Mermaid diagram source code */\n chart: string\n}\n\n// Lazy-load and initialize mermaid once\nlet mermaidInstance: typeof import('mermaid').default | null = null\nlet mermaidLoadPromise: Promise<typeof import('mermaid').default> | null = null\n\nasync function getMermaid() {\n if (mermaidInstance) return mermaidInstance\n if (!mermaidLoadPromise) {\n mermaidLoadPromise = import('mermaid').then((mod) => {\n const m = mod.default\n m.initialize({\n startOnLoad: false,\n theme: 'default',\n securityLevel: 'strict',\n flowchart: { useMaxWidth: true, curve: 'basis' },\n })\n mermaidInstance = m\n return m\n })\n }\n return mermaidLoadPromise\n}\n\nexport function MermaidDiagram({ chart }: MermaidDiagramProps) {\n const [svg, setSvg] = useState<string | null>(null)\n const [error, setError] = useState<string | null>(null)\n const uniqueId = useId().replace(/:/g, '-')\n\n useEffect(() => {\n let cancelled = false\n\n async function render() {\n const mermaid = await getMermaid()\n const diagramId = `mermaid${uniqueId}`\n\n // Validate with parse() before render(). In Mermaid v11 a render() with\n // bad source can return a \"Syntax error in text\" bomb SVG instead of\n // throwing — and it appends DOM side-effects of its own — so a try/catch\n // around render() doesn't reliably catch failures and the bomb leaks\n // into the page (especially under React StrictMode where effects run\n // twice). parse() throws cleanly with no DOM side-effects.\n //\n // Defensive rescue: some LLMs emit single-line `graph`/`flowchart`\n // source. If the original parse fails, try a normalized variant. The\n // normalizer is a no-op on already-multi-line source and on non-graph\n // diagram types, so this only helps the bad-source case and never\n // corrupts valid input.\n let validSource: string | null = null\n let firstErr: unknown\n try {\n await mermaid.parse(chart)\n validSource = chart\n } catch (err) {\n firstErr = err\n const normalized = normalizeMermaidGraph(chart)\n if (normalized !== chart) {\n try {\n await mermaid.parse(normalized)\n validSource = normalized\n } catch (retryErr) {\n console.warn('Mermaid normalized parse also failed', retryErr)\n }\n }\n }\n\n if (cancelled) return\n\n if (!validSource) {\n console.warn('Mermaid parse failed, showing source', firstErr)\n setError('Failed to render diagram')\n setSvg(null)\n return\n }\n\n try {\n const { svg: renderedSvg } = await mermaid.render(diagramId, validSource)\n if (!cancelled) {\n setSvg(renderedSvg)\n setError(null)\n }\n } catch (renderErr) {\n if (!cancelled) {\n console.warn('Mermaid render failed despite parse success', renderErr)\n setError('Failed to render diagram')\n setSvg(null)\n }\n }\n }\n\n render()\n return () => {\n cancelled = true\n }\n }, [chart, uniqueId])\n\n if (error) {\n // Fall back to showing the raw source in a code block\n return (\n <div className=\"code-block\" data-testid=\"mermaid-error\">\n <div className=\"text-sm text-muted-foreground mb-1\">{error}</div>\n <code className=\"language-mermaid\">{chart}</code>\n </div>\n )\n }\n\n if (!svg) {\n return (\n <div\n className=\"flex items-center justify-center py-8 text-muted-foreground text-sm\"\n data-testid=\"mermaid-loading\"\n >\n Rendering diagram...\n </div>\n )\n }\n\n return (\n <div\n className=\"mermaid-diagram my-4 overflow-x-auto rounded-md border border-border bg-background p-4\"\n data-testid=\"mermaid-diagram\"\n dangerouslySetInnerHTML={{ __html: svg }}\n />\n )\n}\n","/**\n * The workspace a conversation's document references belong to, when it is not the open one: an\n * agent's direct-message thread runs in the agent's workspace, so the documents it names are there.\n * A reference then opens that workspace first (`openDocument(id, { workspaceId })`).\n */\n\nimport { createContext, useContext, type ReactNode } from 'react'\nimport { useBlocksEnvironment } from '../../provider/environment'\n\n/** The workspace of the documents referenced inside it (null: the open workspace). */\nexport const DocumentWorkspaceContext = createContext<string | null>(null)\nexport const useDocumentWorkspace = () => useContext(DocumentWorkspaceContext)\n\n/** A reference to a document of another workspace: opening it opens that workspace first. */\nexport function WorkspaceDocumentReference({\n workspaceId,\n docId,\n children,\n className = 'inline-flex rounded-full border px-2 py-0.5 text-xs hover:bg-muted',\n}: {\n workspaceId: string\n docId: string\n children?: ReactNode\n className?: string\n}) {\n const { openDocument } = useBlocksEnvironment()\n return (\n <button\n type=\"button\"\n className={className}\n onClick={() => openDocument(docId, { workspaceId })}\n >\n {children ?? docId}\n </button>\n )\n}\n","/**\n * The conversation's markdown: the kit's `MarkdownRenderer` (`@arbidocs/react`: sanitised HTML,\n * slugs, lazy KaTeX, streaming blocks, tables, code) with what a conversation adds: @mention chips,\n * workspace documents opening in the viewer, quiet external links, document and email pills (the\n * host's chips, `ArbiChatHost.renderDocumentChip` / `renderMailChip`) and Mermaid diagrams.\n */\nimport { useArbiHost, useArbiSession, useDocument } from '@arbidocs/react'\nimport { mentionFromHref, type MentionKind } from '@arbidocs/react/shell'\nimport {\n EntityPill,\n MarkdownCode,\n MarkdownLink,\n MarkdownRenderer as KitMarkdownRenderer,\n MarkdownStreamingContext,\n type MarkdownRendererProps as KitMarkdownRendererProps,\n DocumentEntity,\n} from '@arbidocs/react/ui'\nimport React, { useContext, useMemo } from 'react'\nimport { FileText, Mail } from 'lucide-react'\n\n/** The markdown element overrides, as the kit's renderer takes them. */\ntype Components = NonNullable<KitMarkdownRendererProps['components']>\nimport { MentionChip } from '../../chat/MentionMenu'\nimport { QuietLink } from '../../citations/QuietMarks'\nimport { rehypeDocEntityPills } from '../../chat/rehype-doc-entity-pills'\nimport { workspaceDocIdFromHref } from '../../chat/doc-links'\nimport { useBlocksEnvironment } from '../../provider/environment'\nimport { MermaidDiagram } from './MermaidDiagram'\nimport { useDocumentWorkspace, WorkspaceDocumentReference } from './DocumentWorkspaceContext'\n\n/** Plain text of a link's children (the `@Label` of a mention link). */\nfunction childrenText(children: React.ReactNode): string {\n return React.Children.toArray(children)\n .map((child) => (typeof child === 'string' || typeof child === 'number' ? String(child) : ''))\n .join('')\n}\n\n/** A mention chip; a mention of the reader stands out. */\nfunction MentionLink({ kind, id, text }: { kind: MentionKind; id: string; text: string }) {\n const currentUserId = useArbiSession().user?.external_id\n return (\n <MentionChip\n kind={kind}\n id={id}\n label={text.replace(/^@/, '')}\n isSelf={kind === 'user' && id === currentUserId}\n />\n )\n}\n\n/**\n * A link to elsewhere, as quiet text. Its menu (Open link / Copy link) is the deliberate step\n * the old confirmation dialog used to be; nothing opens until the menu's primary row is chosen.\n */\nexport function ExternalLink({ href, children }: React.ComponentPropsWithoutRef<'a'>) {\n return (\n <QuietLink href={href} kind=\"external\">\n {children}\n </QuietLink>\n )\n}\n\n/**\n * A workspace document referenced by a link's href rather than by its text.\n *\n * `rehypeDocEntityPills` turns a bare `doc-…` id into a pill, but it only walks\n * TEXT nodes — so `[NVDA DCF Valuation Report](…doc-abc12345…)`, which is how an\n * answer links an artifact it just saved, keeps the id in the href where the\n * plugin never looks. The link then fell through to `ExternalLink`, and opening\n * your own workspace document asked you to confirm an \"external link\" and\n * launched a new tab. It opens in the document viewer, like the pill and the\n * artifact card already do.\n */\nexport function InternalDocLink({\n docId,\n href,\n children,\n}: React.ComponentPropsWithoutRef<'a'> & { docId: string }) {\n const { openDocument } = useBlocksEnvironment()\n const workspaceId = useDocumentWorkspace()\n if (workspaceId) {\n return (\n <WorkspaceDocumentReference workspaceId={workspaceId} docId={docId}>\n {children}\n </WorkspaceDocumentReference>\n )\n }\n\n return (\n <QuietLink href={href} kind=\"document\" onOpen={() => openDocument(docId)}>\n {children}\n </QuietLink>\n )\n}\n\n/** A document of the workspace, as a pill: the host's chip, else the document entity. */\nexport function DocumentChip({ docId }: { docId: string }) {\n const render = useArbiHost().chat?.renderDocumentChip\n const workspaceId = useDocumentWorkspace()\n if (workspaceId) return <WorkspaceDocumentReference workspaceId={workspaceId} docId={docId} />\n return render ? <>{render(docId)}</> : <DefaultDocumentChip docId={docId} />\n}\n\nfunction DefaultDocumentChip({ docId }: { docId: string }) {\n const { data: doc } = useDocument(docId)\n const { openDocument } = useBlocksEnvironment()\n if (!doc)\n return (\n <EntityPill\n icon={<FileText className=\"w-3.5 h-3.5 flex-shrink-0\" />}\n label={docId}\n size=\"sm\"\n onClick={() => openDocument(docId)}\n data-testid=\"doc-entity-pill\"\n />\n )\n return (\n <DocumentEntity doc={doc} onClick={() => openDocument(docId)} data-testid=\"doc-entity-pill\" />\n )\n}\n\n/** An email of the person's mailbox, as a pill: the host's chip, else a plain \"Email\". */\nexport function MailChip({ mailId }: { mailId: string }) {\n const render = useArbiHost().chat?.renderMailChip\n if (render) return <>{render(mailId)}</>\n return (\n <EntityPill\n icon={<Mail className=\"w-3.5 h-3.5 flex-shrink-0\" />}\n label=\"Email\"\n size=\"sm\"\n data-testid=\"mail-entity-pill\"\n />\n )\n}\n\n/**\n * The conversation's overrides, layered on the kit's defaults. Module scope, so the reference is stable\n * and memoised markdown blocks do not re-parse.\n */\nconst conversationMarkdownComponents: Partial<Components> = {\n a: function ConversationMarkdownLink({\n href,\n children,\n ...props\n }: React.ComponentPropsWithoutRef<'a'>) {\n const deploymentDomain = useBlocksEnvironment().runtimeConfig.deploymentDomain\n // @mentions: `linkMentions` turned them into `#mention-<id>` links; draw them as chips.\n const mention = mentionFromHref(href)\n if (mention) {\n return <MentionLink kind={mention.kind} id={mention.id} text={childrenText(children)} />\n }\n // Bookmarks: in-page anchors are near-invisible text; the menu jumps or copies the place.\n if (href?.startsWith('#') && !href.startsWith('#cite-')) {\n return (\n <QuietLink href={href} kind=\"anchor\">\n {children}\n </QuietLink>\n )\n }\n // Citations, `cite:` references and bare links: the kit's link.\n if (!href || href.startsWith('#') || href.startsWith('cite:')) {\n return (\n <MarkdownLink href={href} {...props}>\n {children}\n </MarkdownLink>\n )\n }\n // A workspace document is not an external link, wherever it is hosted: it opens in the viewer.\n const docId = workspaceDocIdFromHref(href, deploymentDomain)\n if (docId) {\n return (\n <InternalDocLink docId={docId} href={href} {...props}>\n {children}\n </InternalDocLink>\n )\n }\n return (\n <ExternalLink href={href} {...props}>\n {children}\n </ExternalLink>\n )\n },\n code: function ConversationMarkdownCode(\n props: React.ComponentPropsWithoutRef<'code'> & { inline?: boolean }\n ) {\n const isStreaming = useContext(MarkdownStreamingContext)\n const { className, children } = props\n const language = /language-(\\w+)/.exec(className || '')?.[1]\n if (!language) {\n // Answers often backtick a bare doc id (`doc-f7b3eeb5`). The text-node pass skips code, so\n // the id would stay monospace text; show it as the document pill. Only a whole id (eight\n // alphanumerics): while streaming, a partial one (\"doc-e\") would be looked up and 404.\n const codeText = typeof children === 'string' ? children.trim() : ''\n if (/^doc-[a-zA-Z0-9]{8}$/.test(codeText)) return <DocumentChip docId={codeText} />\n if (/^eml-[a-zA-Z0-9]{8}$/.test(codeText)) return <MailChip mailId={codeText} />\n }\n // Mermaid lazy-loads its own bundle and re-renders SVG on every change. While streaming the\n // fence is almost always partial, so it stays a code block until generation completes.\n if (language === 'mermaid' && !isStreaming) {\n return <MermaidDiagram chart={String(children).replace(/\\n$/, '')} />\n }\n return <MarkdownCode {...props} />\n },\n span: ({ children, className, ...props }: React.ComponentPropsWithoutRef<'span'>) => {\n const docId = (props as Record<string, unknown>)['data-doc-id'] as string | undefined\n if (docId) return <DocumentChip docId={docId} />\n const mailId = (props as Record<string, unknown>)['data-mail-id'] as string | undefined\n if (mailId) return <MailChip mailId={mailId} />\n return (\n <span className={className} {...props}>\n {children}\n </span>\n )\n },\n}\n\n/** Bare `doc-…` / `eml-…` ids in text become `<span data-doc-id>` / `<span data-mail-id>` pills. */\nconst conversationRehypePlugins = [rehypeDocEntityPills]\n\nexport type ConnectedMarkdownProps = Omit<KitMarkdownRendererProps, 'rehypePlugins'>\n\n/**\n * The kit's renderer with the conversation's overrides; a caller's `components` (e.g. the citation\n * core's) still win over both.\n */\nfunction ConnectedMarkdownComponent({ components, ...props }: ConnectedMarkdownProps) {\n const merged = useMemo(\n () =>\n components\n ? { ...conversationMarkdownComponents, ...components }\n : conversationMarkdownComponents,\n [components]\n )\n return (\n <KitMarkdownRenderer {...props} components={merged} rehypePlugins={conversationRehypePlugins} />\n )\n}\n\nexport const ConnectedMarkdown = React.memo(ConnectedMarkdownComponent)\n","/**\n * The PDF document tools (markup, Freeze, signing, signature requests, productions) on the\n * signed-in session, for any host: the API client, the signed-in user, the host's notices and\n * document opening (`BlocksEnvironment`), and the shared caches a change refreshes. A host with its\n * own binding (its own lists to refresh, an XHR upload with progress, Mail) gives it as the host\n * configuration's `documentTools`, field by field. An enclosing `DocumentToolsProvider` (a dialog\n * with its own client) wins.\n */\n\nimport { useCallback, useMemo, type ReactNode } from 'react'\nimport { useQueryClient } from '@tanstack/react-query'\nimport { arbiQueryKeys, refreshDocuments, useArbi } from '@arbidocs/react'\nimport {\n DocumentToolsProvider,\n clientUpload,\n documentBytesKey,\n useOptionalDocumentTools,\n type DocumentChange,\n type DocumentToolsClient,\n type DocumentToolsEnvironment,\n type DocumentToolsNotify,\n type DocumentUploadRequest,\n} from '@arbidocs/react/document-tools'\nimport { useBlocksEnvironment } from '../../provider/environment'\nimport { useHost } from '../../provider/host'\nimport { useConnectedWorkspace } from '../ConnectionProvider'\n\n/** What a host binds of the document tools itself; each absent field is the kit's own. */\nexport interface DocumentToolsHost {\n /** The API client the tools call. Default: the host `arbi`'s. */\n client?: DocumentToolsClient\n /** The deployment domain keys are derived for (signing). Default: the host `arbi`'s. */\n deploymentDomain?: string\n /** Open a document or a version the tools made. Default: the environment's `openDocument`. */\n openDocument?: (documentRef: string) => void\n /** Refresh the host's lists after a change. Default: the shared document caches. */\n onDocumentsChanged?: DocumentToolsEnvironment['onDocumentsChanged']\n /** Upload a derived copy. Default: through the API client, into the open workspace. */\n uploadDocument?: DocumentToolsEnvironment['uploadDocument']\n /**\n * Where \"View certificate\" goes for a signature `reference` (e.g. the site's own verify page).\n * Default: the certificate link the API returns (on the deployment domain).\n */\n certificateUrl?: (reference: string) => string\n /** Email a document (a hook): absent, or returning nothing, when mail is not offered. */\n useEmailDocument?: () => ((documentRef: string) => void) | undefined\n}\n\nconst NO_EMAIL = () => undefined\n\nexport function ConnectedDocumentToolsProvider({ children }: { children: ReactNode }) {\n const enclosing = useOptionalDocumentTools()\n return enclosing ? <>{children}</> : <OwnDocumentTools>{children}</OwnDocumentTools>\n}\n\nfunction OwnDocumentTools({ children }: { children: ReactNode }) {\n const arbi = useArbi()\n const queryClient = useQueryClient()\n const host = useHost().documentTools\n const { user, ensureWorkspaceOpen } = useConnectedWorkspace()\n const { notify: environmentNotify, openDocument: openInHost } = useBlocksEnvironment()\n const useEmailDocument = host?.useEmailDocument ?? NO_EMAIL\n const emailDocument = useEmailDocument()\n const client = host?.client ?? (arbi.isLoggedIn ? arbi.getClient().fetch : null)\n const signer = useMemo(\n () => (user ? { name: user.name, email: user.email, externalId: user.externalId } : null),\n [user]\n )\n const notify = useCallback<DocumentToolsNotify>(\n (message, kind, options) =>\n environmentNotify(message, kind, {\n description: options?.description,\n action: options?.action,\n }),\n [environmentNotify]\n )\n const ownDocumentsChanged = useCallback(\n async (ids: string[], change: DocumentChange) => {\n // The list carries each version's markup count and the copies; a signature or a saved\n // version is a new current version, with new versions and a new rendered PDF.\n const refresh: Promise<unknown>[] = [refreshDocuments(queryClient, arbi, ids)]\n if (change === 'signed' || change === 'version')\n for (const id of ids)\n refresh.push(\n queryClient.invalidateQueries({ queryKey: arbiQueryKeys.documentVersions(id) }),\n queryClient.invalidateQueries({ queryKey: documentBytesKey(id) })\n )\n await Promise.all(refresh)\n },\n [queryClient, arbi]\n )\n // The server files an upload in the session's open workspace: re-assert it first.\n const ownUpload = useCallback(\n async (request: DocumentUploadRequest) => {\n if (!client) throw new Error('Sign in to save a copy.')\n await ensureWorkspaceOpen()\n return clientUpload(client)(request)\n },\n [client, ensureWorkspaceOpen]\n )\n const ownOpenDocument = useCallback((ref: string) => openInHost(ref), [openInHost])\n if (!client) return <>{children}</>\n return (\n <DocumentToolsProvider\n client={client}\n deploymentDomain={host?.deploymentDomain}\n user={signer}\n notify={notify}\n openDocument={host?.openDocument ?? ownOpenDocument}\n onDocumentsChanged={host?.onDocumentsChanged ?? ownDocumentsChanged}\n uploadDocument={host?.uploadDocument ?? ownUpload}\n emailDocument={emailDocument}\n certificateUrl={host?.certificateUrl}\n >\n {children}\n </DocumentToolsProvider>\n )\n}\n","/**\n * What a host adds to the connected document viewer. The viewer reads documents, versions, PDFs,\n * markup and signatures on the signed-in session by itself; these are the host's own things it\n * cannot know: documents the host makes on the client (an artifact streaming in from a chat, an\n * unsaved draft), the host's dialogs and workflows a document action opens, and how the host lays\n * the viewer out. It is the host configuration's `viewer`. Every field is optional: without one the\n * viewer offers less (no Translate button, no draft controls), never something that does nothing.\n * What changes while the viewer is open is read through hooks (`use…`).\n */\n\nimport type { ReactNode } from 'react'\nimport type { components } from '@arbidocs/client'\nimport { useHost } from '../../provider/host'\n\n/** A document's record, as the viewer reads it. */\nexport type ViewerDocumentRecord = components['schemas']['DocResponse']\n\n/** An artifact being generated in a chat, shown in the viewer as it streams. */\nexport interface ViewerStreamingDocument {\n title?: string | null\n /** The content so far (Markdown, or the html/react source of a live artifact). */\n content: string\n /** How it is carried: a document draft, a live `html` / `react` artifact, an `image`. */\n mode?: string | null\n isComplete: boolean\n}\n\n/** A document the user started on the client, with no backend record until it is saved. */\nexport interface ViewerDraftDocument {\n kind: 'text' | 'audio' | 'photo' | 'video'\n title?: string | null\n /** A text draft's starting content. */\n content?: string | null\n}\n\nexport interface DocumentViewerSupport {\n /** The artifact streaming in as this document, if one is (a hook). */\n useStreamingDocument?: (documentId: string) => ViewerStreamingDocument | undefined\n /** The unsaved draft with this client id, if there is one (a hook). */\n useDraftDocument?: (draftId: string) => ViewerDraftDocument | undefined\n /** A draft's kind (text, photo, audio, video), in place of the tabs. */\n renderDraftKind?: (draftId: string) => ReactNode\n /** A draft's name (editable), in place of the title. */\n renderDraftTitle?: (draftId: string) => ReactNode\n /** The recorder of a photo, audio or video draft: the whole body of the viewer. */\n renderCaptureDraft?: (draftId: string) => ReactNode\n /** A text draft was saved as `documentId`; the viewer shows it next. */\n onDraftSaved?: (draftId: string, documentId: string) => void\n /** The copy of a document kept on this device, for when the network is down. */\n loadOfflineCopy?: (document: ViewerDocumentRecord) => Promise<Blob | undefined>\n /** Documents related to the one open (near duplicates), beside its name. */\n renderRelated?: (document: ViewerDocumentRecord) => ReactNode\n /** A document as a pill (the comparison's other side). Default: its name. */\n renderDocumentPill?: (documentId: string) => ReactNode\n /** Open the host's share dialog for the document. Default: share it with the workspace. */\n share?: (document: { id: string; name: string | undefined; isPrivate: boolean }) => void\n /** Ask the assistant about a version (`doc-…@v2`) open read-only. Absent: not offered. */\n askAboutVersion?: (versionRef: string) => void\n /** Translate the document (or the version) on screen. Absent: not offered. */\n translate?: (documentRef: string) => void\n /** Start an image generation from the image on screen. Absent: not offered. */\n useImageAsReference?: (documentId: string) => void\n /**\n * A citation being edited elsewhere (a fact's sources, a field's) picks its passages in the text\n * view: clicks and selections there are handed to it (a hook). Absent: passages are not pickable.\n */\n usePassageCitation?: () => PassageCitation | undefined\n /** Open the document's passages in the host's navigator (a passage's menu). Absent: not offered. */\n openInNavigator?: (documentId: string) => void\n /** Start a new label or field in the host's editor (the passage tagging panel). Absent: not offered. */\n createTag?: () => void\n /** How dates read (versions, signatures). Default: `fmtDate`. */\n formatDate?: (iso: string) => string\n /** Whether the viewer is shown in another window, where PDF pages render without the page's web\n * fonts (a hook). */\n useIsDetached?: () => boolean\n}\n\n/** A passage picked for a citation: its chunk and, when known, its page. */\nexport interface PickedPassage {\n chunk_id: string\n page?: number\n}\n\n/** The citation a host is editing, as the text view sees it. */\nexport interface PassageCitation {\n /** The citation picking passages now, and the document it picks in; null when none is. */\n active: { documentId: string; key: string | null } | null\n /** Passages to light (a fact's cited passages while its sources are open). */\n highlighted: readonly string[]\n /** Passages added to the citation. */\n pick: (passages: PickedPassage[]) => void\n /** Passages taken off it. */\n unpick: (chunkIds: string[]) => void\n}\n\nconst NO_SUPPORT: DocumentViewerSupport = {}\n\nexport function useDocumentViewerSupport(): DocumentViewerSupport {\n return useHost().viewer ?? NO_SUPPORT\n}\n\nconst NONE = () => undefined\nconst ATTACHED = () => false\n\n/** The artifact streaming in as this document (none without the host's). */\nexport function useViewerStreamingDocument(\n documentId: string\n): ViewerStreamingDocument | undefined {\n const useStreaming = useDocumentViewerSupport().useStreamingDocument ?? NONE\n return useStreaming(documentId)\n}\n\n/** The unsaved draft with this id (none without the host's). */\nexport function useViewerDraftDocument(draftId: string): ViewerDraftDocument | undefined {\n const useDraft = useDocumentViewerSupport().useDraftDocument ?? NONE\n return useDraft(draftId)\n}\n\n/** The citation picking passages (none without the host's). */\nexport function useViewerPassageCitation(): PassageCitation | undefined {\n const useCitation = useDocumentViewerSupport().usePassageCitation ?? NONE\n return useCitation()\n}\n\n/** Whether the viewer is in another window (never without the host's). */\nexport function useViewerIsDetached(): boolean {\n const useDetached = useDocumentViewerSupport().useIsDetached ?? ATTACHED\n return useDetached()\n}\n"]}
|
|
@@ -1,10 +1,12 @@
|
|
|
1
1
|
"use client";
|
|
2
|
+
import { getHumanUserCount, getWorkspaceTypeInfo, getVariantBgClass } from './chunk-BTF4AZMG.js';
|
|
2
3
|
import { KeyValueRow, CollapsibleSection } from './chunk-WZ63HE2C.js';
|
|
3
4
|
import { MemberAvatarStack } from './chunk-FUPAGAZB.js';
|
|
4
|
-
import {
|
|
5
|
+
import { WorkspaceTypeBadgeView } from './chunk-NBV56SGU.js';
|
|
6
|
+
import { ActionLink } from './chunk-SUDPZ5IQ.js';
|
|
5
7
|
import { fmtDate } from './chunk-5VYJP6XD.js';
|
|
6
8
|
import { ModalHeader } from './chunk-TX2ZICS7.js';
|
|
7
|
-
import { FileText, MessagesSquare, Users, Check, ChevronRight, UserPlus, LogOut, Globe, AlertCircle, Plus, ArrowUpRight, AlignLeft, CreditCard } from 'lucide-react';
|
|
9
|
+
import { FileText, MessagesSquare, Users, Check, ChevronRight, UserPlus, LogOut, Globe, AlertCircle, Plus, ArrowUpRight, AlignLeft, CreditCard, User } from 'lucide-react';
|
|
8
10
|
import { formatRelativeTime, cn, Popover, PopoverTrigger, PopoverContent, Button, IconToggle, Dialog, DialogContent, DialogTitle, DialogDescription, Select, SelectTrigger, SelectValue, SelectContent, SelectItem, SelectSeparator, Input } from '@arbidocs/react/ui';
|
|
9
11
|
import { jsxs, jsx, Fragment } from 'react/jsx-runtime';
|
|
10
12
|
import { createContext, useContext, useMemo, useId, useState } from 'react';
|
|
@@ -725,7 +727,30 @@ function WorkspaceGroup({
|
|
|
725
727
|
}
|
|
726
728
|
);
|
|
727
729
|
}
|
|
730
|
+
function WorkspaceTypeBadge({
|
|
731
|
+
workspace,
|
|
732
|
+
showTooltip = false,
|
|
733
|
+
size = "md",
|
|
734
|
+
isSelected = false,
|
|
735
|
+
className
|
|
736
|
+
}) {
|
|
737
|
+
const userCount = getHumanUserCount(workspace.users);
|
|
738
|
+
const { type, variant } = getWorkspaceTypeInfo(workspace.is_public, userCount);
|
|
739
|
+
const icon = workspace.is_public ? Globe : userCount > 1 ? Users : User;
|
|
740
|
+
return /* @__PURE__ */ jsx(
|
|
741
|
+
WorkspaceTypeBadgeView,
|
|
742
|
+
{
|
|
743
|
+
icon,
|
|
744
|
+
bgClass: getVariantBgClass(variant),
|
|
745
|
+
typeLabel: type,
|
|
746
|
+
showTooltip,
|
|
747
|
+
size,
|
|
748
|
+
isSelected,
|
|
749
|
+
className
|
|
750
|
+
}
|
|
751
|
+
);
|
|
752
|
+
}
|
|
728
753
|
|
|
729
|
-
export { CommonWorkspaceToggle, DEFAULT_WORKSPACE_CARD_LABELS, ExpandableSection, FormActions, FormErrorBanner, ItalicNone, LeaveFooter, ModalActionRow, PageLoading, ProjectActionButton, ProjectOptionRow, ProjectPicker, WorkspaceAudienceLine, WorkspaceCard, WorkspaceFieldsView, WorkspaceFormModal, WorkspaceGroup, WorkspaceIdentityPanel, WorkspaceList, WorkspacePageFrame, WorkspaceProjectSlot, formatRole, getRoleBadgeClass, getRoleDescription };
|
|
730
|
-
//# sourceMappingURL=chunk-
|
|
731
|
-
//# sourceMappingURL=chunk-
|
|
754
|
+
export { CommonWorkspaceToggle, DEFAULT_WORKSPACE_CARD_LABELS, ExpandableSection, FormActions, FormErrorBanner, ItalicNone, LeaveFooter, ModalActionRow, PageLoading, ProjectActionButton, ProjectOptionRow, ProjectPicker, WorkspaceAudienceLine, WorkspaceCard, WorkspaceFieldsView, WorkspaceFormModal, WorkspaceGroup, WorkspaceIdentityPanel, WorkspaceList, WorkspacePageFrame, WorkspaceProjectSlot, WorkspaceTypeBadge, formatRole, getRoleBadgeClass, getRoleDescription };
|
|
755
|
+
//# sourceMappingURL=chunk-X4Y7ZHFB.js.map
|
|
756
|
+
//# sourceMappingURL=chunk-X4Y7ZHFB.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/workspaces/WorkspaceSettingsParts.tsx","../src/workspaces/CommonWorkspaceToggle.tsx","../src/workspaces/workspace-roles.ts","../src/workspaces/WorkspaceFormParts.tsx","../src/workspaces/WorkspaceCard.tsx","../src/workspaces/WorkspaceGroup.tsx","../src/workspaces/WorkspaceTypeBadge.tsx"],"names":["jsx","jsxs","cn","Button","Globe","FileText","ChevronRight","Users"],"mappings":";;;;;;;;;;;;AASO,SAAS,kBAAA,CAAmB,EAAE,MAAA,EAAQ,QAAA,EAAS,EAA6C;AACjG,EAAA,uBACE,GAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAU,iCAAA;AAAA,MACV,WAAA,EAAU,gBAAA;AAAA,MACV,aAAA,EAAa,MAAA;AAAA,MAGb,QAAA,kBAAA,GAAA,CAAC,SAAI,SAAA,EAAU,2EAAA,EACb,8BAAC,KAAA,EAAA,EAAI,SAAA,EAAU,kCAAA,EAAoC,QAAA,EAAS,CAAA,EAC9D;AAAA;AAAA,GACF;AAEJ;AAGO,SAAS,sBAAA,CAAuB,EAAE,QAAA,EAAS,EAA4B;AAC5E,EAAA,uBACE,GAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,0BAAA;AAAA,MACV,SAAA,EAAU,mEAAA;AAAA,MAET;AAAA;AAAA,GACH;AAEJ;AAUO,SAAS,oBAAA,CAAqB,EAAE,MAAA,EAAQ,OAAA,EAAS,UAAS,EAA8B;AAC7F,EAAA,uBACE,GAAA,CAAC,SAAI,SAAA,EAAU,iCAAA,EACb,+BAAC,KAAA,EAAA,EAAI,SAAA,EAAU,wCAAA,EAAyC,aAAA,EAAa,MAAA,EACnE,QAAA,EAAA;AAAA,oBAAA,GAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,SAAA,EAAW,QAAA,EAAA,OAAA,EAAQ,CAAA;AAAA,IAClC;AAAA,GAAA,EACH,CAAA,EACF,CAAA;AAEJ;AAGO,SAAS,UAAA,CAAW,EAAE,QAAA,EAAS,EAA4B;AAChE,EAAA,uBAAO,GAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,sCAAA,EAAwC,QAAA,EAAS,CAAA;AAC1E;AAoBO,SAAS,qBAAA,CAAsB,EAAE,UAAA,EAAY,OAAA,EAAS,OAAM,EAA+B;AAChG,EAAA,uBACE,IAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,6CAAA,EAA8C,aAAU,oBAAA,EACtE,QAAA,EAAA;AAAA,oBAAA,IAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,yBAAA,EAA0B,aAAA,EAAa,WAAW,MAAA,EAChE,QAAA,EAAA;AAAA,sBAAA,GAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,SAAA,EAAW,QAAA,EAAA,UAAA,CAAW,OAAA,EAAQ,CAAA;AAAA,MAC7C,UAAA,CAAW,MAAA;AAAA,2BAEX,OAAA,EAAA,EACC,QAAA,EAAA;AAAA,wBAAA,GAAA,CAAC,cAAA,EAAA,EAAe,SAAA,EAAU,gNAAA,EACvB,QAAA,EAAA,UAAA,CAAW,SAAA,EACd,CAAA;AAAA,4BACC,cAAA,EAAA,EAAe,KAAA,EAAM,SAAQ,SAAA,EAAU,cAAA,EACrC,qBAAW,SAAA,EACd;AAAA,OAAA,EACF;AAAA,KAAA,EACF,CAAA;AAAA,oBAEA,IAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,yBAAA,EACb,QAAA,EAAA;AAAA,MAAA,OAAA;AAAA,MACA,KAAA,oBACC,IAAA;AAAA,QAAC,MAAA;AAAA,QAAA;AAAA,UACC,OAAA,EAAQ,SAAA;AAAA,UACR,IAAA,EAAK,IAAA;AAAA,UACL,SAAA,EAAU,8CAAA;AAAA,UACV,SAAS,KAAA,CAAM,OAAA;AAAA,UACf,eAAa,KAAA,CAAM,MAAA;AAAA,UAEnB,QAAA,EAAA;AAAA,4BAAA,GAAA,CAAC,QAAA,EAAA,EAAS,WAAU,QAAA,EAAS,CAAA;AAAA,YAC5B,KAAA,CAAM;AAAA;AAAA;AAAA;AACT,KAAA,EAEJ;AAAA,GAAA,EACF,CAAA;AAEJ;AAMO,SAAS,iBAAA,CAAkB;AAAA,EAChC,QAAA;AAAA,EACA,MAAA;AAAA,EACA;AACF,CAAA,EAIG;AACD,EAAA,uBACE,GAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAW,EAAA;AAAA,QACT,+DAAA;AAAA,QACA,WAAW,iBAAA,GAAoB;AAAA,OACjC;AAAA,MACA,WAAA,EAAU,oBAAA;AAAA,MACV,eAAA,EAAe,QAAA;AAAA,MACf,aAAA,EAAa,MAAA;AAAA,MAEb,QAAA,kBAAA,GAAA,CAAC,SAAI,SAAA,EAAU,iBAAA,EACb,8BAAC,KAAA,EAAA,EAAI,SAAA,EAAU,kCAAA,EAAoC,QAAA,EAAS,CAAA,EAC9D;AAAA;AAAA,GACF;AAEJ;AAGO,SAAS,WAAA,CAAY,EAAE,QAAA,EAAS,EAA4B;AACjE,EAAA,uBAAO,GAAA,CAAC,KAAA,EAAA,EAAI,SAAA,EAAU,uCAAA,EAAyC,QAAA,EAAS,CAAA;AAC1E;AAQO,SAAS,WAAA,CAAY,EAAE,MAAA,EAAQ,KAAA,EAAM,EAAqB;AAC/D,EAAA,2BACG,KAAA,EAAA,EAAI,SAAA,EAAU,oBAAmB,WAAA,EAAU,cAAA,EAAe,eAAa,MAAA,EACtE,QAAA,kBAAA,IAAA;AAAA,IAAC,MAAA;AAAA,IAAA;AAAA,MACC,OAAA,EAAQ,OAAA;AAAA,MACR,IAAA,EAAK,IAAA;AAAA,MACL,SAAS,KAAA,CAAM,OAAA;AAAA,MACf,UAAU,KAAA,CAAM,QAAA;AAAA,MAChB,SAAA,EAAU,sGAAA;AAAA,MACV,eAAa,KAAA,CAAM,MAAA;AAAA,MAEnB,QAAA,EAAA;AAAA,wBAAA,GAAA,CAAC,MAAA,EAAA,EAAO,WAAU,eAAA,EAAgB,CAAA;AAAA,QACjC,KAAA,CAAM;AAAA;AAAA;AAAA,GACT,EACF,CAAA;AAEJ;ACxJA,IAAM,MAAA,GAAS;AAAA,EACb,IAAA,EAAM,uBAAA;AAAA,EACN,EAAA,EAAI;AACN,CAAA;AAEO,SAAS,qBAAA,CAAsB;AAAA,EACpC,QAAA;AAAA,EACA,QAAA;AAAA,EACA,QAAA,GAAW,KAAA;AAAA,EACX,eAAA;AAAA,EACA,aAAA,EAAe;AACjB,CAAA,EAA+B;AAC7B,EAAA,uBACEA,GAAAA;AAAA,IAAC,UAAA;AAAA,IAAA;AAAA,MACC,IAAA,EAAM,KAAA;AAAA,MACN,QAAA,EAAU,QAAA;AAAA,MACV,QAAA;AAAA,MACA,MAAA,EAAQ,MAAA;AAAA,MACR,QAAA;AAAA,MACA,eAAA;AAAA,MACA,aAAA,EAAc,8EAAA;AAAA,MACd,eAAA,EAAgB,oGAAA;AAAA,MAChB,aAAA,EAAa;AAAA;AAAA,GACf;AAEJ;;;ACpCO,SAAS,WAAW,IAAA,EAAsB;AAC/C,EAAA,OAAO,IAAA,CAAK,OAAO,CAAC,CAAA,CAAE,aAAY,GAAI,IAAA,CAAK,MAAM,CAAC,CAAA;AACpD;AAEA,IAAM,kBAAA,GAAwD;AAAA,EAC5D,KAAA,EAAO,8DAAA;AAAA,EACP,YAAA,EAAc,oEAAA;AAAA,EACd,KAAA,EAAO;AACT,CAAA;AAGO,SAAS,kBAAkB,IAAA,EAAiC;AACjE,EAAA,OAAO,mBAAmB,IAAI,CAAA;AAChC;AAEA,IAAM,iBAAA,GAAuD;AAAA,EAC3D,KAAA,EACE,4IAAA;AAAA,EACF,YAAA,EACE,0JAAA;AAAA,EACF,KAAA,EACE;AACJ,CAAA;AAGO,SAAS,mBAAmB,IAAA,EAAiC;AAClE,EAAA,OAAO,kBAAkB,IAAI,CAAA;AAC/B;ACNO,SAAS,eAAA,CAAgB;AAAA,EAC9B,OAAA;AAAA,EACA,MAAA;AAAA,EACA,SAAA;AAAA,EACA;AACF,CAAA,EAMG;AACD,EAAA,uBACEC,IAAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,EAAA;AAAA,MACA,IAAA,EAAK,OAAA;AAAA,MACL,WAAA,EAAU,YAAA;AAAA,MACV,aAAA,EAAa,MAAA;AAAA,MACb,SAAA,EAAWC,EAAAA;AAAA,QACT,iGAAA;AAAA,QACA;AAAA,OACF;AAAA,MAEA,QAAA,EAAA;AAAA,wBAAAF,GAAAA,CAAC,WAAA,EAAA,EAAY,SAAA,EAAU,iBAAA,EAAkB,eAAY,MAAA,EAAO,CAAA;AAAA,QAC3D;AAAA;AAAA;AAAA,GACH;AAEJ;AAGO,SAAS,WAAA,CAAY,EAAE,SAAA,EAAW,QAAA,EAAS,EAAgD;AAChG,EAAA,uBACEA,GAAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,cAAA;AAAA,MACV,SAAA,EAAWE,EAAAA,CAAG,2DAAA,EAA6D,SAAS,CAAA;AAAA,MAEnF;AAAA;AAAA,GACH;AAEJ;AAGO,SAAS,cAAA,CAAe,EAAE,QAAA,EAAS,EAA4B;AACpE,EAAA,uBACEF,GAAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,WAAA,EAAU,kBAAA;AAAA,MACV,SAAA,EAAU,wJAAA;AAAA,MAET;AAAA;AAAA,GACH;AAEJ;AAiBO,SAAS,kBAAA,CAAmB;AAAA,EACjC,IAAA;AAAA,EACA,YAAA;AAAA,EACA,KAAA;AAAA,EACA,IAAA;AAAA,EACA,KAAA;AAAA,EACA,MAAA;AAAA,EACA,WAAA,GAAc,wBAAA;AAAA,EACd;AACF,CAAA,EAA4B;AAC1B,EAAA,uBACEA,GAAAA,CAAC,MAAA,EAAA,EAAO,IAAA,EAAY,cAClB,QAAA,kBAAAC,IAAAA;AAAA,IAAC,aAAA;AAAA,IAAA;AAAA,MACC,YAAA,EAAa,OAAA;AAAA,MACb,SAAA,EAAU,sEAAA;AAAA,MACV,aAAA,EAAa,MAAA;AAAA,MAEb,QAAA,EAAA;AAAA,wBAAAD,GAAAA,CAAC,eACC,QAAA,kBAAAA,GAAAA,CAAC,iBAAc,IAAA,EAAY,KAAA,EAAc,aAA0B,CAAA,EACrE,CAAA;AAAA,wBACAC,IAAAA,CAAC,KAAA,EAAA,EAAI,SAAA,EAAU,wCAAA,EACZ,QAAA,EAAA;AAAA,UAAA,KAAA,oBAASD,GAAAA,CAAC,GAAA,EAAA,EAAE,SAAA,EAAU,sCAAsC,QAAA,EAAA,KAAA,EAAM,CAAA;AAAA,UAClE;AAAA,SAAA,EACH;AAAA;AAAA;AAAA,GACF,EACF,CAAA;AAEJ;AAEA,SAAS,aAAA,CAAc;AAAA,EACrB,IAAA;AAAA,EACA,KAAA;AAAA,EACA;AACF,CAAA,EAIG;AACD,EAAA,uBACEC,KAAA,QAAA,EAAA,EACE,QAAA,EAAA;AAAA,oBAAAD,IAAC,WAAA,EAAA,EACC,QAAA,kBAAAC,IAAAA,CAAC,KAAA,EAAA,EAAI,WAAU,yBAAA,EACZ,QAAA,EAAA;AAAA,MAAA,IAAA;AAAA,sBACDD,GAAAA,CAAC,MAAA,EAAA,EAAM,QAAA,EAAA,KAAA,EAAM;AAAA,KAAA,EACf,CAAA,EACF,CAAA;AAAA,oBACAA,GAAAA,CAAC,iBAAA,EAAA,EAAkB,SAAA,EAAU,WAAW,QAAA,EAAA,WAAA,EAAY;AAAA,GAAA,EACtD,CAAA;AAEJ;AAGO,SAAS,gBAAA,CAAiB,EAAE,QAAA,EAAU,IAAA,EAAK,EAA2C;AAC3F,EAAA,uBACEC,IAAAA,CAAC,KAAA,EAAA,EAAI,SAAA,EAAU,wCAAA,EACZ,QAAA,EAAA;AAAA,IAAA,QAAA;AAAA,IACA,wBAAQD,GAAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,kDAAkD,QAAA,EAAA,IAAA,EAAK;AAAA,GAAA,EAClF,CAAA;AAEJ;AA0BA,IAAM,YAAA,GAAe,YAAA;AAId,SAAS,aAAA,CAAc;AAAA,EAC5B,KAAA;AAAA,EACA,OAAA;AAAA,EACA,QAAA;AAAA,EACA,OAAA,GAAU,MAAA;AAAA,EACV,QAAA;AAAA,EACA,QAAA;AAAA,EACA,QAAA;AAAA,EACA,SAAA;AAAA,EACA,MAAA,GAAS,EAAE,WAAA,EAAa,gBAAA,EAAkB,QAAQ,uBAAA,EAAwB;AAAA,EAC1E;AACF,CAAA,EAAuB;AACrB,EAAA,MAAM,UAAU,OAAA,KAAY,SAAA;AAC5B,EAAA,uBACEC,IAAAA;AAAA,IAAC,MAAA;AAAA,IAAA;AAAA,MACC,KAAA,EAAO,KAAA,IAAS,OAAA,CAAQ,CAAC,CAAA,EAAG,EAAA;AAAA,MAC5B,aAAA,EAAe,CAAC,CAAA,KAAO,CAAA,KAAM,eAAe,QAAA,IAAW,GAAI,SAAS,CAAC,CAAA;AAAA,MACrE,UAAU,QAAA,IAAY,QAAA;AAAA,MAEtB,QAAA,EAAA;AAAA,wBAAAD,GAAAA;AAAA,UAAC,aAAA;AAAA,UAAA;AAAA,YACC,SAAA,EAAWE,EAAAA;AAAA,cACT,OAAA,IACE,4GAAA;AAAA,cACF,SAAA;AAAA,cACA,QAAA,IAAY;AAAA,aACd;AAAA,YACA,aAAA,EACE,MAAA,KAAW,OAAA,GAAU,8BAAA,GAAiC,0BAAA,CAAA;AAAA,YAGvD,QAAA,EAAA,OAAA,mBAAUF,GAAAA,CAAC,WAAA,EAAA,EAAY,CAAA,mBAAKA,GAAAA,CAAC,WAAA,EAAA,EAAY,WAAA,EAAa,MAAA,CAAO,WAAA,EAAa;AAAA;AAAA,SAC7E;AAAA,wBACAC,IAAAA,CAAC,aAAA,EAAA,EAAc,KAAA,EAAO,OAAA,GAAU,QAAQ,MAAA,EACrC,QAAA,EAAA;AAAA,UAAA,OAAA,CAAQ,GAAA,CAAI,CAAC,CAAA,qBACZD,GAAAA,CAAC,UAAA,EAAA,EAAsB,KAAA,EAAO,CAAA,CAAE,EAAA,EAC7B,QAAA,EAAA,CAAA,CAAE,OAAA,EAAA,EADY,CAAA,CAAE,EAEnB,CACD,CAAA;AAAA,UACA,QAAA,oBACCC,IAAAA,CAAA,QAAA,EAAA,EACE,QAAA,EAAA;AAAA,4BAAAD,IAAC,eAAA,EAAA,EAAgB,CAAA;AAAA,4BACjBA,IAAC,UAAA,EAAA,EAAW,KAAA,EAAO,cACjB,QAAA,kBAAAC,IAAAA,CAAC,KAAA,EAAA,EAAI,SAAA,EAAU,wCAAA,EACb,QAAA,EAAA;AAAA,8BAAAD,GAAAA,CAAC,IAAA,EAAA,EAAK,SAAA,EAAU,UAAA,EAAW,CAAA;AAAA,8BAC3BA,GAAAA,CAAC,MAAA,EAAA,EAAM,QAAA,EAAA,MAAA,CAAO,MAAA,EAAO;AAAA,aAAA,EACvB,CAAA,EACF;AAAA,WAAA,EACF;AAAA,SAAA,EAEJ;AAAA;AAAA;AAAA,GACF;AAEJ;AAGO,SAAS,mBAAA,CAAoB;AAAA,EAClC,KAAA;AAAA,EACA,OAAA;AAAA,EACA,SAAA;AAAA,EACA;AACF,CAAA,EAKG;AACD,EAAA,uBACEC,IAAAA;AAAA,IAACE,MAAAA;AAAA,IAAA;AAAA,MACC,IAAA,EAAK,QAAA;AAAA,MACL,OAAA,EAAQ,SAAA;AAAA,MACR,IAAA,EAAK,IAAA;AAAA,MACL,OAAA;AAAA,MACA,SAAA,EAAWD,EAAAA;AAAA,QACT,iFAAA;AAAA,QACA;AAAA,OACF;AAAA,MACA,aAAA,EAAa,MAAA;AAAA,MAEb,QAAA,EAAA;AAAA,wBAAAF,GAAAA,CAAC,YAAA,EAAA,EAAa,SAAA,EAAU,UAAA,EAAW,CAAA;AAAA,QAClC;AAAA;AAAA;AAAA,GACH;AAEJ;AAmCA,IAAM,cAAA,GAAwC;AAAA,EAC5C,cAAA,EAAgB,qBAAA;AAAA,EAChB,IAAA,EAAM,QAAA;AAAA,EACN,WAAA,EAAa,aAAA;AAAA,EACb,UAAA,EAAY,YAAA;AAAA,EACZ,OAAA,EAAS,SAAA;AAAA,EACT,IAAA,EAAM,CAAC,CAAA,KAAM,CAAA,EAAG,CAAC,CAAA,KAAA,CAAA;AAAA,EACjB,SAAA,EAAW,CAAC,CAAA,KAAM,CAAA,EAAG,CAAC,CAAA,WAAA;AACxB,CAAA;AAGO,SAAS,mBAAA,CAAoB;AAAA,EAClC,OAAA,GAAU,OAAA;AAAA,EACV,IAAA;AAAA,EACA,WAAA;AAAA,EACA,YAAA;AAAA,EACA,mBAAA;AAAA,EACA,UAAA;AAAA,EACA,WAAA;AAAA,EACA,iBAAA;AAAA,EACA,QAAA,GAAW,KAAA;AAAA,EACX,QAAA,GAAW,KAAA;AAAA,EACX,OAAA;AAAA,EACA,aAAA,GAAgB,EAAA;AAAA,EAChB,UAAA;AAAA,EACA,OAAA;AAAA,EACA;AACF,CAAA,EAA6B;AAC3B,EAAA,MAAM,yBAAyB,KAAA,EAAM;AACrC,EAAA,MAAM,kBAAkB,KAAA,EAAM;AAC9B,EAAA,MAAM,CAAA,GAAI,EAAE,GAAG,cAAA,EAAgB,GAAG,MAAA,EAAO;AACzC,EAAA,MAAM,CAAC,WAAA,EAAa,cAAc,CAAA,GAAI,SAAS,KAAK,CAAA;AACpD,EAAA,MAAM,UAAU,OAAA,KAAY,OAAA;AAC5B,EAAA,MAAM,SAAA,GAAY,gBAAgB,IAAA,CAAK,MAAA;AAEvC,EAAA,MAAM,iBAAiB,CAAC,QAAA,IAAY,WAAA,KAAgB,CAAC,WAAW,SAAA,IAAa,EAAA,CAAA;AAC7E,EAAA,MAAM,UAAA,GAAa,OAAA,GAAU,QAAA,GAAW,QAAA,IAAY,QAAA;AAEpD,EAAA,uBACEC,IAAAA,CAAC,KAAA,EAAA,EAAI,SAAA,EAAU,WAAA,EAAY,aAAU,kBAAA,EAClC,QAAA,EAAA;AAAA,IAAA,QAAA,oBACCD,IAAC,KAAA,EAAA,EAAI,aAAA,EAAY,kCAAiC,SAAA,EAAU,SAAA,EACzD,YAAE,cAAA,EACL,CAAA;AAAA,oBAEFA,GAAAA,CAAC,WAAA,EAAA,EAAY,OAAO,CAAA,CAAE,IAAA,EAAM,sBAAMA,GAAAA,CAAC,YAAS,IAAA,EAAM,EAAA,EAAI,GAAI,OAAA,EAAS,eAAA,EACjE,0BAAAC,IAAAA,CAAC,KAAA,EAAA,EAAI,WAAU,UAAA,EACb,QAAA,EAAA;AAAA,sBAAAD,GAAAA;AAAA,QAAC,KAAA;AAAA,QAAA;AAAA,UACC,EAAA,EAAI,eAAA;AAAA,UACJ,IAAA,EAAK,MAAA;AAAA,UACL,KAAA,EAAO,IAAA;AAAA,UACP,UAAU,CAAC,CAAA,KAAM,YAAA,CAAa,CAAA,CAAE,OAAO,KAAK,CAAA;AAAA,UAC5C,QAAQ,MAAM;AACZ,YAAA,cAAA,CAAe,KAAK,CAAA;AACpB,YAAA,UAAA,IAAa;AAAA,UACf,CAAA;AAAA,UACA,SAAS,MAAM;AACb,YAAA,cAAA,CAAe,IAAI,CAAA;AACnB,YAAA,WAAA,IAAc;AAAA,UAChB,CAAA;AAAA,UACA,SAAA,EAAW,aAAA;AAAA,UACX,QAAA;AAAA,UACA,QAAA,EAAU,UAAA;AAAA,UACV,SAAA,EAAWE,EAAAA;AAAA,YACT,UAAU,eAAA,GAAkB,YAAA;AAAA,YAC5B,QAAA,IAAY,oBAAA;AAAA,YACZ;AAAA,WACF;AAAA,UACA,QAAA,EAAQ,IAAA;AAAA,UACR,cAAA,EAAc,UAAU,IAAA,GAAO,MAAA;AAAA,UAC/B,kBAAA,EAAkB,OAAA;AAAA,UAClB,aAAA,EAAY;AAAA;AAAA,OACd;AAAA,MACC,kCACCF,GAAAA;AAAA,QAAC,KAAA;AAAA,QAAA;AAAA,UACC,SAAA,EAAWE,EAAAA;AAAA,YACT,uFAAA;AAAA,YACA,SAAA,GAAY,IAAI,eAAA,GAAkB;AAAA,WACpC;AAAA,UAEC,QAAA,EAAA,SAAA,GAAY,IAAI,CAAA,CAAE,IAAA,CAAK,CAAC,SAAS,CAAA,GAAI,CAAA,CAAE,SAAA,CAAU,SAAS;AAAA;AAAA;AAC7D,KAAA,EAEJ,CAAA,EACF,CAAA;AAAA,oBAEAF,GAAAA;AAAA,MAAC,WAAA;AAAA,MAAA;AAAA,QACC,OAAO,CAAA,CAAE,WAAA;AAAA,QACT,IAAA,kBAAMA,GAAAA,CAAC,SAAA,EAAA,EAAU,MAAM,EAAA,EAAI,CAAA;AAAA,QAC3B,OAAA,EAAS,sBAAA;AAAA,QAET,QAAA,kBAAAA,GAAAA;AAAA,UAAC,KAAA;AAAA,UAAA;AAAA,YACC,EAAA,EAAI,sBAAA;AAAA,YACJ,IAAA,EAAK,MAAA;AAAA,YACL,OAAA,EAAO,IAAA;AAAA,YACP,KAAA,EAAO,WAAA;AAAA,YACP,UAAU,CAAC,CAAA,KAAM,mBAAA,CAAoB,CAAA,CAAE,OAAO,KAAK,CAAA;AAAA,YACnD,MAAA,EAAQ,iBAAA;AAAA,YACR,QAAA;AAAA,YACA,QAAA,EAAU,UAAA;AAAA,YACV,SAAA,EAAWE,EAAAA,CAAG,OAAA,IAAW,eAAA,EAAiB,YAAY,oBAAoB,CAAA;AAAA,YAC1E,aAAA,EAAY;AAAA;AAAA;AACd;AAAA,KACF;AAAA,IAEC,UAAA,oBACCF,GAAAA,CAAC,WAAA,EAAA,EAAY,OAAO,CAAA,CAAE,UAAA,EAAY,IAAA,kBAAMA,IAACI,KAAAA,EAAA,EAAM,IAAA,EAAM,EAAA,EAAI,GACtD,QAAA,EAAA,UAAA,EACH,CAAA;AAAA,IAED,OAAA,oBACCJ,GAAAA,CAAC,WAAA,EAAA,EAAY,OAAO,CAAA,CAAE,OAAA,EAAS,IAAA,kBAAMA,GAAAA,CAAC,UAAA,EAAA,EAAW,IAAA,EAAM,EAAA,EAAI,GACxD,QAAA,EAAA,OAAA,EACH;AAAA,GAAA,EAEJ,CAAA;AAEJ;ACtXO,IAAM,6BAAA,GAAqD;AAAA,EAChE,aAAA,EAAe,CAAC,IAAA,KAAS,CAAA,eAAA,EAAkB,IAAI,CAAA,CAAA;AAAA,EAC/C,gBAAA,EAAkB,mBAAA;AAAA,EAClB,SAAA,EAAW,WAAA;AAAA,EACX,KAAA,EAAO,OAAA;AAAA,EACP,OAAA,EAAS,SAAA;AAAA,EACT,OAAA,EAAS,CAAC,QAAA,KAAa,CAAA,QAAA,EAAW,QAAQ,CAAA;AAC5C;AAQA,IAAM,cAAc,aAAA,CAAgC;AAAA,EAClD,OAAA,EAAS,KAAA;AAAA,EACT,MAAA,EAAQ;AACV,CAAC,CAAA;AA4BD,SAAS,iBAAA,CAAkB;AAAA,EACzB,OAAA,GAAU,KAAA;AAAA,EACV,QAAA;AAAA,EACA,IAAA;AAAA,EACA,KAAA;AAAA,EACA,MAAA;AAAA,EACA,MAAA;AAAA,EACA,SAAA;AAAA,EACA,QAAA;AAAA,EACA,GAAG;AACL,CAAA,EAA2B;AACzB,EAAA,MAAM,YAAA,GAAe,OAAA,CAAQ,OAAO,EAAE,GAAG,6BAAA,EAA+B,GAAG,MAAA,EAAO,CAAA,EAAI,CAAC,MAAM,CAAC,CAAA;AAC9F,EAAA,MAAM,YAAA,GAAeE,EAAAA;AAAA,IACnB,kHAAA;AAAA,IACA,yEAAA;AAAA,IACA,UACI,kCAAA,GACA,kGAAA;AAAA,IACJ;AAAA,GACF;AACA,EAAA,MAAM,aAAA,GAAgB,CAAC,KAAA,KAAyC;AAC9D,IAAA,IAAI,KAAA,CAAM,MAAA,KAAW,KAAA,CAAM,aAAA,EAAe;AAC1C,IAAA,IAAI,KAAA,CAAM,GAAA,KAAQ,OAAA,IAAW,KAAA,CAAM,QAAQ,GAAA,EAAK;AAC9C,MAAA,KAAA,CAAM,cAAA,EAAe;AACrB,MAAA,QAAA,EAAS;AAAA,IACX;AAAA,EACF,CAAA;AACA,EAAA,uBACEF,GAAAA,CAAC,WAAA,CAAY,QAAA,EAAZ,EAAqB,KAAA,EAAO,EAAE,OAAA,EAAS,MAAA,EAAQ,MAAA,EAAQ,YAAA,EAAa,EAClE,iCACCA,GAAAA;AAAA,IAAC,UAAA;AAAA,IAAA;AAAA,MACE,GAAI,IAAA;AAAA,MACL,IAAA;AAAA,MACA,QAAA;AAAA,MACA,YAAA,EAAY,KAAA;AAAA,MACZ,cAAA,EAAc,UAAU,MAAA,GAAS,MAAA;AAAA,MACjC,WAAA,EAAU,gBAAA;AAAA,MACV,aAAA,EAAa,MAAA;AAAA,MACb,eAAa,OAAA,IAAW,MAAA;AAAA,MACxB,SAAA,EAAW,YAAA;AAAA,MAEV;AAAA;AAAA,sBAGHA,GAAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACE,GAAG,IAAA;AAAA,MACJ,IAAA,EAAK,QAAA;AAAA,MACL,QAAA,EAAU,CAAA;AAAA,MACV,YAAA,EAAY,KAAA;AAAA,MACZ,cAAA,EAAc,UAAU,MAAA,GAAS,MAAA;AAAA,MACjC,WAAA,EAAU,gBAAA;AAAA,MACV,aAAA,EAAa,MAAA;AAAA,MACb,eAAa,OAAA,IAAW,MAAA;AAAA,MACxB,OAAA,EAAS,QAAA;AAAA,MACT,SAAA,EAAW,aAAA;AAAA,MACX,SAAA,EAAW,YAAA;AAAA,MAEV;AAAA;AAAA,GACH,EAEJ,CAAA;AAEJ;AAGA,SAAS,oBAAoB,EAAE,SAAA,EAAW,QAAA,EAAU,GAAG,MAAK,EAAuC;AACjG,EAAA,uBACEA,GAAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACE,GAAG,IAAA;AAAA,MACJ,SAAA,EAAWE,EAAAA,CAAG,6CAAA,EAA+C,SAAS,CAAA;AAAA,MACtE,WAAA,EAAU,uBAAA;AAAA,MAET;AAAA;AAAA,GACH;AAEJ;AAEA,SAAS,kBAAA,CAAmB,EAAE,QAAA,EAAU,SAAA,EAAU,EAAgD;AAChG,EAAA,MAAM,EAAE,MAAA,EAAO,GAAI,UAAA,CAAW,WAAW,CAAA;AACzC,EAAA,uBACEF,GAAAA;AAAA,IAAC,IAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAWE,EAAAA;AAAA,QACT,gGAAA;AAAA,QACA;AAAA,OACF;AAAA,MACA,WAAA,EAAU,sBAAA;AAAA,MACV,aAAA,EAAa,MAAA,IAAU,CAAA,EAAG,MAAM,CAAA,MAAA,CAAA;AAAA,MAE/B;AAAA;AAAA,GACH;AAEJ;AAMA,SAAS,oBAAA,CAAqB;AAAA,EAC5B,MAAA;AAAA,EACA;AACF,CAAA,EAKG;AACD,EAAA,MAAM,EAAE,OAAA,EAAS,MAAA,EAAO,GAAI,WAAW,WAAW,CAAA;AAClD,EAAA,uBACEF,GAAAA;AAAA,IAAC,MAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAU,oFAAA;AAAA,MACV,WAAA,EAAU,yBAAA;AAAA,MACV,aAAA,EAAa,MAAA;AAAA,MAEZ,QAAA,EAAA,OAAA;AAAA;AAAA;AAAA,wBAGCC,IAAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,8HAAA,EACd,QAAA,EAAA;AAAA,0BAAAD,GAAAA,CAAC,KAAA,EAAA,EAAM,SAAA,EAAU,8CAAA,EAA+C,eAAY,MAAA,EAAO,CAAA;AAAA,0BACnFA,GAAAA,CAAC,MAAA,EAAA,EAAK,WAAU,0CAAA,EACb,QAAA,EAAA,YAAA,IAAgB,OAAO,gBAAA,EAC1B;AAAA,SAAA,EACF;AAAA,0BAEAA,GAAAA,CAAC,YAAA,EAAA,EAAa,SAAA,EAAU,QAAA,EAAS,eAAY,MAAA,EAAO;AAAA;AAAA,GAExD;AAEJ;AAEA,SAAS,wBAAA,CAAyB;AAAA,EAChC,QAAA;AAAA,EACA;AACF,CAAA,EAGG;AACD,EAAA,uBACEA,GAAAA;AAAA,IAAC,GAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAWE,EAAAA,CAAG,4CAAA,EAA8C,SAAS,CAAA;AAAA,MACrE,KAAA,EAAO,OAAO,QAAA,KAAa,QAAA,GAAW,QAAA,GAAW,MAAA;AAAA,MACjD,WAAA,EAAU,4BAAA;AAAA,MAET;AAAA;AAAA,GACH;AAEJ;AAGA,SAAS,qBAAA,CAAsB;AAAA,EAC7B,SAAA;AAAA,EACA,QAAA;AAAA,EACA,GAAG;AACL,CAAA,EAAuC;AACrC,EAAA,uBACEF,GAAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACE,GAAG,IAAA;AAAA,MACJ,SAAA,EAAWE,EAAAA,CAAG,wCAAA,EAA0C,SAAS,CAAA;AAAA,MACjE,WAAA,EAAU,yBAAA;AAAA,MAET;AAAA;AAAA,GACH;AAEJ;AAGA,SAAS,oBAAoB,EAAE,SAAA,EAAW,QAAA,EAAU,GAAG,MAAK,EAAuC;AACjG,EAAA,uBACEF,GAAAA,CAAC,KAAA,EAAA,EAAK,GAAG,IAAA,EAAM,WAAWE,EAAAA,CAAG,6BAAA,EAA+B,SAAS,CAAA,EAClE,QAAA,EACH,CAAA;AAEJ;AAeA,SAAS,kBAAA,CAAmB;AAAA,EAC1B,QAAA;AAAA,EACA,SAAA;AAAA,EACA,WAAA;AAAA,EACA,UAAU,EAAC;AAAA,EACX,aAAA,GAAgB,KAAA;AAAA,EAChB,UAAA,GAAa,CAAA;AAAA,EACb;AACF,CAAA,EAA4B;AAC1B,EAAA,MAAM,EAAE,OAAA,EAAS,MAAA,EAAQ,MAAA,EAAO,GAAI,WAAW,WAAW,CAAA;AAC1D,EAAA,uBACED,IAAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAWC,EAAAA,CAAG,gEAAA,EAAkE,SAAS,CAAA;AAAA,MACzF,WAAA,EAAU,sBAAA;AAAA,MAEV,QAAA,EAAA;AAAA,wBAAAD,KAAC,MAAA,EAAA,EAAK,SAAA,EAAU,kCAAA,EAAmC,KAAA,EAAO,OAAO,SAAA,EAC/D,QAAA,EAAA;AAAA,0BAAAD,IAACK,QAAAA,EAAA,EAAS,SAAA,EAAU,QAAA,EAAS,eAAY,MAAA,EAAO,CAAA;AAAA,0BAChDL,GAAAA,CAAC,MAAA,EAAA,EAAK,WAAU,cAAA,EAAgB,QAAA,EAAA,QAAA,CAAS,gBAAe,EAAE;AAAA,SAAA,EAC5D,CAAA;AAAA,QACC,SAAA,KAAc,0BACbC,IAAAA,CAAC,UAAK,SAAA,EAAU,kCAAA,EAAmC,KAAA,EAAO,MAAA,CAAO,KAAA,EAC/D,QAAA,EAAA;AAAA,0BAAAD,GAAAA,CAAC,cAAA,EAAA,EAAe,SAAA,EAAU,QAAA,EAAS,eAAY,MAAA,EAAO,CAAA;AAAA,0BACtDA,GAAAA,CAAC,MAAA,EAAA,EAAK,WAAU,cAAA,EAAgB,QAAA,EAAA,SAAA,CAAU,gBAAe,EAAE;AAAA,SAAA,EAC7D,CAAA;AAAA,wBAEFC,IAAAA,CAAC,MAAA,EAAA,EAAK,WAAU,kCAAA,EAAmC,KAAA,EAAO,OAAO,OAAA,EAC/D,QAAA,EAAA;AAAA,0BAAAD,GAAAA,CAAC,KAAA,EAAA,EAAM,SAAA,EAAU,QAAA,EAAS,eAAY,MAAA,EAAO,CAAA;AAAA,0BAC7CA,GAAAA,CAAC,MAAA,EAAA,EAAK,SAAA,EAAU,cAAA,EAAe,aAAA,EAAa,MAAA,IAAU,CAAA,EAAG,MAAM,CAAA,aAAA,CAAA,EAC5D,QAAA,EAAA,aAAA,GAAgB,QAAA,GAAM,WAAA,EACzB;AAAA,SAAA,EACF,CAAA;AAAA,wBACAA,GAAAA;AAAA,UAAC,iBAAA;AAAA,UAAA;AAAA,YACC,OAAA;AAAA,YACA,KAAA,EAAO,WAAA;AAAA,YACP,GAAA,EAAK,UAAA;AAAA,YACL,MAAA,EAAQ,aAAA;AAAA,YACR,aAAA,EAAe,UAAU,aAAA,GAAgB,YAAA;AAAA,YACzC,OAAO,MAAA,CAAO,OAAA;AAAA,YACd,SAAA,EAAU,SAAA;AAAA,YACV,MAAA,EAAQ,MAAA,IAAU,CAAA,EAAG,MAAM,CAAA,eAAA;AAAA;AAAA;AAC7B;AAAA;AAAA,GACF;AAEJ;AAGA,SAAS,iBAAA,CAAkB,EAAE,SAAA,EAAU,EAA0B;AAC/D,EAAA,MAAM,EAAE,MAAA,EAAO,GAAI,UAAA,CAAW,WAAW,CAAA;AACzC,EAAA,uBACEA,GAAAA;AAAA,IAAC,MAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAU,sEAAA;AAAA,MACV,KAAA,EAAO,QAAQ,SAAS,CAAA;AAAA,MACxB,WAAA,EAAU,qBAAA;AAAA,MAET,QAAA,EAAA,MAAA,CAAO,OAAA,CAAQ,kBAAA,CAAmB,SAAS,CAAC;AAAA;AAAA,GAC/C;AAEJ;AAoCA,SAAS,iBAAA,CAAkB;AAAA,EACzB,SAAA;AAAA,EACA,OAAA,GAAU,KAAA;AAAA,EACV,QAAA;AAAA,EACA,IAAA;AAAA,EACA,IAAA;AAAA,EACA,MAAA;AAAA,EACA,aAAA;AAAA,EACA,UAAA;AAAA,EACA,KAAA;AAAA,EACA,MAAA;AAAA,EACA;AACF,CAAA,EAAuB;AACrB,EAAA,MAAM,YAAA,GAAe,EAAE,GAAG,6BAAA,EAA+B,GAAG,MAAA,EAAO;AACnE,EAAA,uBACEC,IAAAA;AAAA,IAAC,iBAAA;AAAA,IAAA;AAAA,MACC,OAAA;AAAA,MACA,QAAA;AAAA,MACA,IAAA;AAAA,MACA,KAAA,EAAO,YAAA,CAAa,aAAA,CAAc,SAAA,CAAU,IAAI,CAAA;AAAA,MAChD,MAAA;AAAA,MACA,MAAA;AAAA,MACA,SAAA;AAAA,MAEA,QAAA,EAAA;AAAA,wBAAAA,KAAC,mBAAA,EAAA,EACE,QAAA,EAAA;AAAA,UAAA,IAAA;AAAA,0BACDD,GAAAA,CAAC,kBAAA,EAAA,EAAoB,QAAA,EAAA,SAAA,CAAU,IAAA,EAAK,CAAA;AAAA,0BACpCA,GAAAA,CAAC,oBAAA,EAAA,EAAqB,MAAA,EAAQ,aAAA,EAAe;AAAA,SAAA,EAC/C,CAAA;AAAA,QACC,UAAU,QAAA,oBAAYA,GAAAA,CAAC,qBAAA,EAAA,EAAuB,oBAAU,QAAA,EAAS,CAAA;AAAA,QACjE,UAAU,WAAA,oBACTA,GAAAA,CAAC,wBAAA,EAAA,EAA0B,oBAAU,WAAA,EAAY,CAAA;AAAA,wBAEnDC,KAAC,mBAAA,EAAA,EACE,QAAA,EAAA;AAAA,UAAA,KAAA,KAAU,yBACTD,GAAAA;AAAA,YAAC,kBAAA;AAAA,YAAA;AAAA,cACC,UAAU,SAAA,CAAU,QAAA;AAAA,cACpB,WAAW,SAAA,CAAU,SAAA;AAAA,cACrB,aAAa,SAAA,CAAU,WAAA;AAAA,cACvB,SAAS,SAAA,CAAU,OAAA;AAAA,cACnB,eAAe,SAAA,CAAU,aAAA;AAAA,cACzB;AAAA;AAAA,WACF,GAEA,KAAA;AAAA,UAED,UAAU,SAAA,oBAAaA,IAAC,iBAAA,EAAA,EAAkB,SAAA,EAAW,UAAU,SAAA,EAAW;AAAA,SAAA,EAC7E;AAAA;AAAA;AAAA,GACF;AAEJ;AAEO,IAAM,aAAA,GAAgB,MAAA,CAAO,MAAA,CAAO,iBAAA,EAAmB;AAAA,EAC5D,IAAA,EAAM,iBAAA;AAAA,EACN,MAAA,EAAQ,mBAAA;AAAA,EACR,KAAA,EAAO,kBAAA;AAAA,EACP,OAAA,EAAS,oBAAA;AAAA,EACT,QAAA,EAAU,qBAAA;AAAA,EACV,WAAA,EAAa,wBAAA;AAAA,EACb,MAAA,EAAQ,mBAAA;AAAA,EACR,KAAA,EAAO,kBAAA;AAAA,EACP,IAAA,EAAM;AACR,CAAC;ACraM,SAAS,aAAA,CAAc,EAAE,QAAA,EAAU,SAAA,EAAW,QAAO,EAAuB;AACjF,EAAA,uBACEA,GAAAA;AAAA,IAAC,KAAA;AAAA,IAAA;AAAA,MACC,SAAA,EAAWE,EAAAA,CAAG,8CAAA,EAAgD,SAAS,CAAA;AAAA,MACvE,WAAA,EAAU,gBAAA;AAAA,MACV,aAAA,EAAa,MAAA;AAAA,MAEZ;AAAA;AAAA,GACH;AAEJ;AAyBO,SAAS,cAAA,CAAe;AAAA,EAC7B,KAAA;AAAA,EACA,UAAA;AAAA,EACA,QAAA;AAAA,EACA,MAAA;AAAA,EACA,SAAA;AAAA,EACA,aAAA;AAAA,EACA,QAAA;AAAA,EACA;AACF,CAAA,EAAwB;AACtB,EAAA,uBACEF,GAAAA;AAAA,IAAC,kBAAA;AAAA,IAAA;AAAA,MACC,KAAA;AAAA,MACA,UAAA;AAAA,MACA,QAAA;AAAA,MACA,aAAA,EAAe,MAAA;AAAA,MACf,cACE,MAAA,IAAU,SAAA,mBACRC,IAAAA,CAAC,MAAA,EAAA,EAAK,WAAU,4EAAA,EACb,QAAA,EAAA;AAAA,QAAA,SAAA;AAAA,wBACDD,GAAAA,CAACM,YAAAA,EAAA,EAAa,SAAA,EAAU,iBAAA,EAAkB,eAAY,MAAA,EAAO;AAAA,OAAA,EAC/D,CAAA,GACE,aAAA,IAAiB,CAAC,UAAA,mBACpBN,IAAC,MAAA,EAAA,EAAK,SAAA,EAAU,wCAAA,EAA0C,QAAA,EAAA,aAAA,EAAc,CAAA,GACtE,MAAA;AAAA,MAEN,SAAA,EAAWE,EAAAA,CAAG,OAAA,EAAS,SAAS,CAAA;AAAA,MAChC,eAAA,EAAgB,qEAAA;AAAA,MAChB,iBAAA,EAAkB,kDAAA;AAAA,MAEjB;AAAA;AAAA,GACH;AAEJ;AC7DO,SAAS,kBAAA,CAAmB;AAAA,EACjC,SAAA;AAAA,EACA,WAAA,GAAc,KAAA;AAAA,EACd,IAAA,GAAO,IAAA;AAAA,EACP,UAAA,GAAa,KAAA;AAAA,EACb;AACF,CAAA,EAA4B;AAC1B,EAAA,MAAM,SAAA,GAAY,iBAAA,CAAkB,SAAA,CAAU,KAAK,CAAA;AACnD,EAAA,MAAM,EAAE,IAAA,EAAM,OAAA,KAAY,oBAAA,CAAqB,SAAA,CAAU,WAAW,SAAS,CAAA;AAC7E,EAAA,MAAM,OAAO,SAAA,CAAU,SAAA,GAAYE,KAAAA,GAAQ,SAAA,GAAY,IAAIG,KAAAA,GAAQ,IAAA;AAEnE,EAAA,uBACEP,GAAAA;AAAA,IAAC,sBAAA;AAAA,IAAA;AAAA,MACC,IAAA;AAAA,MACA,OAAA,EAAS,kBAAkB,OAAO,CAAA;AAAA,MAClC,SAAA,EAAW,IAAA;AAAA,MACX,WAAA;AAAA,MACA,IAAA;AAAA,MACA,UAAA;AAAA,MACA;AAAA;AAAA,GACF;AAEJ","file":"chunk-X4Y7ZHFB.js","sourcesContent":["import type { ReactNode } from 'react'\nimport { LogOut, UserPlus } from 'lucide-react'\nimport { Button, cn, Popover, PopoverContent, PopoverTrigger } from '@arbidocs/react/ui'\n\n/**\n * Page frame of a workspace's home: a bounded column whose ONE scroll region spans the full\n * width (scrollbar on the outer edge), the inset living on the content inside it. A container,\n * so children can use `@2xl:` queries.\n */\nexport function WorkspacePageFrame({ testId, children }: { testId?: string; children: ReactNode }) {\n return (\n <div\n className=\"flex h-full flex-col @container\"\n data-slot=\"workspace-page\"\n data-testid={testId}\n >\n {/* scrollbar-gutter:stable keeps the content from jumping when a scrollbar appears. */}\n <div className=\"scrollbar-subtle min-h-0 flex-1 overflow-y-auto [scrollbar-gutter:stable]\">\n <div className=\"space-y-6 px-4 pb-6 sm:px-6 pt-4\">{children}</div>\n </div>\n </div>\n )\n}\n\n/** Tinted card holding the identity bar and the expandable member list. */\nexport function WorkspaceIdentityPanel({ children }: { children: ReactNode }) {\n return (\n <div\n data-slot=\"workspace-identity-panel\"\n className=\"group rounded-lg border border-border bg-card px-4 py-3 shadow-xs\"\n >\n {children}\n </div>\n )\n}\n\nexport interface WorkspaceProjectSlotProps {\n testId: string\n /** Screen-reader caption (\"Project:\"): the chip says what it is without a word in front. */\n caption: string\n children: ReactNode\n}\n\n/** The project control / chip pinned to the end of the name row. */\nexport function WorkspaceProjectSlot({ testId, caption, children }: WorkspaceProjectSlotProps) {\n return (\n <div className=\"flex min-w-0 items-center gap-3\">\n <div className=\"flex min-w-0 flex-1 items-center gap-2\" data-testid={testId}>\n <span className=\"sr-only\">{caption}</span>\n {children}\n </div>\n </div>\n )\n}\n\n/** Stated absence (\"None\") rather than a blank gap. */\nexport function ItalicNone({ children }: { children: ReactNode }) {\n return <span className=\"text-sm italic text-muted-foreground\">{children}</span>\n}\n\nexport interface WorkspaceAudienceLineProps {\n visibility: {\n testId: string\n caption: string\n /** The owner's visibility switch (developers only). */\n toggle?: ReactNode\n /** The state named in words, so the switch is never a puzzle. */\n stateText: string\n /** What the state means for who can see the workspace; opened by tapping the state words. */\n stateHelp: string\n }\n /** Member avatar stack. */\n members: ReactNode\n /** \"Share\" button (owners). */\n share?: { label: string; onClick: () => void; testId: string }\n}\n\n/** Visibility and members end the description line together: who can see and use the workspace. */\nexport function WorkspaceAudienceLine({ visibility, members, share }: WorkspaceAudienceLineProps) {\n return (\n <span className=\"flex flex-wrap items-center gap-x-4 gap-y-2\" data-slot=\"workspace-audience\">\n <span className=\"flex items-center gap-2\" data-testid={visibility.testId}>\n <span className=\"sr-only\">{visibility.caption}</span>\n {visibility.toggle}\n {/* Tap-to-explain, not hover-only: the words must answer a click on touch screens too. */}\n <Popover>\n <PopoverTrigger className=\"touch-hit cursor-pointer rounded-sm text-sm text-muted-foreground underline decoration-dotted underline-offset-4 hover:text-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring\">\n {visibility.stateText}\n </PopoverTrigger>\n <PopoverContent align=\"start\" className=\"w-64 text-sm\">\n {visibility.stateHelp}\n </PopoverContent>\n </Popover>\n </span>\n {/* Faces first, then Share: \"these people ... add more\". */}\n <span className=\"flex items-center gap-1\">\n {members}\n {share && (\n <Button\n variant=\"outline\"\n size=\"sm\"\n className=\"h-8 gap-1.5 px-3 text-sm pointer-coarse:h-11\"\n onClick={share.onClick}\n data-testid={share.testId}\n >\n <UserPlus className=\"size-4\" />\n {share.label}\n </Button>\n )}\n </span>\n </span>\n )\n}\n\n/**\n * Collapsible block under the identity bar. Stays mounted and animates its height (grid-rows\n * 0fr to 1fr), so opening and closing glides instead of snapping.\n */\nexport function ExpandableSection({\n expanded,\n testId,\n children,\n}: {\n expanded: boolean\n testId?: string\n children: ReactNode\n}) {\n return (\n <div\n className={cn(\n 'grid transition-[grid-template-rows] duration-300 ease-in-out',\n expanded ? 'grid-rows-[1fr]' : 'grid-rows-[0fr]'\n )}\n data-slot=\"expandable-section\"\n data-expanded={expanded}\n data-testid={testId}\n >\n <div className=\"overflow-hidden\">\n <div className=\"mt-4 border-t border-border pt-4\">{children}</div>\n </div>\n </div>\n )\n}\n\n/** Centered loading placeholder of a page body. */\nexport function PageLoading({ children }: { children: ReactNode }) {\n return <div className=\"flex h-64 items-center justify-center\">{children}</div>\n}\n\nexport interface LeaveFooterProps {\n testId?: string\n leave: { label: string; disabled?: boolean; onClick: () => void; testId?: string }\n}\n\n/** Leaving ENDS your part in the workspace, so it sits last and alone at the foot of the page. */\nexport function LeaveFooter({ testId, leave }: LeaveFooterProps) {\n return (\n <div className=\"flex justify-end\" data-slot=\"leave-footer\" data-testid={testId}>\n <Button\n variant=\"ghost\"\n size=\"sm\"\n onClick={leave.onClick}\n disabled={leave.disabled}\n className=\"h-7 px-2 text-sm text-destructive hover:bg-destructive/10 hover:text-destructive pointer-coarse:h-11\"\n data-testid={leave.testId}\n >\n <LogOut className=\"mr-1 size-3.5\" />\n {leave.label}\n </Button>\n </div>\n )\n}\n","/**\n * CommonWorkspaceToggle Component\n *\n * Toggle for workspace common/members-only visibility.\n * Takes isCommon and onToggle as props for form integration.\n */\n\nimport { Globe } from 'lucide-react'\nimport { IconToggle } from '@arbidocs/react/ui'\n\nexport interface CommonWorkspaceToggleProps {\n isCommon: boolean\n onToggle: (isCommon: boolean) => void\n disabled?: boolean\n /** Tooltip to show when disabled */\n disabledTooltip?: string\n 'data-testid'?: string\n}\n\nconst COLORS = {\n text: 'text-muted-foreground',\n bg: 'bg-gray-600',\n}\n\nexport function CommonWorkspaceToggle({\n isCommon,\n onToggle,\n disabled = false,\n disabledTooltip,\n 'data-testid': dataTestId,\n}: CommonWorkspaceToggleProps) {\n return (\n <IconToggle\n icon={Globe}\n isActive={isCommon}\n onToggle={onToggle}\n colors={COLORS}\n disabled={disabled}\n disabledTooltip={disabledTooltip}\n tooltipActive=\"On: everyone on this deployment can see it. Turn off to limit it to members.\"\n tooltipInactive=\"Off: only members of this workspace can see it. Turn on to let everyone on this deployment see it.\"\n data-testid={dataTestId}\n />\n )\n}\n","/**\n * A workspace role ('owner' | 'collaborator' | 'guest') as people see it: its name, its badge\n * colours and what it lets a member do.\n */\n\nexport type WorkspaceRoleName = 'owner' | 'collaborator' | 'guest'\n\n/** \"Owner\", \"Collaborator\", \"Guest\". */\nexport function formatRole(role: string): string {\n return role.charAt(0).toUpperCase() + role.slice(1)\n}\n\nconst ROLE_BADGE_CLASSES: Record<WorkspaceRoleName, string> = {\n owner: 'bg-primary text-white hover:bg-primary border border-primary',\n collaborator: 'bg-secondary text-white hover:bg-secondary border border-secondary',\n guest: 'bg-gray-600 text-white hover:bg-gray-600 border border-gray-600',\n}\n\n/** The badge classes of a role. */\nexport function getRoleBadgeClass(role: WorkspaceRoleName): string {\n return ROLE_BADGE_CLASSES[role]\n}\n\nconst ROLE_DESCRIPTIONS: Record<WorkspaceRoleName, string> = {\n owner:\n 'Owners have full control of the workspace, including adding and removing members, but cannot see private content created by other members.',\n collaborator:\n 'Collaborators can create and edit shared content, but cannot delete shared content created by others and cannot manage workspace settings or membership.',\n guest:\n 'Guests can create private content and view shared content, but cannot create or edit shared content.',\n}\n\n/** What a role lets a member do (a tooltip). */\nexport function getRoleDescription(role: WorkspaceRoleName): string {\n return ROLE_DESCRIPTIONS[role]\n}\n","import { useState, type ReactNode, useId } from 'react'\nimport {\n AlertCircle,\n AlignLeft,\n ArrowUpRight,\n CreditCard,\n FileText,\n Globe,\n Plus,\n} from 'lucide-react'\nimport {\n Button,\n cn,\n Dialog,\n DialogContent,\n DialogDescription,\n DialogTitle,\n Input,\n Select,\n SelectContent,\n SelectItem,\n SelectSeparator,\n SelectTrigger,\n SelectValue,\n} from '@arbidocs/react/ui'\nimport { KeyValueRow } from '../home/KeyValueRow'\nimport { ModalHeader } from '../settings/ModalScaffold'\n\n/** Inline error strip of a form. */\nexport function FormErrorBanner({\n message,\n testId,\n className,\n id,\n}: {\n message: string\n testId?: string\n className?: string\n /** Lets a field point at this message with `aria-describedby`. */\n id?: string\n}) {\n return (\n <div\n id={id}\n role=\"alert\"\n data-slot=\"form-error\"\n data-testid={testId}\n className={cn(\n 'flex items-center gap-2 rounded-md border border-red-border bg-red-bg p-3 text-sm text-red-text',\n className\n )}\n >\n <AlertCircle className=\"size-4 shrink-0\" aria-hidden=\"true\" />\n {message}\n </div>\n )\n}\n\n/** Right-aligned footer row of a form (Cancel + submit). */\nexport function FormActions({ className, children }: { className?: string; children: ReactNode }) {\n return (\n <div\n data-slot=\"form-actions\"\n className={cn('sticky bottom-0 flex justify-end gap-2 bg-background pt-2', className)}\n >\n {children}\n </div>\n )\n}\n\n/** Footer row of a modal body, separated by a rule. */\nexport function ModalActionRow({ children }: { children: ReactNode }) {\n return (\n <div\n data-slot=\"modal-action-row\"\n className=\"sticky bottom-0 -mx-6 -mb-6 flex flex-col-reverse gap-2 border-t border-border bg-background px-6 pb-6 pt-3 sm:flex-row sm:items-center sm:justify-end\"\n >\n {children}\n </div>\n )\n}\n\nexport interface WorkspaceFormModalProps {\n open: boolean\n onOpenChange: (open: boolean) => void\n title: ReactNode\n /** Icon before the title. */\n icon?: ReactNode\n /** Optional intro paragraph above the form (first-run welcome). */\n intro?: ReactNode\n testId?: string\n /** Visually hidden description. */\n description?: string\n children: ReactNode\n}\n\n/** Dialog frame of the create-workspace form: header, optional intro, scrolling body. */\nexport function WorkspaceFormModal({\n open,\n onOpenChange,\n title,\n icon,\n intro,\n testId,\n description = 'Create a new workspace',\n children,\n}: WorkspaceFormModalProps) {\n return (\n <Dialog open={open} onOpenChange={onOpenChange}>\n <DialogContent\n presentation=\"sheet\"\n className=\"flex max-h-panel w-modal max-w-modal-vw flex-col overflow-hidden p-0\"\n data-testid={testId}\n >\n <ModalHeader>\n <ModalTitleRow icon={icon} title={title} description={description} />\n </ModalHeader>\n <div className=\"min-h-0 flex-1 overflow-auto px-6 pb-6\">\n {intro && <p className=\"pb-4 text-sm text-muted-foreground\">{intro}</p>}\n {children}\n </div>\n </DialogContent>\n </Dialog>\n )\n}\n\nfunction ModalTitleRow({\n icon,\n title,\n description,\n}: {\n icon?: ReactNode\n title: ReactNode\n description: string\n}) {\n return (\n <>\n <DialogTitle>\n <div className=\"flex items-center gap-2\">\n {icon}\n <span>{title}</span>\n </div>\n </DialogTitle>\n <DialogDescription className=\"sr-only\">{description}</DialogDescription>\n </>\n )\n}\n\n/** One entry of the project picker: identity on the left, optional quota summary on the right. */\nexport function ProjectOptionRow({ identity, meta }: { identity: ReactNode; meta?: string }) {\n return (\n <div className=\"flex w-full min-w-0 items-center gap-2\">\n {identity}\n {meta && <span className=\"ml-auto truncate text-sm text-muted-foreground\">{meta}</span>}\n </div>\n )\n}\n\nexport interface ProjectPickerOption {\n id: string\n content: ReactNode\n}\n\nexport interface ProjectPickerProps {\n value?: string\n options: ProjectPickerOption[]\n onChange: (id: string) => void\n /**\n * `form` (default): the full-width field of the workspace form. `welcome`: the compact switcher\n * in the welcome dialog's quota header (muted pill, menu aligned to its end).\n */\n variant?: 'form' | 'welcome'\n /** Adds a \"Create new project...\" entry. */\n onCreate?: () => void\n disabled?: boolean\n readOnly?: boolean\n className?: string\n labels?: { placeholder: string; create: string }\n /** Trigger test id (default `workspace-project-select`, or `welcome-modal-project-select`). */\n testId?: string\n}\n\nconst CREATE_VALUE = '__create__'\n\n/** The one project picker: a workspace's owning project (optionally with a create entry), or the\n * welcome dialog's project switcher (`variant=\"welcome\"`). */\nexport function ProjectPicker({\n value,\n options,\n onChange,\n variant = 'form',\n onCreate,\n disabled,\n readOnly,\n className,\n labels = { placeholder: 'Select project', create: 'Create new project...' },\n testId,\n}: ProjectPickerProps) {\n const welcome = variant === 'welcome'\n return (\n <Select\n value={value ?? options[0]?.id}\n onValueChange={(v) => (v === CREATE_VALUE ? onCreate?.() : onChange(v))}\n disabled={disabled || readOnly}\n >\n <SelectTrigger\n className={cn(\n welcome &&\n 'h-7 w-auto max-w-[9.5rem] shrink-0 gap-1 border-none bg-muted px-2 text-xs font-medium pointer-coarse:h-11',\n className,\n readOnly && 'cursor-not-allowed'\n )}\n data-testid={\n testId ?? (welcome ? 'welcome-modal-project-select' : 'workspace-project-select')\n }\n >\n {welcome ? <SelectValue /> : <SelectValue placeholder={labels.placeholder} />}\n </SelectTrigger>\n <SelectContent align={welcome ? 'end' : undefined}>\n {options.map((o) => (\n <SelectItem key={o.id} value={o.id}>\n {o.content}\n </SelectItem>\n ))}\n {onCreate && (\n <>\n <SelectSeparator />\n <SelectItem value={CREATE_VALUE}>\n <div className=\"flex items-center gap-1.5 text-primary\">\n <Plus className=\"size-3.5\" />\n <span>{labels.create}</span>\n </div>\n </SelectItem>\n </>\n )}\n </SelectContent>\n </Select>\n )\n}\n\n/** Compact CTA on a project row (e.g. Upgrade / Change plan). */\nexport function ProjectActionButton({\n label,\n onClick,\n className,\n testId,\n}: {\n label: string\n onClick: () => void\n className?: string\n testId?: string\n}) {\n return (\n <Button\n type=\"button\"\n variant=\"outline\"\n size=\"sm\"\n onClick={onClick}\n className={cn(\n 'h-7 gap-1.5 whitespace-nowrap px-2 py-0 text-sm font-medium pointer-coarse:h-11',\n className\n )}\n data-testid={testId}\n >\n <ArrowUpRight className=\"size-3.5\" />\n {label}\n </Button>\n )\n}\n\nexport interface WorkspaceFieldsViewProps {\n /** `modal` (create flow) or `settings` (editing an existing workspace). */\n variant?: 'modal' | 'settings'\n name: string\n description: string\n onNameChange: (value: string) => void\n onDescriptionChange: (value: string) => void\n onNameBlur?: () => void\n onNameFocus?: () => void\n onDescriptionBlur?: () => void\n disabled?: boolean\n readOnly?: boolean\n maxNameLength?: number\n /** Id of the form's error message (a `FormErrorBanner id`): the name input is then `aria-invalid`\n * and described by it. */\n errorId?: string\n /** Content of the Visibility row (settings only); omit to hide the row. */\n visibility?: ReactNode\n /** Content of the Project row; omit to hide the row. */\n project?: ReactNode\n labels?: Partial<WorkspaceFieldsLabels>\n}\n\nexport interface WorkspaceFieldsLabels {\n readOnlyNotice: string\n name: string\n description: string\n visibility: string\n project: string\n over: (n: number) => string\n charsLeft: (n: number) => string\n}\n\nconst DEFAULT_LABELS: WorkspaceFieldsLabels = {\n readOnlyNotice: 'Read-only workspace',\n name: 'Name *',\n description: 'Description',\n visibility: 'Visibility',\n project: 'Project',\n over: (n) => `${n} over`,\n charsLeft: (n) => `${n} chars left`,\n}\n\n/** Name / description / visibility / project rows shared by the create and settings forms. */\nexport function WorkspaceFieldsView({\n variant = 'modal',\n name,\n description,\n onNameChange,\n onDescriptionChange,\n onNameBlur,\n onNameFocus,\n onDescriptionBlur,\n disabled = false,\n readOnly = false,\n errorId,\n maxNameLength = 50,\n visibility,\n project,\n labels,\n}: WorkspaceFieldsViewProps) {\n const workspaceDescriptionId = useId()\n const workspaceNameId = useId()\n const l = { ...DEFAULT_LABELS, ...labels }\n const [nameFocused, setNameFocused] = useState(false)\n const isModal = variant === 'modal'\n const charsLeft = maxNameLength - name.length\n // The modal only surfaces the counter near the limit; settings shows it while focused.\n const counterVisible = !readOnly && nameFocused && (!isModal || charsLeft <= 10)\n const isDisabled = isModal ? disabled : disabled || readOnly\n\n return (\n <div className=\"space-y-1\" data-slot=\"workspace-fields\">\n {readOnly && (\n <div data-testid=\"workspace-form-readonly-notice\" className=\"sr-only\">\n {l.readOnlyNotice}\n </div>\n )}\n <KeyValueRow label={l.name} icon={<FileText size={14} />} htmlFor={workspaceNameId}>\n <div className=\"relative\">\n <Input\n id={workspaceNameId}\n type=\"text\"\n value={name}\n onChange={(e) => onNameChange(e.target.value)}\n onBlur={() => {\n setNameFocused(false)\n onNameBlur?.()\n }}\n onFocus={() => {\n setNameFocused(true)\n onNameFocus?.()\n }}\n maxLength={maxNameLength}\n readOnly={readOnly}\n disabled={isDisabled}\n className={cn(\n isModal ? 'bg-background' : 'capitalize',\n readOnly && 'cursor-not-allowed',\n 'pr-20'\n )}\n required\n aria-invalid={errorId ? true : undefined}\n aria-describedby={errorId}\n data-testid=\"workspace-form-name-input\"\n />\n {counterVisible && (\n <div\n className={cn(\n 'pointer-events-none absolute right-3 top-1/2 hidden -translate-y-1/2 text-sm lg:block',\n charsLeft < 0 ? 'text-red-text' : 'text-muted-foreground'\n )}\n >\n {charsLeft < 0 ? l.over(-charsLeft) : l.charsLeft(charsLeft)}\n </div>\n )}\n </div>\n </KeyValueRow>\n\n <KeyValueRow\n label={l.description}\n icon={<AlignLeft size={14} />}\n htmlFor={workspaceDescriptionId}\n >\n <Input\n id={workspaceDescriptionId}\n type=\"text\"\n dictate\n value={description}\n onChange={(e) => onDescriptionChange(e.target.value)}\n onBlur={onDescriptionBlur}\n readOnly={readOnly}\n disabled={isDisabled}\n className={cn(isModal && 'bg-background', readOnly && 'cursor-not-allowed')}\n data-testid=\"workspace-form-description-input\"\n />\n </KeyValueRow>\n\n {visibility && (\n <KeyValueRow label={l.visibility} icon={<Globe size={14} />}>\n {visibility}\n </KeyValueRow>\n )}\n {project && (\n <KeyValueRow label={l.project} icon={<CreditCard size={14} />}>\n {project}\n </KeyValueRow>\n )}\n </div>\n )\n}\n","import {\n createContext,\n useContext,\n type HTMLAttributes,\n useMemo,\n type KeyboardEvent,\n type ReactNode,\n} from 'react'\nimport { Check, ChevronRight, FileText, MessagesSquare, Users } from 'lucide-react'\nimport { cn } from '@arbidocs/react/ui'\nimport { formatRelativeTime } from '@arbidocs/react/ui'\nimport { fmtDate } from '../lib/format'\nimport { ActionLink } from '../components/ActionLink'\nimport { MemberAvatarStack, type StackedMember } from '../components/MemberAvatarStack'\n\n/** Everything a workspace tile shows, source-agnostic (not the raw SDK shape). */\nexport interface WorkspaceSummary {\n id: string\n name: string\n description?: string | null\n /** Host-supplied line under the name (a reference, a client, a status...). Not interpreted. */\n subtitle?: ReactNode\n docCount: number\n /** Hidden when undefined, so a host without chats shows no empty counter. */\n chatCount?: number\n /** Number of visible members (agents excluded by the caller). */\n memberCount: number\n members: StackedMember[]\n /** The viewer may not see who is here (RLS): renders an em dash, not a `0`. */\n membersHidden?: boolean\n /** ISO timestamp: rendered as \"Updated {relative}\". */\n updatedAt?: string | null\n}\n\n/** Every fixed string of the workspace tile. Pass a partial `labels` to translate or reword. */\nexport interface WorkspaceCardLabels {\n /** The tile's accessible name. */\n openWorkspace: (name: string) => string\n currentWorkspace: string\n documents: string\n chats: string\n members: string\n /** `relative` is the formatted \"3 days ago\". */\n updated: (relative: string) => string\n}\n\nexport const DEFAULT_WORKSPACE_CARD_LABELS: WorkspaceCardLabels = {\n openWorkspace: (name) => `Open workspace ${name}`,\n currentWorkspace: 'Current workspace',\n documents: 'Documents',\n chats: 'Tasks',\n members: 'Members',\n updated: (relative) => `Updated ${relative}`,\n}\n\ninterface CardContextValue {\n current: boolean\n testId?: string\n labels: WorkspaceCardLabels\n}\n\nconst CardContext = createContext<CardContextValue>({\n current: false,\n labels: DEFAULT_WORKSPACE_CARD_LABELS,\n})\n\ntype DivProps = Omit<HTMLAttributes<HTMLDivElement>, 'children'>\n\n/* ------------------------------------------------------------------ */\n/* Parts */\n/* ------------------------------------------------------------------ */\n\nexport interface WorkspaceCardRootProps extends DivProps {\n /** This is the workspace you are in: accented surface, \"Current workspace\" cue. */\n current?: boolean\n onSelect: () => void\n /**\n * Real link target. The tile then renders as an anchor (ctrl-click / new tab, in-SPA through\n * the host environment's `linkComponent`); `onSelect` still fires on a plain click.\n */\n href?: string\n /** Accessible name; defaults to `labels.openWorkspace(name)` when composed via `WorkspaceCard`. */\n label: string\n testId?: string\n labels?: Partial<WorkspaceCardLabels>\n children: ReactNode\n}\n\n/**\n * The tile surface: one button that opens the workspace. A raised white card\n * (hairline border, soft shadow, hover lift); the current workspace takes the selection tint.\n */\nfunction WorkspaceCardRoot({\n current = false,\n onSelect,\n href,\n label,\n testId,\n labels,\n className,\n children,\n ...rest\n}: WorkspaceCardRootProps) {\n const mergedLabels = useMemo(() => ({ ...DEFAULT_WORKSPACE_CARD_LABELS, ...labels }), [labels])\n const surfaceClass = cn(\n '@container/ws-card flex min-h-40 w-full cursor-pointer flex-col gap-3 rounded-lg p-4 text-left transition-colors',\n 'focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring',\n current\n ? 'bg-accent text-accent-foreground'\n : 'border border-border bg-card shadow-xs transition-colors hover:border-ring/50 hover:bg-accent/40',\n className\n )\n const handleKeyDown = (event: KeyboardEvent<HTMLDivElement>) => {\n if (event.target !== event.currentTarget) return\n if (event.key === 'Enter' || event.key === ' ') {\n event.preventDefault()\n onSelect()\n }\n }\n return (\n <CardContext.Provider value={{ current, testId, labels: mergedLabels }}>\n {href ? (\n <ActionLink\n {...(rest as object)}\n href={href}\n onSelect={onSelect}\n aria-label={label}\n aria-current={current ? 'page' : undefined}\n data-slot=\"workspace-card\"\n data-testid={testId}\n data-active={current || undefined}\n className={surfaceClass}\n >\n {children}\n </ActionLink>\n ) : (\n <div\n {...rest}\n role=\"button\"\n tabIndex={0}\n aria-label={label}\n aria-current={current ? 'page' : undefined}\n data-slot=\"workspace-card\"\n data-testid={testId}\n data-active={current || undefined}\n onClick={onSelect}\n onKeyDown={handleKeyDown}\n className={surfaceClass}\n >\n {children}\n </div>\n )}\n </CardContext.Provider>\n )\n}\n\n/** Mark + name + open cue, on one row. Put the entity mark first. */\nfunction WorkspaceCardHeader({ className, children, ...rest }: DivProps & { children: ReactNode }) {\n return (\n <div\n {...rest}\n className={cn('flex flex-wrap items-center gap-x-3 gap-y-2', className)}\n data-slot=\"workspace-card-header\"\n >\n {children}\n </div>\n )\n}\n\nfunction WorkspaceCardTitle({ children, className }: { children: ReactNode; className?: string }) {\n const { testId } = useContext(CardContext)\n return (\n <h3\n className={cn(\n 'line-clamp-2 min-w-24 flex-1 break-words text-base font-semibold leading-tight text-foreground',\n className\n )}\n data-slot=\"workspace-card-title\"\n data-testid={testId && `${testId}-title`}\n >\n {children}\n </h3>\n )\n}\n\n/**\n * The open cue is always on screen (never hover-only): a chevron, or the words\n * \"Current workspace\" on the one you are in.\n */\nfunction WorkspaceCardOpenCue({\n testId,\n currentLabel,\n}: {\n /** Deliberately separate from the card id: suites count cards by prefix. */\n testId?: string\n /** Overrides `labels.currentWorkspace`. */\n currentLabel?: string\n}) {\n const { current, labels } = useContext(CardContext)\n return (\n <span\n className=\"inline-flex max-w-full min-w-0 shrink-0 items-center text-sm text-muted-foreground\"\n data-slot=\"workspace-card-open-cue\"\n data-testid={testId}\n >\n {current ? (\n // Never wider than the card: the words truncate, and in a card narrower than 20rem\n // the pill shrinks to a check (the words stay as the accessible name).\n <span className=\"inline-flex max-w-full min-w-0 items-center gap-1 rounded-full bg-background px-2 py-0.5 text-xs font-medium text-foreground\">\n <Check className=\"hidden size-3 shrink-0 @max-xs/ws-card:block\" aria-hidden=\"true\" />\n <span className=\"min-w-0 truncate @max-xs/ws-card:sr-only\">\n {currentLabel ?? labels.currentWorkspace}\n </span>\n </span>\n ) : (\n <ChevronRight className=\"size-4\" aria-hidden=\"true\" />\n )}\n </span>\n )\n}\n\nfunction WorkspaceCardDescription({\n children,\n className,\n}: {\n children: ReactNode\n className?: string\n}) {\n return (\n <p\n className={cn('line-clamp-2 text-sm text-muted-foreground', className)}\n title={typeof children === 'string' ? children : undefined}\n data-slot=\"workspace-card-description\"\n >\n {children}\n </p>\n )\n}\n\n/** Host-supplied line under the title. */\nfunction WorkspaceCardSubtitle({\n className,\n children,\n ...rest\n}: DivProps & { children: ReactNode }) {\n return (\n <div\n {...rest}\n className={cn('truncate text-xs text-muted-foreground', className)}\n data-slot=\"workspace-card-subtitle\"\n >\n {children}\n </div>\n )\n}\n\n/** Footer block: stats row and meta line, pinned to the bottom of the tile. */\nfunction WorkspaceCardFooter({ className, children, ...rest }: DivProps & { children: ReactNode }) {\n return (\n <div {...rest} className={cn('mt-auto flex flex-col gap-2', className)}>\n {children}\n </div>\n )\n}\n\nexport interface WorkspaceCardStatsProps {\n docCount: number\n /** Omit to hide the chats counter. */\n chatCount?: number\n memberCount: number\n members?: StackedMember[]\n membersHidden?: boolean\n /** Faces before the rest collapse into `+N`. */\n maxAvatars?: number\n className?: string\n}\n\n/** Documents / chats / members counts, with the member faces at the trailing edge. */\nfunction WorkspaceCardStats({\n docCount,\n chatCount,\n memberCount,\n members = [],\n membersHidden = false,\n maxAvatars = 3,\n className,\n}: WorkspaceCardStatsProps) {\n const { current, testId, labels } = useContext(CardContext)\n return (\n <div\n className={cn('flex w-full items-center gap-x-4 text-sm text-muted-foreground', className)}\n data-slot=\"workspace-card-stats\"\n >\n <span className=\"inline-flex items-center gap-1.5\" title={labels.documents}>\n <FileText className=\"size-4\" aria-hidden=\"true\" />\n <span className=\"tabular-nums\">{docCount.toLocaleString()}</span>\n </span>\n {chatCount !== undefined && (\n <span className=\"inline-flex items-center gap-1.5\" title={labels.chats}>\n <MessagesSquare className=\"size-4\" aria-hidden=\"true\" />\n <span className=\"tabular-nums\">{chatCount.toLocaleString()}</span>\n </span>\n )}\n <span className=\"inline-flex items-center gap-1.5\" title={labels.members}>\n <Users className=\"size-4\" aria-hidden=\"true\" />\n <span className=\"tabular-nums\" data-testid={testId && `${testId}-member-count`}>\n {membersHidden ? '—' : memberCount}\n </span>\n </span>\n <MemberAvatarStack\n members={members}\n total={memberCount}\n max={maxAvatars}\n hidden={membersHidden}\n ringClassName={current ? 'ring-accent' : 'ring-muted'}\n label={labels.members}\n className=\"ml-auto\"\n testId={testId && `${testId}-member-avatars`}\n />\n </div>\n )\n}\n\n/** \"Updated 3 days ago\", with the exact date on the title. */\nfunction WorkspaceCardMeta({ updatedAt }: { updatedAt: string }) {\n const { labels } = useContext(CardContext)\n return (\n <span\n className=\"min-w-0 max-w-full self-start truncate text-xs text-muted-foreground\"\n title={fmtDate(updatedAt)}\n data-slot=\"workspace-card-meta\"\n >\n {labels.updated(formatRelativeTime(updatedAt))}\n </span>\n )\n}\n\n/* ------------------------------------------------------------------ */\n/* Default composition */\n/* ------------------------------------------------------------------ */\n\nexport interface WorkspaceCardProps {\n workspace: WorkspaceSummary\n current?: boolean\n onSelect: () => void\n /** Real link target; see `WorkspaceCard.Root`. */\n href?: string\n /** The entity mark shown before the name (the host's own workspace glyph). */\n mark?: ReactNode\n /** Card id; derived ids: `-title`, `-member-count`, `-member-avatars`. */\n testId?: string\n /** Id for the open cue (kept apart from `testId`, see `WorkspaceCard.OpenCue`). */\n openCueTestId?: string\n maxAvatars?: number\n /**\n * The stats row: omit for the default counts + member faces, `false` to hide it, or any node to\n * replace it.\n */\n stats?: ReactNode | false\n /** Reword the tile's fixed strings. */\n labels?: Partial<WorkspaceCardLabels>\n className?: string\n}\n\n/**\n * The workspace tile: mark + name + open cue, description, stats and meta.\n * The whole tile opens the workspace; nothing on it is hover-only.\n *\n * Need a different layout? Compose the parts: `WorkspaceCard.Root`, `.Header`,\n * `.Title`, `.OpenCue`, `.Subtitle`, `.Description`, `.Footer`, `.Stats`, `.Meta`.\n */\nfunction WorkspaceCardBase({\n workspace,\n current = false,\n onSelect,\n href,\n mark,\n testId,\n openCueTestId,\n maxAvatars,\n stats,\n labels,\n className,\n}: WorkspaceCardProps) {\n const mergedLabels = { ...DEFAULT_WORKSPACE_CARD_LABELS, ...labels }\n return (\n <WorkspaceCardRoot\n current={current}\n onSelect={onSelect}\n href={href}\n label={mergedLabels.openWorkspace(workspace.name)}\n labels={labels}\n testId={testId}\n className={className}\n >\n <WorkspaceCardHeader>\n {mark}\n <WorkspaceCardTitle>{workspace.name}</WorkspaceCardTitle>\n <WorkspaceCardOpenCue testId={openCueTestId} />\n </WorkspaceCardHeader>\n {workspace.subtitle && <WorkspaceCardSubtitle>{workspace.subtitle}</WorkspaceCardSubtitle>}\n {workspace.description && (\n <WorkspaceCardDescription>{workspace.description}</WorkspaceCardDescription>\n )}\n <WorkspaceCardFooter>\n {stats === undefined ? (\n <WorkspaceCardStats\n docCount={workspace.docCount}\n chatCount={workspace.chatCount}\n memberCount={workspace.memberCount}\n members={workspace.members}\n membersHidden={workspace.membersHidden}\n maxAvatars={maxAvatars}\n />\n ) : (\n stats\n )}\n {workspace.updatedAt && <WorkspaceCardMeta updatedAt={workspace.updatedAt} />}\n </WorkspaceCardFooter>\n </WorkspaceCardRoot>\n )\n}\n\nexport const WorkspaceCard = Object.assign(WorkspaceCardBase, {\n Root: WorkspaceCardRoot,\n Header: WorkspaceCardHeader,\n Title: WorkspaceCardTitle,\n OpenCue: WorkspaceCardOpenCue,\n Subtitle: WorkspaceCardSubtitle,\n Description: WorkspaceCardDescription,\n Footer: WorkspaceCardFooter,\n Stats: WorkspaceCardStats,\n Meta: WorkspaceCardMeta,\n})\n","import type { ReactNode } from 'react'\nimport { ChevronRight } from 'lucide-react'\nimport { cn } from '@arbidocs/react/ui'\nimport { CollapsibleSection } from '../home/CollapsibleSection'\n\nexport interface WorkspaceListProps {\n children: ReactNode\n className?: string\n testId?: string\n}\n\n/** The column that stacks workspace groups (padding follows the page gutter). */\nexport function WorkspaceList({ children, className, testId }: WorkspaceListProps) {\n return (\n <div\n className={cn('flex w-full flex-col gap-2 px-4 py-4 sm:px-8', className)}\n data-slot=\"workspace-list\"\n data-testid={testId}\n >\n {children}\n </div>\n )\n}\n\nexport interface WorkspaceGroupProps {\n /** Group heading: name, count, badges. Plain text on the canvas, no band. */\n title: ReactNode\n isExpanded: boolean\n onToggle: () => void\n /**\n * Makes the whole header one target (e.g. open the project panel); the\n * chevron stays a separate toggle. Adds a trailing `openLabel` affordance.\n */\n onOpen?: () => void\n /** Words beside the trailing chevron when `onOpen` is set, e.g. \"Plans & Usage\". */\n openLabel?: string\n /** Muted words on the right of a collapsed group without `onOpen`, e.g. \"Show 11 shared workspaces\". */\n collapsedHint?: string\n /** The cards, laid out in a responsive grid (1 / 2 / 3 columns). */\n children: ReactNode\n className?: string\n}\n\n/**\n * One collapsible band of workspace tiles under a slim header. The open\n * affordance is always visible, so nothing is reachable by hover alone.\n */\nexport function WorkspaceGroup({\n title,\n isExpanded,\n onToggle,\n onOpen,\n openLabel,\n collapsedHint,\n children,\n className,\n}: WorkspaceGroupProps) {\n return (\n <CollapsibleSection\n title={title}\n isExpanded={isExpanded}\n onToggle={onToggle}\n onHeaderClick={onOpen}\n rightContent={\n onOpen && openLabel ? (\n <span className=\"flex shrink-0 items-center gap-1 text-sm font-medium text-muted-foreground\">\n {openLabel}\n <ChevronRight className=\"size-4 shrink-0\" aria-hidden=\"true\" />\n </span>\n ) : collapsedHint && !isExpanded ? (\n <span className=\"shrink-0 text-sm text-muted-foreground\">{collapsedHint}</span>\n ) : undefined\n }\n className={cn('group', className)}\n headerClassName=\"mb-3 flex-wrap gap-y-2 rounded-md px-1 py-1 pointer-coarse:min-h-11\"\n childrenClassName=\"mb-8 grid gap-3 @xl:grid-cols-2 @5xl:grid-cols-3\"\n >\n {children}\n </CollapsibleSection>\n )\n}\n","/**\n * WorkspaceTypeBadge: a workspace's type badge (private, shared or public: icon, colour, label).\n */\n\nimport { User, Users, Globe } from 'lucide-react'\nimport type { components } from '@arbidocs/client'\nimport { WorkspaceTypeBadgeView } from './WorkspaceBadges'\nimport { getHumanUserCount, getVariantBgClass, getWorkspaceTypeInfo } from './workspace-type'\n\ntype Workspace = Pick<components['schemas']['WorkspaceResponse'], 'is_public' | 'users'>\n\nexport interface WorkspaceTypeBadgeProps {\n workspace: Workspace\n showTooltip?: boolean\n size?: 'sm' | 'md'\n isSelected?: boolean\n className?: string\n}\n\nexport function WorkspaceTypeBadge({\n workspace,\n showTooltip = false,\n size = 'md',\n isSelected = false,\n className,\n}: WorkspaceTypeBadgeProps) {\n const userCount = getHumanUserCount(workspace.users)\n const { type, variant } = getWorkspaceTypeInfo(workspace.is_public, userCount)\n const icon = workspace.is_public ? Globe : userCount > 1 ? Users : User\n\n return (\n <WorkspaceTypeBadgeView\n icon={icon}\n bgClass={getVariantBgClass(variant)}\n typeLabel={type}\n showTooltip={showTooltip}\n size={size}\n isSelected={isSelected}\n className={className}\n />\n )\n}\n"]}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use client";
|
|
2
2
|
import { DataTable } from './chunk-SLRVI2YU.js';
|
|
3
|
-
import { ActionLink } from './chunk-
|
|
3
|
+
import { ActionLink } from './chunk-SUDPZ5IQ.js';
|
|
4
4
|
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
5
5
|
import { cn, Card } from '@arbidocs/react/ui';
|
|
6
6
|
import { ArrowUpRight, ArrowDownRight } from 'lucide-react';
|
|
@@ -151,5 +151,5 @@ function StatGroup({ items, testId }) {
|
|
|
151
151
|
}
|
|
152
152
|
|
|
153
153
|
export { DataTableBlock, MetricCard, PageHeader, StatGroup };
|
|
154
|
-
//# sourceMappingURL=chunk-
|
|
155
|
-
//# sourceMappingURL=chunk-
|
|
154
|
+
//# sourceMappingURL=chunk-XL55UDLO.js.map
|
|
155
|
+
//# sourceMappingURL=chunk-XL55UDLO.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/components/DataTableBlock.tsx","../src/components/PageHeader.tsx","../src/components/MetricCard.tsx","../src/components/StatGroup.tsx"],"names":["jsxs","jsx","cn"],"mappings":"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","file":"chunk-UAFP562F.js","sourcesContent":["/**\n * A **serializable** data table for the Puck builder.\n *\n * The library's developer-facing {@link DataTable} is driven by `Column<T>` whose\n * `header`/`render` are React nodes and functions — powerful, but non-serializable,\n * so it can never be a Puck block. `DataTableBlock` closes that gap with a flat,\n * JSON-safe schema (string headers, string field keys, string cells) and rebuilds\n * the non-serializable `Column<Row>[]` internally, rendering through the very same\n * {@link DataTable} so it inherits the library's markup and tokens verbatim.\n */\nimport { DataTable, type Column } from './DataTable'\n\nexport interface DataTableBlockColumn {\n /** Column heading text. */\n header: string\n /** Key used to look a cell up in each row record. */\n field: string\n /** Cell/heading alignment. */\n align?: 'left' | 'right' | 'center'\n}\n\nexport interface DataTableBlockProps {\n /** Serializable column schema. */\n columns: DataTableBlockColumn[]\n /** One record per row; cells are looked up by each column's `field`. */\n rows: Array<Record<string, string>>\n /** Optional caption rendered above the table. */\n caption?: string\n /** Empty-state title shown when there are no rows. */\n emptyText?: string\n /** testid area prefix; also set on the wrapper element. */\n testId?: string\n}\n\n/** A row wrapper so {@link DataTable} gets a stable id without polluting the record. */\ninterface TableRowData {\n __id: string\n cells: Record<string, string>\n}\n\n/**\n * Renders a {@link DataTable} from a flat, serializable schema. Columns are mapped\n * to `Column<TableRowData>[]` (header string, positional-stable key, alignment) and\n * each cell is resolved by `field`; rows carry a synthetic id for React keys/testids.\n */\nexport function DataTableBlock({ columns, rows, caption, emptyText, testId }: DataTableBlockProps) {\n const area = testId ?? 'data-table-block'\n\n const tableColumns: Column<TableRowData>[] = columns.map((col, index) => ({\n key: col.field || `col-${index}`,\n header: col.header,\n align: col.align,\n render: (row) => row.cells[col.field] ?? '',\n }))\n\n const tableRows: TableRowData[] = rows.map((cells, index) => ({ __id: String(index), cells }))\n\n return (\n <div data-testid={testId}>\n {caption ? (\n <p\n className=\"mb-2 text-sm text-muted-foreground\"\n data-testid={testId ? `${testId}-caption` : undefined}\n >\n {caption}\n </p>\n ) : null}\n <DataTable\n columns={tableColumns}\n rows={tableRows}\n getRowId={(row) => row.__id}\n area={area}\n emptyTitle={emptyText}\n />\n </div>\n )\n}\n","import type { ReactNode } from 'react'\nimport { cn } from '@arbidocs/react/ui'\n\nexport interface PageHeaderProps {\n title: ReactNode\n eyebrow?: ReactNode\n description?: ReactNode\n /** Before the title block: a back button, an avatar or an icon. */\n leading?: ReactNode\n actions?: ReactNode\n /** Under the whole header: a tab strip or segmented control. */\n tabs?: ReactNode\n className?: string\n testId?: string\n}\n\n/** Standard page title block: leading + eyebrow + title + description + actions, then tabs. */\nexport function PageHeader({\n title,\n eyebrow,\n description,\n leading,\n actions,\n tabs,\n className,\n testId,\n}: PageHeaderProps) {\n return (\n <div className={cn('flex flex-col gap-3', className)} data-testid={testId}>\n <div className=\"flex flex-col gap-3 sm:flex-row sm:items-end sm:justify-between\">\n <div className=\"flex min-w-0 items-center gap-3\">\n {leading && (\n <div className=\"shrink-0\" data-slot=\"page-header-leading\">\n {leading}\n </div>\n )}\n <div className=\"min-w-0\">\n {eyebrow && (\n <p className=\"mb-1 text-xs font-semibold uppercase tracking-wider text-muted-foreground\">\n {eyebrow}\n </p>\n )}\n <h1 className=\"font-display text-2xl font-semibold tracking-tight text-foreground\">\n {title}\n </h1>\n {description && (\n <p className=\"mt-1 max-w-2xl text-sm text-muted-foreground\">{description}</p>\n )}\n </div>\n </div>\n {actions && <div className=\"flex shrink-0 items-center gap-2\">{actions}</div>}\n </div>\n {tabs && <div data-slot=\"page-header-tabs\">{tabs}</div>}\n </div>\n )\n}\n","import type { ReactNode } from 'react'\nimport type { LucideIcon } from 'lucide-react'\nimport { ArrowDownRight, ArrowUpRight } from 'lucide-react'\nimport { Card, cn } from '@arbidocs/react/ui'\nimport { ActionLink } from './ActionLink'\n\nexport interface MetricCardProps {\n label: ReactNode\n value: ReactNode\n icon?: LucideIcon\n hint?: ReactNode\n delta?: { value: string; direction: 'up' | 'down'; good?: boolean }\n /**\n * Icon accent as a theme colour-token key (e.g. `primary`, `success`, or the host's own brand\n * token). Resolved to `var(--color-<accent>)` at render. `'default'` inherits `foreground`.\n */\n accent?: string\n /** Show a placeholder instead of the value (the figure is still being fetched). */\n isLoading?: boolean\n /** Makes the tile a real link (ctrl/cmd-click works). */\n href?: string\n /** Click handler; with `href`, a plain click calls it instead of navigating. */\n onSelect?: () => void\n className?: string\n testId?: string\n}\n\n/** The one true KPI tile. Used across every dashboard and module header. */\nexport function MetricCard({\n label,\n value,\n icon: Icon,\n hint,\n delta,\n accent = 'default',\n isLoading = false,\n href,\n onSelect,\n className,\n testId,\n}: MetricCardProps) {\n const accentStyle =\n accent && accent !== 'default' ? { color: `var(--color-${accent})` } : undefined\n const deltaGood = delta?.good ?? delta?.direction === 'up'\n const isInteractive = Boolean(href || onSelect)\n const card = (\n <Card\n variant=\"elevated\"\n className={cn('card-hover min-w-0 rounded-xl p-5', className)}\n data-testid={isInteractive ? undefined : testId}\n aria-busy={isLoading || undefined}\n >\n <div className=\"flex items-start justify-between gap-3\">\n <p className=\"min-w-0 text-xs font-medium uppercase tracking-wide text-muted-foreground\">\n {label}\n </p>\n {Icon && <Icon className=\"size-4 shrink-0\" style={accentStyle} />}\n </div>\n {isLoading ? (\n <div\n className=\"mt-2 h-8 w-20 animate-pulse rounded bg-muted\"\n data-slot=\"metric-card-skeleton\"\n />\n ) : (\n <p\n className=\"mt-2 font-display text-2xl font-semibold tracking-tight [overflow-wrap:anywhere]\"\n data-testid={testId && `${testId}-value`}\n >\n {value}\n </p>\n )}\n <div className=\"mt-1 flex items-center gap-2\">\n {delta && !isLoading && (\n <span\n className={cn(\n 'inline-flex items-center gap-0.5 text-xs font-medium',\n deltaGood ? 'text-success' : 'text-destructive'\n )}\n >\n {delta.direction === 'up' ? (\n <ArrowUpRight className=\"size-3\" />\n ) : (\n <ArrowDownRight className=\"size-3\" />\n )}\n {delta.value}\n </span>\n )}\n {hint && <span className=\"text-xs text-muted-foreground\">{hint}</span>}\n </div>\n </Card>\n )\n if (!isInteractive) return card\n return (\n <ActionLink\n href={href}\n onSelect={onSelect}\n className=\"block rounded-xl text-left focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring\"\n data-testid={testId}\n >\n {card}\n </ActionLink>\n )\n}\n","import { cn } from '@arbidocs/react/ui'\n\nexport interface StatItem {\n value: string\n label: string\n /** Optional caption under the label (e.g. a qualifier or unit). */\n sub?: string\n}\n\nexport interface StatGroupProps {\n items: StatItem[]\n testId?: string\n}\n\nconst GRID: Record<number, string> = {\n 1: 'grid-cols-1',\n 2: 'grid-cols-2',\n 3: 'grid-cols-2 sm:grid-cols-3',\n 4: 'grid-cols-2 lg:grid-cols-4',\n}\n\n/** Big-number stat group — headline metrics with captions. */\nexport function StatGroup({ items, testId }: StatGroupProps) {\n const list = items ?? []\n const cols = GRID[Math.min(list.length, 4)] ?? GRID[4]\n return (\n <dl className={cn('grid gap-8', cols)} data-testid={testId}>\n {list.map((item, i) => (\n <div key={i} className=\"min-w-0 text-center\" data-testid={testId && `${testId}-item-${i}`}>\n <dt className=\"sr-only\">{item.label}</dt>\n <dd className=\"text-4xl font-semibold tracking-tight [overflow-wrap:anywhere] sm:text-5xl\">\n {item.value}\n </dd>\n <p className=\"mt-2 text-sm text-muted-foreground\">{item.label}</p>\n {item.sub && <p className=\"mt-1 text-xs text-muted-foreground/80\">{item.sub}</p>}\n </div>\n ))}\n </dl>\n )\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/components/DataTableBlock.tsx","../src/components/PageHeader.tsx","../src/components/MetricCard.tsx","../src/components/StatGroup.tsx"],"names":["jsxs","jsx","cn"],"mappings":"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","file":"chunk-XL55UDLO.js","sourcesContent":["/**\n * A **serializable** data table for the Puck builder.\n *\n * The library's developer-facing {@link DataTable} is driven by `Column<T>` whose\n * `header`/`render` are React nodes and functions — powerful, but non-serializable,\n * so it can never be a Puck block. `DataTableBlock` closes that gap with a flat,\n * JSON-safe schema (string headers, string field keys, string cells) and rebuilds\n * the non-serializable `Column<Row>[]` internally, rendering through the very same\n * {@link DataTable} so it inherits the library's markup and tokens verbatim.\n */\nimport { DataTable, type Column } from './DataTable'\n\nexport interface DataTableBlockColumn {\n /** Column heading text. */\n header: string\n /** Key used to look a cell up in each row record. */\n field: string\n /** Cell/heading alignment. */\n align?: 'left' | 'right' | 'center'\n}\n\nexport interface DataTableBlockProps {\n /** Serializable column schema. */\n columns: DataTableBlockColumn[]\n /** One record per row; cells are looked up by each column's `field`. */\n rows: Array<Record<string, string>>\n /** Optional caption rendered above the table. */\n caption?: string\n /** Empty-state title shown when there are no rows. */\n emptyText?: string\n /** testid area prefix; also set on the wrapper element. */\n testId?: string\n}\n\n/** A row wrapper so {@link DataTable} gets a stable id without polluting the record. */\ninterface TableRowData {\n __id: string\n cells: Record<string, string>\n}\n\n/**\n * Renders a {@link DataTable} from a flat, serializable schema. Columns are mapped\n * to `Column<TableRowData>[]` (header string, positional-stable key, alignment) and\n * each cell is resolved by `field`; rows carry a synthetic id for React keys/testids.\n */\nexport function DataTableBlock({ columns, rows, caption, emptyText, testId }: DataTableBlockProps) {\n const area = testId ?? 'data-table-block'\n\n const tableColumns: Column<TableRowData>[] = columns.map((col, index) => ({\n key: col.field || `col-${index}`,\n header: col.header,\n align: col.align,\n render: (row) => row.cells[col.field] ?? '',\n }))\n\n const tableRows: TableRowData[] = rows.map((cells, index) => ({ __id: String(index), cells }))\n\n return (\n <div data-testid={testId}>\n {caption ? (\n <p\n className=\"mb-2 text-sm text-muted-foreground\"\n data-testid={testId ? `${testId}-caption` : undefined}\n >\n {caption}\n </p>\n ) : null}\n <DataTable\n columns={tableColumns}\n rows={tableRows}\n getRowId={(row) => row.__id}\n area={area}\n emptyTitle={emptyText}\n />\n </div>\n )\n}\n","import type { ReactNode } from 'react'\nimport { cn } from '@arbidocs/react/ui'\n\nexport interface PageHeaderProps {\n title: ReactNode\n eyebrow?: ReactNode\n description?: ReactNode\n /** Before the title block: a back button, an avatar or an icon. */\n leading?: ReactNode\n actions?: ReactNode\n /** Under the whole header: a tab strip or segmented control. */\n tabs?: ReactNode\n className?: string\n testId?: string\n}\n\n/** Standard page title block: leading + eyebrow + title + description + actions, then tabs. */\nexport function PageHeader({\n title,\n eyebrow,\n description,\n leading,\n actions,\n tabs,\n className,\n testId,\n}: PageHeaderProps) {\n return (\n <div className={cn('flex flex-col gap-3', className)} data-testid={testId}>\n <div className=\"flex flex-col gap-3 sm:flex-row sm:items-end sm:justify-between\">\n <div className=\"flex min-w-0 items-center gap-3\">\n {leading && (\n <div className=\"shrink-0\" data-slot=\"page-header-leading\">\n {leading}\n </div>\n )}\n <div className=\"min-w-0\">\n {eyebrow && (\n <p className=\"mb-1 text-xs font-semibold uppercase tracking-wider text-muted-foreground\">\n {eyebrow}\n </p>\n )}\n <h1 className=\"font-display text-2xl font-semibold tracking-tight text-foreground\">\n {title}\n </h1>\n {description && (\n <p className=\"mt-1 max-w-2xl text-sm text-muted-foreground\">{description}</p>\n )}\n </div>\n </div>\n {actions && <div className=\"flex shrink-0 items-center gap-2\">{actions}</div>}\n </div>\n {tabs && <div data-slot=\"page-header-tabs\">{tabs}</div>}\n </div>\n )\n}\n","import type { ReactNode } from 'react'\nimport type { LucideIcon } from 'lucide-react'\nimport { ArrowDownRight, ArrowUpRight } from 'lucide-react'\nimport { Card, cn } from '@arbidocs/react/ui'\nimport { ActionLink } from './ActionLink'\n\nexport interface MetricCardProps {\n label: ReactNode\n value: ReactNode\n icon?: LucideIcon\n hint?: ReactNode\n delta?: { value: string; direction: 'up' | 'down'; good?: boolean }\n /**\n * Icon accent as a theme colour-token key (e.g. `primary`, `success`, or the host's own brand\n * token). Resolved to `var(--color-<accent>)` at render. `'default'` inherits `foreground`.\n */\n accent?: string\n /** Show a placeholder instead of the value (the figure is still being fetched). */\n isLoading?: boolean\n /** Makes the tile a real link (ctrl/cmd-click works). */\n href?: string\n /** Click handler; with `href`, a plain click calls it instead of navigating. */\n onSelect?: () => void\n className?: string\n testId?: string\n}\n\n/** The one true KPI tile. Used across every dashboard and module header. */\nexport function MetricCard({\n label,\n value,\n icon: Icon,\n hint,\n delta,\n accent = 'default',\n isLoading = false,\n href,\n onSelect,\n className,\n testId,\n}: MetricCardProps) {\n const accentStyle =\n accent && accent !== 'default' ? { color: `var(--color-${accent})` } : undefined\n const deltaGood = delta?.good ?? delta?.direction === 'up'\n const isInteractive = Boolean(href || onSelect)\n const card = (\n <Card\n variant=\"elevated\"\n className={cn('card-hover min-w-0 rounded-xl p-5', className)}\n data-testid={isInteractive ? undefined : testId}\n aria-busy={isLoading || undefined}\n >\n <div className=\"flex items-start justify-between gap-3\">\n <p className=\"min-w-0 text-xs font-medium uppercase tracking-wide text-muted-foreground\">\n {label}\n </p>\n {Icon && <Icon className=\"size-4 shrink-0\" style={accentStyle} />}\n </div>\n {isLoading ? (\n <div\n className=\"mt-2 h-8 w-20 animate-pulse rounded bg-muted\"\n data-slot=\"metric-card-skeleton\"\n />\n ) : (\n <p\n className=\"mt-2 font-display text-2xl font-semibold tracking-tight [overflow-wrap:anywhere]\"\n data-testid={testId && `${testId}-value`}\n >\n {value}\n </p>\n )}\n <div className=\"mt-1 flex items-center gap-2\">\n {delta && !isLoading && (\n <span\n className={cn(\n 'inline-flex items-center gap-0.5 text-xs font-medium',\n deltaGood ? 'text-success' : 'text-destructive'\n )}\n >\n {delta.direction === 'up' ? (\n <ArrowUpRight className=\"size-3\" />\n ) : (\n <ArrowDownRight className=\"size-3\" />\n )}\n {delta.value}\n </span>\n )}\n {hint && <span className=\"text-xs text-muted-foreground\">{hint}</span>}\n </div>\n </Card>\n )\n if (!isInteractive) return card\n return (\n <ActionLink\n href={href}\n onSelect={onSelect}\n className=\"block rounded-xl text-left focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring\"\n data-testid={testId}\n >\n {card}\n </ActionLink>\n )\n}\n","import { cn } from '@arbidocs/react/ui'\n\nexport interface StatItem {\n value: string\n label: string\n /** Optional caption under the label (e.g. a qualifier or unit). */\n sub?: string\n}\n\nexport interface StatGroupProps {\n items: StatItem[]\n testId?: string\n}\n\nconst GRID: Record<number, string> = {\n 1: 'grid-cols-1',\n 2: 'grid-cols-2',\n 3: 'grid-cols-2 sm:grid-cols-3',\n 4: 'grid-cols-2 lg:grid-cols-4',\n}\n\n/** Big-number stat group — headline metrics with captions. */\nexport function StatGroup({ items, testId }: StatGroupProps) {\n const list = items ?? []\n const cols = GRID[Math.min(list.length, 4)] ?? GRID[4]\n return (\n <dl className={cn('grid gap-8', cols)} data-testid={testId}>\n {list.map((item, i) => (\n <div key={i} className=\"min-w-0 text-center\" data-testid={testId && `${testId}-item-${i}`}>\n <dt className=\"sr-only\">{item.label}</dt>\n <dd className=\"text-4xl font-semibold tracking-tight [overflow-wrap:anywhere] sm:text-5xl\">\n {item.value}\n </dd>\n <p className=\"mt-2 text-sm text-muted-foreground\">{item.label}</p>\n {item.sub && <p className=\"mt-1 text-xs text-muted-foreground/80\">{item.sub}</p>}\n </div>\n ))}\n </dl>\n )\n}\n"]}
|