@contractspec/lib.example-shared-ui 6.0.5 → 6.0.7
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/.turbo/turbo-build.log +90 -84
- package/AGENTS.md +43 -25
- package/CHANGELOG.md +11 -0
- package/README.md +63 -35
- package/dist/EvolutionDashboard.js +9 -9
- package/dist/EvolutionSidebar.js +15 -15
- package/dist/LocalDataIndicator.js +3 -3
- package/dist/MarkdownView.d.ts +0 -7
- package/dist/MarkdownView.js +76 -172
- package/dist/PersonalizationInsights.js +12 -12
- package/dist/SaveToStudioButton.js +2 -2
- package/dist/SpecDrivenTemplateShell.d.ts +1 -1
- package/dist/SpecDrivenTemplateShell.js +10 -10
- package/dist/SpecEditorPanel.js +3 -3
- package/dist/TemplateShell.js +10 -10
- package/dist/browser/EvolutionDashboard.js +9 -9
- package/dist/browser/EvolutionSidebar.js +15 -15
- package/dist/browser/LocalDataIndicator.js +3 -3
- package/dist/browser/MarkdownView.js +76 -172
- package/dist/browser/PersonalizationInsights.js +12 -12
- package/dist/browser/SaveToStudioButton.js +2 -2
- package/dist/browser/SpecDrivenTemplateShell.js +10 -10
- package/dist/browser/SpecEditorPanel.js +3 -3
- package/dist/browser/TemplateShell.js +10 -10
- package/dist/browser/hooks/index.js +29 -29
- package/dist/browser/index.js +193 -286
- package/dist/browser/lib/component-registry.js +1 -1
- package/dist/browser/markdown/formatPresentationName.js +9 -0
- package/dist/browser/markdown/useMarkdownPresentation.js +65 -0
- package/dist/hooks/index.d.ts +3 -3
- package/dist/hooks/index.js +29 -29
- package/dist/index.d.ts +12 -11
- package/dist/index.js +193 -286
- package/dist/lib/component-registry.js +1 -1
- package/dist/markdown/formatPresentationName.d.ts +1 -0
- package/dist/markdown/formatPresentationName.js +10 -0
- package/dist/markdown/useMarkdownPresentation.d.ts +21 -0
- package/dist/markdown/useMarkdownPresentation.js +66 -0
- package/dist/node/EvolutionDashboard.js +9 -9
- package/dist/node/EvolutionSidebar.js +15 -15
- package/dist/node/LocalDataIndicator.js +3 -3
- package/dist/node/MarkdownView.js +76 -172
- package/dist/node/PersonalizationInsights.js +12 -12
- package/dist/node/SaveToStudioButton.js +2 -2
- package/dist/node/SpecDrivenTemplateShell.js +10 -10
- package/dist/node/SpecEditorPanel.js +3 -3
- package/dist/node/TemplateShell.js +10 -10
- package/dist/node/hooks/index.js +29 -29
- package/dist/node/index.js +193 -286
- package/dist/node/lib/component-registry.js +1 -1
- package/dist/node/markdown/formatPresentationName.js +9 -0
- package/dist/node/markdown/useMarkdownPresentation.js +65 -0
- package/dist/utils/index.d.ts +1 -1
- package/package.json +40 -13
- package/src/EvolutionDashboard.tsx +415 -415
- package/src/EvolutionSidebar.tsx +245 -245
- package/src/LocalDataIndicator.tsx +28 -28
- package/src/MarkdownView.tsx +119 -372
- package/src/OverlayContextProvider.tsx +272 -272
- package/src/PersonalizationInsights.tsx +232 -232
- package/src/SaveToStudioButton.tsx +51 -51
- package/src/SpecDrivenTemplateShell.tsx +59 -59
- package/src/SpecEditorPanel.tsx +138 -138
- package/src/TemplateShell.tsx +50 -50
- package/src/bundles/ExampleTemplateBundle.ts +78 -78
- package/src/hooks/index.ts +3 -3
- package/src/hooks/useBehaviorTracking.ts +252 -252
- package/src/hooks/useEvolution.ts +437 -437
- package/src/hooks/useRegistryTemplates.ts +42 -42
- package/src/hooks/useSpecContent.ts +214 -214
- package/src/hooks/useWorkflowComposer.ts +567 -567
- package/src/index.ts +12 -11
- package/src/lib/component-registry.tsx +40 -40
- package/src/lib/runtime-context.tsx +31 -31
- package/src/lib/types.ts +57 -57
- package/src/markdown/formatPresentationName.ts +9 -0
- package/src/markdown/useMarkdownPresentation.ts +107 -0
- package/src/overlay-types.ts +15 -15
- package/src/utils/fetchPresentationData.ts +13 -13
- package/src/utils/generateSpecFromTemplate.ts +29 -29
- package/src/utils/index.ts +1 -1
- package/tsconfig.json +8 -8
package/dist/browser/index.js
CHANGED
|
@@ -257,10 +257,10 @@ function generateRecommendedActions(anomaly) {
|
|
|
257
257
|
}
|
|
258
258
|
|
|
259
259
|
// src/EvolutionDashboard.tsx
|
|
260
|
-
import { useCallback as useCallback2, useMemo as useMemo2 } from "react";
|
|
261
260
|
import { Button, LoaderBlock } from "@contractspec/lib.design-system";
|
|
262
|
-
import { Card } from "@contractspec/lib.ui-kit-web/ui/card";
|
|
263
261
|
import { Badge } from "@contractspec/lib.ui-kit-web/ui/badge";
|
|
262
|
+
import { Card } from "@contractspec/lib.ui-kit-web/ui/card";
|
|
263
|
+
import { useCallback as useCallback2, useMemo as useMemo2 } from "react";
|
|
264
264
|
import { jsxDEV } from "react/jsx-dev-runtime";
|
|
265
265
|
"use client";
|
|
266
266
|
function EvolutionDashboard({
|
|
@@ -339,7 +339,7 @@ function EvolutionDashboard({
|
|
|
339
339
|
/* @__PURE__ */ jsxDEV("div", {
|
|
340
340
|
children: [
|
|
341
341
|
/* @__PURE__ */ jsxDEV("h2", {
|
|
342
|
-
className: "text-xl
|
|
342
|
+
className: "font-semibold text-xl",
|
|
343
343
|
children: "AI Evolution Engine"
|
|
344
344
|
}, undefined, false, undefined, this),
|
|
345
345
|
/* @__PURE__ */ jsxDEV("p", {
|
|
@@ -397,7 +397,7 @@ function EvolutionDashboard({
|
|
|
397
397
|
]
|
|
398
398
|
}, undefined, true, undefined, this),
|
|
399
399
|
/* @__PURE__ */ jsxDEV("p", {
|
|
400
|
-
className: "text-muted-foreground
|
|
400
|
+
className: "mt-2 text-muted-foreground text-xs",
|
|
401
401
|
children: "Simulate sandbox operations, analyze patterns, and generate AI improvement suggestions."
|
|
402
402
|
}, undefined, false, undefined, this)
|
|
403
403
|
]
|
|
@@ -514,7 +514,7 @@ function UsageStatCard({ stat }) {
|
|
|
514
514
|
className: "mb-2 flex items-center justify-between",
|
|
515
515
|
children: [
|
|
516
516
|
/* @__PURE__ */ jsxDEV("span", {
|
|
517
|
-
className: "font-mono text-sm
|
|
517
|
+
className: "font-medium font-mono text-sm",
|
|
518
518
|
children: stat.operation.name
|
|
519
519
|
}, undefined, false, undefined, this),
|
|
520
520
|
/* @__PURE__ */ jsxDEV(Badge, {
|
|
@@ -616,7 +616,7 @@ function AnomalyCard({ anomaly }) {
|
|
|
616
616
|
/* @__PURE__ */ jsxDEV("div", {
|
|
617
617
|
children: [
|
|
618
618
|
/* @__PURE__ */ jsxDEV("p", {
|
|
619
|
-
className: "text-sm
|
|
619
|
+
className: "font-medium text-sm",
|
|
620
620
|
children: anomaly.description
|
|
621
621
|
}, undefined, false, undefined, this),
|
|
622
622
|
/* @__PURE__ */ jsxDEV("p", {
|
|
@@ -686,7 +686,7 @@ function SuggestionCard({
|
|
|
686
686
|
]
|
|
687
687
|
}, undefined, true, undefined, this),
|
|
688
688
|
/* @__PURE__ */ jsxDEV("p", {
|
|
689
|
-
className: "text-muted-foreground
|
|
689
|
+
className: "mt-1 text-muted-foreground text-sm",
|
|
690
690
|
children: suggestion.proposal.rationale
|
|
691
691
|
}, undefined, false, undefined, this)
|
|
692
692
|
]
|
|
@@ -702,7 +702,7 @@ function SuggestionCard({
|
|
|
702
702
|
className: "mt-3",
|
|
703
703
|
children: [
|
|
704
704
|
/* @__PURE__ */ jsxDEV("p", {
|
|
705
|
-
className: "mb-1
|
|
705
|
+
className: "mb-1 font-semibold text-violet-400 text-xs uppercase",
|
|
706
706
|
children: "Recommended Actions"
|
|
707
707
|
}, undefined, false, undefined, this),
|
|
708
708
|
/* @__PURE__ */ jsxDEV("ul", {
|
|
@@ -783,7 +783,7 @@ function HintCard({ hint }) {
|
|
|
783
783
|
children: hint.summary
|
|
784
784
|
}, undefined, false, undefined, this),
|
|
785
785
|
/* @__PURE__ */ jsxDEV("p", {
|
|
786
|
-
className: "text-muted-foreground
|
|
786
|
+
className: "mt-1 text-muted-foreground text-xs",
|
|
787
787
|
children: hint.justification
|
|
788
788
|
}, undefined, false, undefined, this),
|
|
789
789
|
hint.recommendedActions.length > 0 && /* @__PURE__ */ jsxDEV("ul", {
|
|
@@ -800,10 +800,10 @@ function HintCard({ hint }) {
|
|
|
800
800
|
}
|
|
801
801
|
|
|
802
802
|
// src/EvolutionSidebar.tsx
|
|
803
|
-
import { useCallback as useCallback3, useMemo as useMemo3 } from "react";
|
|
804
803
|
import { Button as Button2 } from "@contractspec/lib.design-system";
|
|
805
|
-
import { Card as Card2 } from "@contractspec/lib.ui-kit-web/ui/card";
|
|
806
804
|
import { Badge as Badge2 } from "@contractspec/lib.ui-kit-web/ui/badge";
|
|
805
|
+
import { Card as Card2 } from "@contractspec/lib.ui-kit-web/ui/card";
|
|
806
|
+
import { useCallback as useCallback3, useMemo as useMemo3 } from "react";
|
|
807
807
|
import { jsxDEV as jsxDEV2 } from "react/jsx-dev-runtime";
|
|
808
808
|
"use client";
|
|
809
809
|
function EvolutionSidebar({
|
|
@@ -862,7 +862,7 @@ function EvolutionSidebar({
|
|
|
862
862
|
className: "w-80 overflow-hidden",
|
|
863
863
|
children: [
|
|
864
864
|
/* @__PURE__ */ jsxDEV2("div", {
|
|
865
|
-
className: "flex items-center justify-between border-
|
|
865
|
+
className: "flex items-center justify-between border-violet-500/20 border-b bg-violet-500/5 px-3 py-2",
|
|
866
866
|
children: [
|
|
867
867
|
/* @__PURE__ */ jsxDEV2("div", {
|
|
868
868
|
className: "flex items-center gap-2",
|
|
@@ -871,7 +871,7 @@ function EvolutionSidebar({
|
|
|
871
871
|
children: "\uD83E\uDD16"
|
|
872
872
|
}, undefined, false, undefined, this),
|
|
873
873
|
/* @__PURE__ */ jsxDEV2("span", {
|
|
874
|
-
className: "text-sm
|
|
874
|
+
className: "font-semibold text-sm",
|
|
875
875
|
children: "Evolution"
|
|
876
876
|
}, undefined, false, undefined, this)
|
|
877
877
|
]
|
|
@@ -887,7 +887,7 @@ function EvolutionSidebar({
|
|
|
887
887
|
}, undefined, false, undefined, this),
|
|
888
888
|
/* @__PURE__ */ jsxDEV2("button", {
|
|
889
889
|
onClick: onToggle,
|
|
890
|
-
className: "text-muted-foreground hover:text-foreground
|
|
890
|
+
className: "p-1 text-muted-foreground hover:text-foreground",
|
|
891
891
|
type: "button",
|
|
892
892
|
title: "Collapse",
|
|
893
893
|
children: "✕"
|
|
@@ -932,14 +932,14 @@ function EvolutionSidebar({
|
|
|
932
932
|
]
|
|
933
933
|
}, undefined, true, undefined, this),
|
|
934
934
|
loading && /* @__PURE__ */ jsxDEV2("div", {
|
|
935
|
-
className: "
|
|
935
|
+
className: "py-4 text-center text-muted-foreground text-sm",
|
|
936
936
|
children: "Generating suggestions..."
|
|
937
937
|
}, undefined, false, undefined, this),
|
|
938
938
|
topAnomalies.length > 0 && /* @__PURE__ */ jsxDEV2("div", {
|
|
939
939
|
className: "mb-4",
|
|
940
940
|
children: [
|
|
941
941
|
/* @__PURE__ */ jsxDEV2("p", {
|
|
942
|
-
className: "mb-2
|
|
942
|
+
className: "mb-2 font-semibold text-violet-400 text-xs uppercase",
|
|
943
943
|
children: "Top Issues"
|
|
944
944
|
}, undefined, false, undefined, this),
|
|
945
945
|
/* @__PURE__ */ jsxDEV2("div", {
|
|
@@ -960,7 +960,7 @@ function EvolutionSidebar({
|
|
|
960
960
|
]
|
|
961
961
|
}, undefined, true, undefined, this),
|
|
962
962
|
/* @__PURE__ */ jsxDEV2("p", {
|
|
963
|
-
className: "text-muted-foreground
|
|
963
|
+
className: "mt-1 truncate text-muted-foreground",
|
|
964
964
|
children: anomaly.description
|
|
965
965
|
}, undefined, false, undefined, this)
|
|
966
966
|
]
|
|
@@ -971,7 +971,7 @@ function EvolutionSidebar({
|
|
|
971
971
|
pendingSuggestions.length > 0 && /* @__PURE__ */ jsxDEV2("div", {
|
|
972
972
|
children: [
|
|
973
973
|
/* @__PURE__ */ jsxDEV2("p", {
|
|
974
|
-
className: "mb-2
|
|
974
|
+
className: "mb-2 font-semibold text-violet-400 text-xs uppercase",
|
|
975
975
|
children: "Pending Suggestions"
|
|
976
976
|
}, undefined, false, undefined, this),
|
|
977
977
|
/* @__PURE__ */ jsxDEV2("div", {
|
|
@@ -983,7 +983,7 @@ function EvolutionSidebar({
|
|
|
983
983
|
onReject: handleReject
|
|
984
984
|
}, suggestion.id, false, undefined, this)),
|
|
985
985
|
pendingSuggestions.length > 3 && /* @__PURE__ */ jsxDEV2("p", {
|
|
986
|
-
className: "text-muted-foreground text-
|
|
986
|
+
className: "text-center text-muted-foreground text-xs",
|
|
987
987
|
children: [
|
|
988
988
|
"+",
|
|
989
989
|
pendingSuggestions.length - 3,
|
|
@@ -995,13 +995,13 @@ function EvolutionSidebar({
|
|
|
995
995
|
]
|
|
996
996
|
}, undefined, true, undefined, this),
|
|
997
997
|
anomalies.length === 0 && pendingSuggestions.length === 0 && !loading && /* @__PURE__ */ jsxDEV2("div", {
|
|
998
|
-
className: "
|
|
998
|
+
className: "py-4 text-center text-muted-foreground text-xs",
|
|
999
999
|
children: "No issues detected. Keep coding!"
|
|
1000
1000
|
}, undefined, false, undefined, this)
|
|
1001
1001
|
]
|
|
1002
1002
|
}, undefined, true, undefined, this),
|
|
1003
1003
|
onOpenEvolution && /* @__PURE__ */ jsxDEV2("div", {
|
|
1004
|
-
className: "border-
|
|
1004
|
+
className: "border-violet-500/20 border-t p-2",
|
|
1005
1005
|
children: /* @__PURE__ */ jsxDEV2(Button2, {
|
|
1006
1006
|
variant: "ghost",
|
|
1007
1007
|
size: "sm",
|
|
@@ -1027,7 +1027,7 @@ function CompactSuggestionCard({
|
|
|
1027
1027
|
className: "min-w-0 flex-1",
|
|
1028
1028
|
children: [
|
|
1029
1029
|
/* @__PURE__ */ jsxDEV2("p", {
|
|
1030
|
-
className: "truncate text-xs
|
|
1030
|
+
className: "truncate font-medium text-xs",
|
|
1031
1031
|
children: suggestion.proposal.summary
|
|
1032
1032
|
}, undefined, false, undefined, this),
|
|
1033
1033
|
/* @__PURE__ */ jsxDEV2("div", {
|
|
@@ -1054,13 +1054,13 @@ function CompactSuggestionCard({
|
|
|
1054
1054
|
children: [
|
|
1055
1055
|
/* @__PURE__ */ jsxDEV2("button", {
|
|
1056
1056
|
onClick: () => onReject(suggestion.id),
|
|
1057
|
-
className: "rounded px-2 py-0.5 text-
|
|
1057
|
+
className: "rounded px-2 py-0.5 text-red-400 text-xs hover:bg-red-400/10",
|
|
1058
1058
|
type: "button",
|
|
1059
1059
|
children: "Reject"
|
|
1060
1060
|
}, undefined, false, undefined, this),
|
|
1061
1061
|
/* @__PURE__ */ jsxDEV2("button", {
|
|
1062
1062
|
onClick: () => onApprove(suggestion.id),
|
|
1063
|
-
className: "rounded bg-violet-500/20 px-2 py-0.5 text-
|
|
1063
|
+
className: "rounded bg-violet-500/20 px-2 py-0.5 text-violet-400 text-xs hover:bg-violet-500/30",
|
|
1064
1064
|
type: "button",
|
|
1065
1065
|
children: "Approve"
|
|
1066
1066
|
}, undefined, false, undefined, this)
|
|
@@ -1099,7 +1099,7 @@ function LocalDataIndicator() {
|
|
|
1099
1099
|
}
|
|
1100
1100
|
};
|
|
1101
1101
|
return /* @__PURE__ */ jsxDEV3("div", {
|
|
1102
|
-
className: "
|
|
1102
|
+
className: "inline-flex items-center gap-2 rounded-full border border-border bg-muted/40 px-3 py-1 text-muted-foreground text-xs",
|
|
1103
1103
|
children: [
|
|
1104
1104
|
/* @__PURE__ */ jsxDEV3(Shield, {
|
|
1105
1105
|
className: "h-3.5 w-3.5 text-violet-400"
|
|
@@ -1109,14 +1109,14 @@ function LocalDataIndicator() {
|
|
|
1109
1109
|
"Local runtime ·",
|
|
1110
1110
|
" ",
|
|
1111
1111
|
/* @__PURE__ */ jsxDEV3("span", {
|
|
1112
|
-
className: "text-foreground
|
|
1112
|
+
className: "font-semibold text-foreground",
|
|
1113
1113
|
children: template.name
|
|
1114
1114
|
}, undefined, false, undefined, this)
|
|
1115
1115
|
]
|
|
1116
1116
|
}, undefined, true, undefined, this),
|
|
1117
1117
|
/* @__PURE__ */ jsxDEV3("button", {
|
|
1118
1118
|
type: "button",
|
|
1119
|
-
className: "
|
|
1119
|
+
className: "inline-flex items-center gap-1 rounded-full border border-border px-2 py-0.5 font-semibold text-[11px] text-muted-foreground hover:text-foreground",
|
|
1120
1120
|
onClick: handleReset,
|
|
1121
1121
|
disabled: isResetting,
|
|
1122
1122
|
children: [
|
|
@@ -1130,31 +1130,24 @@ function LocalDataIndicator() {
|
|
|
1130
1130
|
}, undefined, true, undefined, this);
|
|
1131
1131
|
}
|
|
1132
1132
|
|
|
1133
|
-
// src/
|
|
1133
|
+
// src/markdown/formatPresentationName.ts
|
|
1134
|
+
function formatPresentationName(name) {
|
|
1135
|
+
const parts = name.split(".");
|
|
1136
|
+
const lastPart = parts[parts.length - 1] ?? name;
|
|
1137
|
+
return lastPart.split("-").map((word) => word.charAt(0).toUpperCase() + word.slice(1)).join(" ");
|
|
1138
|
+
}
|
|
1139
|
+
|
|
1140
|
+
// src/markdown/useMarkdownPresentation.ts
|
|
1134
1141
|
import { useCallback as useCallback4, useEffect as useEffect2, useState as useState3 } from "react";
|
|
1135
|
-
import {
|
|
1136
|
-
Button as Button3,
|
|
1137
|
-
ErrorState,
|
|
1138
|
-
LoaderBlock as LoaderBlock2
|
|
1139
|
-
} from "@contractspec/lib.design-system";
|
|
1140
|
-
import { Card as Card3 } from "@contractspec/lib.ui-kit-web/ui/card";
|
|
1141
|
-
import { Badge as Badge3 } from "@contractspec/lib.ui-kit-web/ui/badge";
|
|
1142
|
-
import { jsxDEV as jsxDEV4 } from "react/jsx-dev-runtime";
|
|
1143
1142
|
"use client";
|
|
1144
|
-
function
|
|
1145
|
-
|
|
1143
|
+
function useMarkdownPresentation({
|
|
1144
|
+
engine,
|
|
1145
|
+
fetchData,
|
|
1146
1146
|
presentationId,
|
|
1147
|
-
|
|
1147
|
+
presentations,
|
|
1148
|
+
resolvePresentation,
|
|
1149
|
+
templateId
|
|
1148
1150
|
}) {
|
|
1149
|
-
const {
|
|
1150
|
-
engine,
|
|
1151
|
-
template,
|
|
1152
|
-
templateId: contextTemplateId,
|
|
1153
|
-
resolvePresentation,
|
|
1154
|
-
fetchData
|
|
1155
|
-
} = useTemplateRuntime();
|
|
1156
|
-
const templateId = propTemplateId ?? contextTemplateId;
|
|
1157
|
-
const presentations = template?.presentations ?? [];
|
|
1158
1151
|
const [selectedPresentation, setSelectedPresentation] = useState3("");
|
|
1159
1152
|
const [markdownContent, setMarkdownContent] = useState3("");
|
|
1160
1153
|
const [loading, setLoading] = useState3(false);
|
|
@@ -1162,10 +1155,16 @@ function MarkdownView({
|
|
|
1162
1155
|
useEffect2(() => {
|
|
1163
1156
|
if (presentationId && presentations.includes(presentationId)) {
|
|
1164
1157
|
setSelectedPresentation(presentationId);
|
|
1165
|
-
|
|
1158
|
+
return;
|
|
1159
|
+
}
|
|
1160
|
+
if (presentations.length === 0) {
|
|
1161
|
+
setSelectedPresentation("");
|
|
1162
|
+
return;
|
|
1163
|
+
}
|
|
1164
|
+
if (!presentations.includes(selectedPresentation)) {
|
|
1166
1165
|
setSelectedPresentation(presentations[0] ?? "");
|
|
1167
1166
|
}
|
|
1168
|
-
}, [presentationId, presentations, selectedPresentation]);
|
|
1167
|
+
}, [presentationId, presentations, selectedPresentation, templateId]);
|
|
1169
1168
|
const renderMarkdown = useCallback4(async () => {
|
|
1170
1169
|
if (!selectedPresentation || !engine)
|
|
1171
1170
|
return;
|
|
@@ -1187,16 +1186,61 @@ function MarkdownView({
|
|
|
1187
1186
|
} finally {
|
|
1188
1187
|
setLoading(false);
|
|
1189
1188
|
}
|
|
1190
|
-
}, [
|
|
1189
|
+
}, [engine, fetchData, resolvePresentation, selectedPresentation]);
|
|
1190
|
+
useEffect2(() => {
|
|
1191
|
+
renderMarkdown();
|
|
1192
|
+
}, [renderMarkdown]);
|
|
1193
|
+
return {
|
|
1194
|
+
error,
|
|
1195
|
+
loading,
|
|
1196
|
+
markdownContent,
|
|
1197
|
+
renderMarkdown,
|
|
1191
1198
|
selectedPresentation,
|
|
1192
|
-
|
|
1199
|
+
setSelectedPresentation
|
|
1200
|
+
};
|
|
1201
|
+
}
|
|
1202
|
+
|
|
1203
|
+
// src/MarkdownView.tsx
|
|
1204
|
+
import {
|
|
1205
|
+
Button as Button3,
|
|
1206
|
+
ErrorState,
|
|
1207
|
+
LoaderBlock as LoaderBlock2,
|
|
1208
|
+
MarkdownRenderer
|
|
1209
|
+
} from "@contractspec/lib.design-system";
|
|
1210
|
+
import { Badge as Badge3 } from "@contractspec/lib.ui-kit-web/ui/badge";
|
|
1211
|
+
import { Card as Card3 } from "@contractspec/lib.ui-kit-web/ui/card";
|
|
1212
|
+
import { useCallback as useCallback5 } from "react";
|
|
1213
|
+
import { jsxDEV as jsxDEV4 } from "react/jsx-dev-runtime";
|
|
1214
|
+
"use client";
|
|
1215
|
+
function MarkdownView({
|
|
1216
|
+
templateId: propTemplateId,
|
|
1217
|
+
presentationId,
|
|
1218
|
+
className
|
|
1219
|
+
}) {
|
|
1220
|
+
const {
|
|
1193
1221
|
engine,
|
|
1222
|
+
template,
|
|
1223
|
+
templateId: contextTemplateId,
|
|
1194
1224
|
resolvePresentation,
|
|
1195
1225
|
fetchData
|
|
1196
|
-
|
|
1197
|
-
|
|
1198
|
-
|
|
1199
|
-
|
|
1226
|
+
} = useTemplateRuntime();
|
|
1227
|
+
const templateId = propTemplateId ?? contextTemplateId;
|
|
1228
|
+
const presentations = template?.presentations ?? [];
|
|
1229
|
+
const {
|
|
1230
|
+
error,
|
|
1231
|
+
loading,
|
|
1232
|
+
markdownContent,
|
|
1233
|
+
renderMarkdown,
|
|
1234
|
+
selectedPresentation,
|
|
1235
|
+
setSelectedPresentation
|
|
1236
|
+
} = useMarkdownPresentation({
|
|
1237
|
+
engine,
|
|
1238
|
+
fetchData,
|
|
1239
|
+
presentationId,
|
|
1240
|
+
presentations,
|
|
1241
|
+
resolvePresentation,
|
|
1242
|
+
templateId
|
|
1243
|
+
});
|
|
1200
1244
|
if (!presentations.length) {
|
|
1201
1245
|
return /* @__PURE__ */ jsxDEV4(Card3, {
|
|
1202
1246
|
className,
|
|
@@ -1209,7 +1253,7 @@ function MarkdownView({
|
|
|
1209
1253
|
}, undefined, false, undefined, this)
|
|
1210
1254
|
}, undefined, false, undefined, this);
|
|
1211
1255
|
}
|
|
1212
|
-
const handleCopy =
|
|
1256
|
+
const handleCopy = useCallback5(() => {
|
|
1213
1257
|
if (markdownContent) {
|
|
1214
1258
|
navigator.clipboard.writeText(markdownContent);
|
|
1215
1259
|
}
|
|
@@ -1221,7 +1265,7 @@ function MarkdownView({
|
|
|
1221
1265
|
className: "mb-4 flex flex-wrap items-center gap-2",
|
|
1222
1266
|
children: [
|
|
1223
1267
|
/* @__PURE__ */ jsxDEV4("span", {
|
|
1224
|
-
className: "text-muted-foreground text-sm
|
|
1268
|
+
className: "font-medium text-muted-foreground text-sm",
|
|
1225
1269
|
children: "Presentation:"
|
|
1226
1270
|
}, undefined, false, undefined, this),
|
|
1227
1271
|
presentations.map((name) => /* @__PURE__ */ jsxDEV4(Button3, {
|
|
@@ -1278,145 +1322,6 @@ function MarkdownView({
|
|
|
1278
1322
|
]
|
|
1279
1323
|
}, undefined, true, undefined, this);
|
|
1280
1324
|
}
|
|
1281
|
-
function MarkdownRenderer({ content }) {
|
|
1282
|
-
const lines = content.split(`
|
|
1283
|
-
`);
|
|
1284
|
-
const rendered = [];
|
|
1285
|
-
let i = 0;
|
|
1286
|
-
while (i < lines.length) {
|
|
1287
|
-
const line = lines[i] ?? "";
|
|
1288
|
-
if (line.startsWith("|") && lines[i + 1]?.match(/^\|[\s-|]+\|$/)) {
|
|
1289
|
-
const tableLines = [line];
|
|
1290
|
-
i++;
|
|
1291
|
-
while (i < lines.length && (lines[i]?.startsWith("|") ?? false)) {
|
|
1292
|
-
tableLines.push(lines[i] ?? "");
|
|
1293
|
-
i++;
|
|
1294
|
-
}
|
|
1295
|
-
rendered.push(renderTable(tableLines, rendered.length));
|
|
1296
|
-
continue;
|
|
1297
|
-
}
|
|
1298
|
-
if (line.startsWith("# ")) {
|
|
1299
|
-
rendered.push(/* @__PURE__ */ jsxDEV4("h1", {
|
|
1300
|
-
className: "mb-4 text-2xl font-bold",
|
|
1301
|
-
children: line.slice(2)
|
|
1302
|
-
}, i, false, undefined, this));
|
|
1303
|
-
} else if (line.startsWith("## ")) {
|
|
1304
|
-
rendered.push(/* @__PURE__ */ jsxDEV4("h2", {
|
|
1305
|
-
className: "mt-6 mb-3 text-xl font-semibold",
|
|
1306
|
-
children: line.slice(3)
|
|
1307
|
-
}, i, false, undefined, this));
|
|
1308
|
-
} else if (line.startsWith("### ")) {
|
|
1309
|
-
rendered.push(/* @__PURE__ */ jsxDEV4("h3", {
|
|
1310
|
-
className: "mt-4 mb-2 text-lg font-medium",
|
|
1311
|
-
children: line.slice(4)
|
|
1312
|
-
}, i, false, undefined, this));
|
|
1313
|
-
} else if (line.startsWith("> ")) {
|
|
1314
|
-
rendered.push(/* @__PURE__ */ jsxDEV4("blockquote", {
|
|
1315
|
-
className: "text-muted-foreground my-2 border-l-4 border-violet-500/50 pl-4 italic",
|
|
1316
|
-
children: line.slice(2)
|
|
1317
|
-
}, i, false, undefined, this));
|
|
1318
|
-
} else if (line.startsWith("- ")) {
|
|
1319
|
-
rendered.push(/* @__PURE__ */ jsxDEV4("li", {
|
|
1320
|
-
className: "ml-4 list-disc",
|
|
1321
|
-
children: formatInlineMarkdown(line.slice(2))
|
|
1322
|
-
}, i, false, undefined, this));
|
|
1323
|
-
} else if (line.startsWith("**") && line.includes(":**")) {
|
|
1324
|
-
const [label, ...rest] = line.split(":**");
|
|
1325
|
-
rendered.push(/* @__PURE__ */ jsxDEV4("p", {
|
|
1326
|
-
className: "my-1",
|
|
1327
|
-
children: [
|
|
1328
|
-
/* @__PURE__ */ jsxDEV4("strong", {
|
|
1329
|
-
children: [
|
|
1330
|
-
label?.slice(2),
|
|
1331
|
-
":"
|
|
1332
|
-
]
|
|
1333
|
-
}, undefined, true, undefined, this),
|
|
1334
|
-
rest.join(":**")
|
|
1335
|
-
]
|
|
1336
|
-
}, i, true, undefined, this));
|
|
1337
|
-
} else if (line.startsWith("_") && line.endsWith("_")) {
|
|
1338
|
-
rendered.push(/* @__PURE__ */ jsxDEV4("p", {
|
|
1339
|
-
className: "text-muted-foreground my-1 italic",
|
|
1340
|
-
children: line.slice(1, -1)
|
|
1341
|
-
}, i, false, undefined, this));
|
|
1342
|
-
} else if (!line.trim()) {
|
|
1343
|
-
rendered.push(/* @__PURE__ */ jsxDEV4("div", {
|
|
1344
|
-
className: "h-2"
|
|
1345
|
-
}, i, false, undefined, this));
|
|
1346
|
-
} else {
|
|
1347
|
-
rendered.push(/* @__PURE__ */ jsxDEV4("p", {
|
|
1348
|
-
className: "my-1",
|
|
1349
|
-
children: formatInlineMarkdown(line)
|
|
1350
|
-
}, i, false, undefined, this));
|
|
1351
|
-
}
|
|
1352
|
-
i++;
|
|
1353
|
-
}
|
|
1354
|
-
return /* @__PURE__ */ jsxDEV4("div", {
|
|
1355
|
-
className: "prose prose-sm dark:prose-invert max-w-none",
|
|
1356
|
-
children: rendered
|
|
1357
|
-
}, undefined, false, undefined, this);
|
|
1358
|
-
}
|
|
1359
|
-
function renderTable(lines, keyPrefix) {
|
|
1360
|
-
if (lines.length < 2)
|
|
1361
|
-
return null;
|
|
1362
|
-
const parseRow = (row) => row.split("|").slice(1, -1).map((cell) => cell.trim());
|
|
1363
|
-
const headers = parseRow(lines[0] ?? "");
|
|
1364
|
-
const dataRows = lines.slice(2).map(parseRow);
|
|
1365
|
-
return /* @__PURE__ */ jsxDEV4("div", {
|
|
1366
|
-
className: "my-4 overflow-x-auto",
|
|
1367
|
-
children: /* @__PURE__ */ jsxDEV4("table", {
|
|
1368
|
-
className: "border-border min-w-full border-collapse border text-sm",
|
|
1369
|
-
children: [
|
|
1370
|
-
/* @__PURE__ */ jsxDEV4("thead", {
|
|
1371
|
-
children: /* @__PURE__ */ jsxDEV4("tr", {
|
|
1372
|
-
className: "bg-muted/50",
|
|
1373
|
-
children: headers.map((header, idx) => /* @__PURE__ */ jsxDEV4("th", {
|
|
1374
|
-
className: "border-border border px-3 py-2 text-left font-semibold",
|
|
1375
|
-
children: header
|
|
1376
|
-
}, idx, false, undefined, this))
|
|
1377
|
-
}, undefined, false, undefined, this)
|
|
1378
|
-
}, undefined, false, undefined, this),
|
|
1379
|
-
/* @__PURE__ */ jsxDEV4("tbody", {
|
|
1380
|
-
children: dataRows.map((row, rowIdx) => /* @__PURE__ */ jsxDEV4("tr", {
|
|
1381
|
-
className: "hover:bg-muted/30",
|
|
1382
|
-
children: row.map((cell, cellIdx) => /* @__PURE__ */ jsxDEV4("td", {
|
|
1383
|
-
className: "border-border border px-3 py-2",
|
|
1384
|
-
children: formatInlineMarkdown(cell)
|
|
1385
|
-
}, cellIdx, false, undefined, this))
|
|
1386
|
-
}, rowIdx, false, undefined, this))
|
|
1387
|
-
}, undefined, false, undefined, this)
|
|
1388
|
-
]
|
|
1389
|
-
}, undefined, true, undefined, this)
|
|
1390
|
-
}, `table-${keyPrefix}`, false, undefined, this);
|
|
1391
|
-
}
|
|
1392
|
-
function formatInlineMarkdown(text) {
|
|
1393
|
-
const parts = text.split(/(\*\*[^*]+\*\*)/g);
|
|
1394
|
-
return parts.map((part, i) => {
|
|
1395
|
-
if (part.startsWith("**") && part.endsWith("**")) {
|
|
1396
|
-
return /* @__PURE__ */ jsxDEV4("strong", {
|
|
1397
|
-
children: part.slice(2, -2)
|
|
1398
|
-
}, i, false, undefined, this);
|
|
1399
|
-
}
|
|
1400
|
-
if (part.includes("`")) {
|
|
1401
|
-
const codeParts = part.split(/(`[^`]+`)/g);
|
|
1402
|
-
return codeParts.map((cp, j) => {
|
|
1403
|
-
if (cp.startsWith("`") && cp.endsWith("`")) {
|
|
1404
|
-
return /* @__PURE__ */ jsxDEV4("code", {
|
|
1405
|
-
className: "rounded bg-violet-500/10 px-1.5 py-0.5 font-mono text-sm",
|
|
1406
|
-
children: cp.slice(1, -1)
|
|
1407
|
-
}, `${i}-${j}`, false, undefined, this);
|
|
1408
|
-
}
|
|
1409
|
-
return cp;
|
|
1410
|
-
});
|
|
1411
|
-
}
|
|
1412
|
-
return part;
|
|
1413
|
-
});
|
|
1414
|
-
}
|
|
1415
|
-
function formatPresentationName(name) {
|
|
1416
|
-
const parts = name.split(".");
|
|
1417
|
-
const lastPart = parts[parts.length - 1] ?? name;
|
|
1418
|
-
return lastPart.split("-").map((word) => word.charAt(0).toUpperCase() + word.slice(1)).join(" ");
|
|
1419
|
-
}
|
|
1420
1325
|
|
|
1421
1326
|
// src/OverlayContextProvider.tsx
|
|
1422
1327
|
import * as React from "react";
|
|
@@ -1617,7 +1522,7 @@ function getTemplateOverlays(templateId, _role) {
|
|
|
1617
1522
|
}
|
|
1618
1523
|
|
|
1619
1524
|
// src/hooks/useBehaviorTracking.ts
|
|
1620
|
-
import { useCallback as
|
|
1525
|
+
import { useCallback as useCallback6, useEffect as useEffect3, useMemo as useMemo5, useRef as useRef2, useState as useState4 } from "react";
|
|
1621
1526
|
"use client";
|
|
1622
1527
|
var BEHAVIOR_STORAGE_KEY = "contractspec-behavior-data";
|
|
1623
1528
|
var ALL_FEATURES = [
|
|
@@ -1662,7 +1567,7 @@ function useBehaviorTracking(templateId) {
|
|
|
1662
1567
|
} catch {}
|
|
1663
1568
|
}
|
|
1664
1569
|
}, [events]);
|
|
1665
|
-
const trackEvent =
|
|
1570
|
+
const trackEvent = useCallback6((type, metadata) => {
|
|
1666
1571
|
const event = {
|
|
1667
1572
|
type,
|
|
1668
1573
|
timestamp: new Date,
|
|
@@ -1672,10 +1577,10 @@ function useBehaviorTracking(templateId) {
|
|
|
1672
1577
|
setEvents((prev) => [...prev, event]);
|
|
1673
1578
|
setEventCount((prev) => prev + 1);
|
|
1674
1579
|
}, [templateId]);
|
|
1675
|
-
const getEventsByType =
|
|
1580
|
+
const getEventsByType = useCallback6((type) => {
|
|
1676
1581
|
return events.filter((e) => e.type === type);
|
|
1677
1582
|
}, [events]);
|
|
1678
|
-
const getSummary =
|
|
1583
|
+
const getSummary = useCallback6(() => {
|
|
1679
1584
|
const now = new Date;
|
|
1680
1585
|
const sessionDuration = now.getTime() - sessionStartRef.current.getTime();
|
|
1681
1586
|
const templateCounts = new Map;
|
|
@@ -1730,7 +1635,7 @@ function useBehaviorTracking(templateId) {
|
|
|
1730
1635
|
recommendations
|
|
1731
1636
|
};
|
|
1732
1637
|
}, [events]);
|
|
1733
|
-
const clear =
|
|
1638
|
+
const clear = useCallback6(() => {
|
|
1734
1639
|
setEvents([]);
|
|
1735
1640
|
setEventCount(0);
|
|
1736
1641
|
sessionStartRef.current = new Date;
|
|
@@ -1772,10 +1677,10 @@ function generateRecommendations(featuresUsed, unusedFeatures, mostUsedModes, to
|
|
|
1772
1677
|
}
|
|
1773
1678
|
|
|
1774
1679
|
// src/PersonalizationInsights.tsx
|
|
1775
|
-
import { useCallback as useCallback6, useMemo as useMemo6, useState as useState5 } from "react";
|
|
1776
1680
|
import { Button as Button4 } from "@contractspec/lib.design-system";
|
|
1777
|
-
import { Card as Card4 } from "@contractspec/lib.ui-kit-web/ui/card";
|
|
1778
1681
|
import { Badge as Badge4 } from "@contractspec/lib.ui-kit-web/ui/badge";
|
|
1682
|
+
import { Card as Card4 } from "@contractspec/lib.ui-kit-web/ui/card";
|
|
1683
|
+
import { useCallback as useCallback7, useMemo as useMemo6, useState as useState5 } from "react";
|
|
1779
1684
|
import { jsxDEV as jsxDEV6 } from "react/jsx-dev-runtime";
|
|
1780
1685
|
"use client";
|
|
1781
1686
|
function PersonalizationInsights({
|
|
@@ -1786,7 +1691,7 @@ function PersonalizationInsights({
|
|
|
1786
1691
|
const { getSummary, eventCount, clear, sessionStart } = useBehaviorTracking(templateId);
|
|
1787
1692
|
const [showDetails, setShowDetails] = useState5(false);
|
|
1788
1693
|
const summary = useMemo6(() => getSummary(), [getSummary]);
|
|
1789
|
-
const formatDuration =
|
|
1694
|
+
const formatDuration = useCallback7((ms) => {
|
|
1790
1695
|
const seconds = Math.floor(ms / 1000);
|
|
1791
1696
|
const minutes = Math.floor(seconds / 60);
|
|
1792
1697
|
const hours = Math.floor(minutes / 60);
|
|
@@ -1798,7 +1703,7 @@ function PersonalizationInsights({
|
|
|
1798
1703
|
}
|
|
1799
1704
|
return `${seconds}s`;
|
|
1800
1705
|
}, []);
|
|
1801
|
-
const handleClear =
|
|
1706
|
+
const handleClear = useCallback7(() => {
|
|
1802
1707
|
clear();
|
|
1803
1708
|
}, [clear]);
|
|
1804
1709
|
if (collapsed) {
|
|
@@ -1824,7 +1729,7 @@ function PersonalizationInsights({
|
|
|
1824
1729
|
className: "overflow-hidden",
|
|
1825
1730
|
children: [
|
|
1826
1731
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
1827
|
-
className: "flex items-center justify-between border-
|
|
1732
|
+
className: "flex items-center justify-between border-blue-500/20 border-b bg-blue-500/5 px-4 py-3",
|
|
1828
1733
|
children: [
|
|
1829
1734
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
1830
1735
|
className: "flex items-center gap-2",
|
|
@@ -1849,7 +1754,7 @@ function PersonalizationInsights({
|
|
|
1849
1754
|
}, undefined, false, undefined, this),
|
|
1850
1755
|
onToggle && /* @__PURE__ */ jsxDEV6("button", {
|
|
1851
1756
|
onClick: onToggle,
|
|
1852
|
-
className: "text-muted-foreground hover:text-foreground
|
|
1757
|
+
className: "p-1 text-muted-foreground hover:text-foreground",
|
|
1853
1758
|
type: "button",
|
|
1854
1759
|
title: "Collapse",
|
|
1855
1760
|
children: "✕"
|
|
@@ -1891,7 +1796,7 @@ function PersonalizationInsights({
|
|
|
1891
1796
|
className: "mb-4",
|
|
1892
1797
|
children: [
|
|
1893
1798
|
/* @__PURE__ */ jsxDEV6("h4", {
|
|
1894
|
-
className: "mb-2
|
|
1799
|
+
className: "mb-2 font-semibold text-blue-400 text-xs uppercase",
|
|
1895
1800
|
children: "Recommendations"
|
|
1896
1801
|
}, undefined, false, undefined, this),
|
|
1897
1802
|
/* @__PURE__ */ jsxDEV6("ul", {
|
|
@@ -1915,7 +1820,7 @@ function PersonalizationInsights({
|
|
|
1915
1820
|
className: "mb-4",
|
|
1916
1821
|
children: [
|
|
1917
1822
|
/* @__PURE__ */ jsxDEV6("h4", {
|
|
1918
|
-
className: "mb-2
|
|
1823
|
+
className: "mb-2 font-semibold text-blue-400 text-xs uppercase",
|
|
1919
1824
|
children: "Try These Features"
|
|
1920
1825
|
}, undefined, false, undefined, this),
|
|
1921
1826
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
@@ -1932,7 +1837,7 @@ function PersonalizationInsights({
|
|
|
1932
1837
|
sessionStart
|
|
1933
1838
|
}, undefined, false, undefined, this),
|
|
1934
1839
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
1935
|
-
className: "mt-4 flex justify-end border-
|
|
1840
|
+
className: "mt-4 flex justify-end border-blue-500/10 border-t pt-4",
|
|
1936
1841
|
children: /* @__PURE__ */ jsxDEV6(Button4, {
|
|
1937
1842
|
variant: "ghost",
|
|
1938
1843
|
size: "sm",
|
|
@@ -1964,7 +1869,7 @@ function StatCard({
|
|
|
1964
1869
|
children: icon
|
|
1965
1870
|
}, undefined, false, undefined, this),
|
|
1966
1871
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
1967
|
-
className: "text-lg
|
|
1872
|
+
className: "font-bold text-lg",
|
|
1968
1873
|
children: value
|
|
1969
1874
|
}, undefined, false, undefined, this),
|
|
1970
1875
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
@@ -1979,12 +1884,12 @@ function DetailedInsights({
|
|
|
1979
1884
|
sessionStart
|
|
1980
1885
|
}) {
|
|
1981
1886
|
return /* @__PURE__ */ jsxDEV6("div", {
|
|
1982
|
-
className: "mt-4 space-y-4 border-
|
|
1887
|
+
className: "mt-4 space-y-4 border-blue-500/10 border-t pt-4",
|
|
1983
1888
|
children: [
|
|
1984
1889
|
summary.mostUsedTemplates.length > 0 && /* @__PURE__ */ jsxDEV6("div", {
|
|
1985
1890
|
children: [
|
|
1986
1891
|
/* @__PURE__ */ jsxDEV6("h4", {
|
|
1987
|
-
className: "mb-2
|
|
1892
|
+
className: "mb-2 font-semibold text-blue-400 text-xs uppercase",
|
|
1988
1893
|
children: "Most Used Templates"
|
|
1989
1894
|
}, undefined, false, undefined, this),
|
|
1990
1895
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
@@ -2010,7 +1915,7 @@ function DetailedInsights({
|
|
|
2010
1915
|
summary.mostUsedModes.length > 0 && /* @__PURE__ */ jsxDEV6("div", {
|
|
2011
1916
|
children: [
|
|
2012
1917
|
/* @__PURE__ */ jsxDEV6("h4", {
|
|
2013
|
-
className: "mb-2
|
|
1918
|
+
className: "mb-2 font-semibold text-blue-400 text-xs uppercase",
|
|
2014
1919
|
children: "Mode Usage"
|
|
2015
1920
|
}, undefined, false, undefined, this),
|
|
2016
1921
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
@@ -2036,7 +1941,7 @@ function DetailedInsights({
|
|
|
2036
1941
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
2037
1942
|
children: [
|
|
2038
1943
|
/* @__PURE__ */ jsxDEV6("h4", {
|
|
2039
|
-
className: "mb-2
|
|
1944
|
+
className: "mb-2 font-semibold text-blue-400 text-xs uppercase",
|
|
2040
1945
|
children: "Features Used"
|
|
2041
1946
|
}, undefined, false, undefined, this),
|
|
2042
1947
|
/* @__PURE__ */ jsxDEV6("div", {
|
|
@@ -2070,8 +1975,8 @@ function formatTemplateId(id) {
|
|
|
2070
1975
|
}
|
|
2071
1976
|
|
|
2072
1977
|
// src/SaveToStudioButton.tsx
|
|
2073
|
-
import { useState as useState6 } from "react";
|
|
2074
1978
|
import { Sparkles } from "lucide-react";
|
|
1979
|
+
import { useState as useState6 } from "react";
|
|
2075
1980
|
import { jsxDEV as jsxDEV7 } from "react/jsx-dev-runtime";
|
|
2076
1981
|
"use client";
|
|
2077
1982
|
function SaveToStudioButton({
|
|
@@ -2121,7 +2026,7 @@ function SaveToStudioButton({
|
|
|
2121
2026
|
children: error
|
|
2122
2027
|
}, undefined, false, undefined, this) : null,
|
|
2123
2028
|
status === "saved" ? /* @__PURE__ */ jsxDEV7("p", {
|
|
2124
|
-
className: "text-
|
|
2029
|
+
className: "text-emerald-400 text-xs",
|
|
2125
2030
|
children: "Template sent to Studio."
|
|
2126
2031
|
}, undefined, false, undefined, this) : null
|
|
2127
2032
|
]
|
|
@@ -2145,7 +2050,7 @@ function SpecDrivenTemplateShell({
|
|
|
2145
2050
|
children
|
|
2146
2051
|
}) {
|
|
2147
2052
|
const headerContent = /* @__PURE__ */ jsxDEV8("header", {
|
|
2148
|
-
className: "border-border bg-card
|
|
2053
|
+
className: "rounded-2xl border border-border bg-card p-6 shadow-sm",
|
|
2149
2054
|
children: [
|
|
2150
2055
|
/* @__PURE__ */ jsxDEV8("div", {
|
|
2151
2056
|
className: "flex flex-wrap items-center justify-between gap-4",
|
|
@@ -2153,15 +2058,15 @@ function SpecDrivenTemplateShell({
|
|
|
2153
2058
|
/* @__PURE__ */ jsxDEV8("div", {
|
|
2154
2059
|
children: [
|
|
2155
2060
|
/* @__PURE__ */ jsxDEV8("p", {
|
|
2156
|
-
className: "text-muted-foreground text-sm
|
|
2061
|
+
className: "font-semibold text-muted-foreground text-sm uppercase tracking-wide",
|
|
2157
2062
|
children: "ContractSpec Templates"
|
|
2158
2063
|
}, undefined, false, undefined, this),
|
|
2159
2064
|
/* @__PURE__ */ jsxDEV8("h1", {
|
|
2160
|
-
className: "text-3xl
|
|
2065
|
+
className: "font-bold text-3xl",
|
|
2161
2066
|
children: title
|
|
2162
2067
|
}, undefined, false, undefined, this),
|
|
2163
2068
|
description ? /* @__PURE__ */ jsxDEV8("p", {
|
|
2164
|
-
className: "
|
|
2069
|
+
className: "mt-2 max-w-2xl text-muted-foreground text-sm",
|
|
2165
2070
|
children: description
|
|
2166
2071
|
}, undefined, false, undefined, this) : null
|
|
2167
2072
|
]
|
|
@@ -2192,7 +2097,7 @@ function SpecDrivenTemplateShell({
|
|
|
2192
2097
|
};
|
|
2193
2098
|
if (sidebar != null) {
|
|
2194
2099
|
slotContent.sidebar = /* @__PURE__ */ jsxDEV8("aside", {
|
|
2195
|
-
className: "border-border bg-card
|
|
2100
|
+
className: "rounded-2xl border border-border bg-card p-4",
|
|
2196
2101
|
children: sidebar
|
|
2197
2102
|
}, undefined, false, undefined, this);
|
|
2198
2103
|
}
|
|
@@ -2626,7 +2531,7 @@ contractSpec("${templateId}.main.v1", {
|
|
|
2626
2531
|
}
|
|
2627
2532
|
|
|
2628
2533
|
// src/hooks/useSpecContent.ts
|
|
2629
|
-
import { useCallback as
|
|
2534
|
+
import { useCallback as useCallback8, useEffect as useEffect4, useState as useState7 } from "react";
|
|
2630
2535
|
"use client";
|
|
2631
2536
|
var SPEC_STORAGE_KEY = "contractspec-spec-content";
|
|
2632
2537
|
function useSpecContent(templateId) {
|
|
@@ -2663,11 +2568,11 @@ function useSpecContent(templateId) {
|
|
|
2663
2568
|
}
|
|
2664
2569
|
setLoading(false);
|
|
2665
2570
|
}, [templateId]);
|
|
2666
|
-
const setContent =
|
|
2571
|
+
const setContent = useCallback8((newContent) => {
|
|
2667
2572
|
setContentState(newContent);
|
|
2668
2573
|
setValidation(null);
|
|
2669
2574
|
}, []);
|
|
2670
|
-
const save =
|
|
2575
|
+
const save = useCallback8(() => {
|
|
2671
2576
|
try {
|
|
2672
2577
|
const savedAt = new Date().toISOString();
|
|
2673
2578
|
localStorage.setItem(`${SPEC_STORAGE_KEY}-${templateId}`, JSON.stringify({
|
|
@@ -2678,7 +2583,7 @@ function useSpecContent(templateId) {
|
|
|
2678
2583
|
setLastSaved(savedAt);
|
|
2679
2584
|
} catch {}
|
|
2680
2585
|
}, [content, templateId]);
|
|
2681
|
-
const validate =
|
|
2586
|
+
const validate = useCallback8(() => {
|
|
2682
2587
|
const errors = [];
|
|
2683
2588
|
const lines = content.split(`
|
|
2684
2589
|
`);
|
|
@@ -2746,7 +2651,7 @@ function useSpecContent(templateId) {
|
|
|
2746
2651
|
setValidation(result);
|
|
2747
2652
|
return result;
|
|
2748
2653
|
}, [content]);
|
|
2749
|
-
const reset =
|
|
2654
|
+
const reset = useCallback8(() => {
|
|
2750
2655
|
const generated = generateSpecFromTemplate(template);
|
|
2751
2656
|
setContentState(generated);
|
|
2752
2657
|
setSavedContent(generated);
|
|
@@ -2770,9 +2675,9 @@ function useSpecContent(templateId) {
|
|
|
2770
2675
|
}
|
|
2771
2676
|
|
|
2772
2677
|
// src/SpecEditorPanel.tsx
|
|
2773
|
-
import { useCallback as useCallback8, useEffect as useEffect5 } from "react";
|
|
2774
2678
|
import { Button as Button5, LoaderBlock as LoaderBlock3 } from "@contractspec/lib.design-system";
|
|
2775
2679
|
import { Badge as Badge5 } from "@contractspec/lib.ui-kit-web/ui/badge";
|
|
2680
|
+
import { useCallback as useCallback9, useEffect as useEffect5 } from "react";
|
|
2776
2681
|
import { jsxDEV as jsxDEV9 } from "react/jsx-dev-runtime";
|
|
2777
2682
|
"use client";
|
|
2778
2683
|
function SpecEditorPanel({
|
|
@@ -2796,11 +2701,11 @@ function SpecEditorPanel({
|
|
|
2796
2701
|
onLog?.(`Spec loaded for ${templateId}`);
|
|
2797
2702
|
}
|
|
2798
2703
|
}, [loading, content, templateId, onLog]);
|
|
2799
|
-
const handleSave =
|
|
2704
|
+
const handleSave = useCallback9(() => {
|
|
2800
2705
|
save();
|
|
2801
2706
|
onLog?.("Spec saved locally");
|
|
2802
2707
|
}, [save, onLog]);
|
|
2803
|
-
const handleValidate =
|
|
2708
|
+
const handleValidate = useCallback9(() => {
|
|
2804
2709
|
const result = validate();
|
|
2805
2710
|
if (result.valid) {
|
|
2806
2711
|
onLog?.("Spec validation passed");
|
|
@@ -2810,7 +2715,7 @@ function SpecEditorPanel({
|
|
|
2810
2715
|
onLog?.(`Spec validation: ${errorCount} errors, ${warnCount} warnings`);
|
|
2811
2716
|
}
|
|
2812
2717
|
}, [validate, onLog]);
|
|
2813
|
-
const handleReset =
|
|
2718
|
+
const handleReset = useCallback9(() => {
|
|
2814
2719
|
reset();
|
|
2815
2720
|
onLog?.("Spec reset to template defaults");
|
|
2816
2721
|
}, [reset, onLog]);
|
|
@@ -2876,7 +2781,7 @@ function SpecEditorPanel({
|
|
|
2876
2781
|
className: "rounded-lg border border-amber-500/50 bg-amber-500/10 p-3",
|
|
2877
2782
|
children: [
|
|
2878
2783
|
/* @__PURE__ */ jsxDEV9("p", {
|
|
2879
|
-
className: "mb-2
|
|
2784
|
+
className: "mb-2 font-semibold text-amber-400 text-xs uppercase",
|
|
2880
2785
|
children: "Validation Issues"
|
|
2881
2786
|
}, undefined, false, undefined, this),
|
|
2882
2787
|
/* @__PURE__ */ jsxDEV9("ul", {
|
|
@@ -2894,7 +2799,7 @@ function SpecEditorPanel({
|
|
|
2894
2799
|
]
|
|
2895
2800
|
}, undefined, true, undefined, this),
|
|
2896
2801
|
/* @__PURE__ */ jsxDEV9("div", {
|
|
2897
|
-
className: "border-border bg-card
|
|
2802
|
+
className: "rounded-2xl border border-border bg-card p-4",
|
|
2898
2803
|
children: /* @__PURE__ */ jsxDEV9(SpecEditor, {
|
|
2899
2804
|
projectId: "sandbox",
|
|
2900
2805
|
type: "CAPABILITY",
|
|
@@ -2923,7 +2828,7 @@ var TemplateShell = ({
|
|
|
2923
2828
|
className: "space-y-6",
|
|
2924
2829
|
children: [
|
|
2925
2830
|
/* @__PURE__ */ jsxDEV10("header", {
|
|
2926
|
-
className: "border-border bg-card
|
|
2831
|
+
className: "rounded-2xl border border-border bg-card p-6 shadow-sm",
|
|
2927
2832
|
children: [
|
|
2928
2833
|
/* @__PURE__ */ jsxDEV10("div", {
|
|
2929
2834
|
className: "flex flex-wrap items-center justify-between gap-4",
|
|
@@ -2931,15 +2836,15 @@ var TemplateShell = ({
|
|
|
2931
2836
|
/* @__PURE__ */ jsxDEV10("div", {
|
|
2932
2837
|
children: [
|
|
2933
2838
|
/* @__PURE__ */ jsxDEV10("p", {
|
|
2934
|
-
className: "text-muted-foreground text-sm
|
|
2839
|
+
className: "font-semibold text-muted-foreground text-sm uppercase tracking-wide",
|
|
2935
2840
|
children: "ContractSpec Templates"
|
|
2936
2841
|
}, undefined, false, undefined, this),
|
|
2937
2842
|
/* @__PURE__ */ jsxDEV10("h1", {
|
|
2938
|
-
className: "text-3xl
|
|
2843
|
+
className: "font-bold text-3xl",
|
|
2939
2844
|
children: title
|
|
2940
2845
|
}, undefined, false, undefined, this),
|
|
2941
2846
|
description ? /* @__PURE__ */ jsxDEV10("p", {
|
|
2942
|
-
className: "
|
|
2847
|
+
className: "mt-2 max-w-2xl text-muted-foreground text-sm",
|
|
2943
2848
|
children: description
|
|
2944
2849
|
}, undefined, false, undefined, this) : null
|
|
2945
2850
|
]
|
|
@@ -2969,7 +2874,7 @@ var TemplateShell = ({
|
|
|
2969
2874
|
children
|
|
2970
2875
|
}, undefined, false, undefined, this),
|
|
2971
2876
|
sidebar ? /* @__PURE__ */ jsxDEV10("aside", {
|
|
2972
|
-
className: "border-border bg-card
|
|
2877
|
+
className: "rounded-2xl border border-border bg-card p-4",
|
|
2973
2878
|
children: sidebar
|
|
2974
2879
|
}, undefined, false, undefined, this) : null
|
|
2975
2880
|
]
|
|
@@ -2977,8 +2882,37 @@ var TemplateShell = ({
|
|
|
2977
2882
|
]
|
|
2978
2883
|
}, undefined, true, undefined, this);
|
|
2979
2884
|
|
|
2885
|
+
// src/hooks/useRegistryTemplates.ts
|
|
2886
|
+
import { useQuery } from "@tanstack/react-query";
|
|
2887
|
+
function useRegistryTemplates() {
|
|
2888
|
+
return useQuery({
|
|
2889
|
+
queryKey: ["registryTemplates"],
|
|
2890
|
+
queryFn: async () => {
|
|
2891
|
+
const registryUrl = process.env.NEXT_PUBLIC_CONTRACTSPEC_REGISTRY_URL ?? "";
|
|
2892
|
+
if (!registryUrl)
|
|
2893
|
+
return [];
|
|
2894
|
+
const res = await fetch(`${registryUrl.replace(/\/$/, "")}/r/contractspec.json`, {
|
|
2895
|
+
method: "GET",
|
|
2896
|
+
headers: { Accept: "application/json" }
|
|
2897
|
+
});
|
|
2898
|
+
if (!res.ok)
|
|
2899
|
+
return [];
|
|
2900
|
+
const json = await res.json();
|
|
2901
|
+
const items = json.items ?? [];
|
|
2902
|
+
return items.filter((i) => i.type === "contractspec:template").map((i) => ({
|
|
2903
|
+
id: i.name,
|
|
2904
|
+
name: i.title ?? i.name,
|
|
2905
|
+
description: i.description,
|
|
2906
|
+
tags: i.meta?.tags ?? [],
|
|
2907
|
+
source: "registry",
|
|
2908
|
+
registryUrl
|
|
2909
|
+
}));
|
|
2910
|
+
}
|
|
2911
|
+
});
|
|
2912
|
+
}
|
|
2913
|
+
|
|
2980
2914
|
// src/hooks/useWorkflowComposer.ts
|
|
2981
|
-
import { useCallback as
|
|
2915
|
+
import { useCallback as useCallback10, useEffect as useEffect6, useMemo as useMemo7, useState as useState8 } from "react";
|
|
2982
2916
|
"use client";
|
|
2983
2917
|
function useWorkflowComposer(templateId) {
|
|
2984
2918
|
const [selectedWorkflow, setSelectedWorkflow] = useState8(null);
|
|
@@ -2995,7 +2929,7 @@ function useWorkflowComposer(templateId) {
|
|
|
2995
2929
|
const currentBase = useMemo7(() => {
|
|
2996
2930
|
return baseWorkflows.find((w) => w.meta.key === selectedWorkflow) ?? null;
|
|
2997
2931
|
}, [baseWorkflows, selectedWorkflow]);
|
|
2998
|
-
const compose =
|
|
2932
|
+
const compose = useCallback10((scope) => {
|
|
2999
2933
|
if (!currentBase)
|
|
3000
2934
|
return null;
|
|
3001
2935
|
const applicableExtensions = extensions.filter((ext) => ext.workflow === currentBase.meta.key).filter((ext) => matchesScope(ext, scope)).sort((a, b) => (a.priority ?? 0) - (b.priority ?? 0));
|
|
@@ -3009,13 +2943,13 @@ function useWorkflowComposer(templateId) {
|
|
|
3009
2943
|
return composedWorkflow;
|
|
3010
2944
|
}, [currentBase, extensions]);
|
|
3011
2945
|
const workflow = useMemo7(() => compose(), [compose]);
|
|
3012
|
-
const selectWorkflow =
|
|
2946
|
+
const selectWorkflow = useCallback10((workflowName) => {
|
|
3013
2947
|
setSelectedWorkflow(workflowName);
|
|
3014
2948
|
}, []);
|
|
3015
|
-
const addExtension =
|
|
2949
|
+
const addExtension = useCallback10((extension) => {
|
|
3016
2950
|
setExtensions((prev) => [...prev, extension]);
|
|
3017
2951
|
}, []);
|
|
3018
|
-
const removeExtension =
|
|
2952
|
+
const removeExtension = useCallback10((workflowName, index) => {
|
|
3019
2953
|
setExtensions((prev) => {
|
|
3020
2954
|
const forWorkflow = prev.filter((e) => e.workflow === workflowName);
|
|
3021
2955
|
const others = prev.filter((e) => e.workflow !== workflowName);
|
|
@@ -3023,7 +2957,7 @@ function useWorkflowComposer(templateId) {
|
|
|
3023
2957
|
return [...others, ...forWorkflow];
|
|
3024
2958
|
});
|
|
3025
2959
|
}, []);
|
|
3026
|
-
const generateSpecCode =
|
|
2960
|
+
const generateSpecCode = useCallback10(() => {
|
|
3027
2961
|
const composed = workflow;
|
|
3028
2962
|
if (!composed) {
|
|
3029
2963
|
return "// No workflow selected";
|
|
@@ -3467,47 +3401,8 @@ function getTemplateWorkflows(templateId) {
|
|
|
3467
3401
|
};
|
|
3468
3402
|
return templateWorkflows[templateId] ?? [];
|
|
3469
3403
|
}
|
|
3470
|
-
|
|
3471
|
-
// src/hooks/useRegistryTemplates.ts
|
|
3472
|
-
import { useQuery } from "@tanstack/react-query";
|
|
3473
|
-
function useRegistryTemplates() {
|
|
3474
|
-
return useQuery({
|
|
3475
|
-
queryKey: ["registryTemplates"],
|
|
3476
|
-
queryFn: async () => {
|
|
3477
|
-
const registryUrl = process.env.NEXT_PUBLIC_CONTRACTSPEC_REGISTRY_URL ?? "";
|
|
3478
|
-
if (!registryUrl)
|
|
3479
|
-
return [];
|
|
3480
|
-
const res = await fetch(`${registryUrl.replace(/\/$/, "")}/r/contractspec.json`, {
|
|
3481
|
-
method: "GET",
|
|
3482
|
-
headers: { Accept: "application/json" }
|
|
3483
|
-
});
|
|
3484
|
-
if (!res.ok)
|
|
3485
|
-
return [];
|
|
3486
|
-
const json = await res.json();
|
|
3487
|
-
const items = json.items ?? [];
|
|
3488
|
-
return items.filter((i) => i.type === "contractspec:template").map((i) => ({
|
|
3489
|
-
id: i.name,
|
|
3490
|
-
name: i.title ?? i.name,
|
|
3491
|
-
description: i.description,
|
|
3492
|
-
tags: i.meta?.tags ?? [],
|
|
3493
|
-
source: "registry",
|
|
3494
|
-
registryUrl
|
|
3495
|
-
}));
|
|
3496
|
-
}
|
|
3497
|
-
});
|
|
3498
|
-
}
|
|
3499
|
-
// src/utils/fetchPresentationData.ts
|
|
3500
|
-
async function fetchPresentationData(_presentationName, _templateId) {
|
|
3501
|
-
throw new Error("fetchPresentationData is deprecated. Use fetchData from TemplateRuntimeContext.");
|
|
3502
|
-
}
|
|
3503
|
-
function hasPresentationDataFetcher(_presentationName) {
|
|
3504
|
-
return false;
|
|
3505
|
-
}
|
|
3506
|
-
function getRegisteredPresentationFetchers() {
|
|
3507
|
-
return [];
|
|
3508
|
-
}
|
|
3509
3404
|
// src/lib/component-registry.tsx
|
|
3510
|
-
import {
|
|
3405
|
+
import { useEffect as useEffect7, useState as useState9 } from "react";
|
|
3511
3406
|
"use client";
|
|
3512
3407
|
|
|
3513
3408
|
class TemplateComponentRegistry {
|
|
@@ -3542,6 +3437,18 @@ function useTemplateComponents(templateId) {
|
|
|
3542
3437
|
}, [templateId]);
|
|
3543
3438
|
return components;
|
|
3544
3439
|
}
|
|
3440
|
+
// src/utils/fetchPresentationData.ts
|
|
3441
|
+
async function fetchPresentationData(_presentationName, _templateId) {
|
|
3442
|
+
throw new Error("fetchPresentationData is deprecated. Use fetchData from TemplateRuntimeContext.");
|
|
3443
|
+
}
|
|
3444
|
+
function hasPresentationDataFetcher(_presentationName) {
|
|
3445
|
+
return false;
|
|
3446
|
+
}
|
|
3447
|
+
function getRegisteredPresentationFetchers() {
|
|
3448
|
+
return [];
|
|
3449
|
+
}
|
|
3450
|
+
// src/index.ts
|
|
3451
|
+
import { MarkdownRenderer as MarkdownRenderer2 } from "@contractspec/lib.design-system";
|
|
3545
3452
|
export {
|
|
3546
3453
|
useWorkflowComposer,
|
|
3547
3454
|
useTemplateRuntime,
|
|
@@ -3567,7 +3474,7 @@ export {
|
|
|
3567
3474
|
PersonalizationInsights,
|
|
3568
3475
|
OverlayContextProvider,
|
|
3569
3476
|
MarkdownView,
|
|
3570
|
-
MarkdownRenderer,
|
|
3477
|
+
MarkdownRenderer2 as MarkdownRenderer,
|
|
3571
3478
|
LocalDataIndicator,
|
|
3572
3479
|
EvolutionSidebar,
|
|
3573
3480
|
EvolutionDashboard
|