@burdenoff/fluidgrids-fe-sdk 2026.1111.14 → 2026.1111.15

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (43) hide show
  1. package/README.md +41 -0
  2. package/dist/{ExecutionDetailPage-itor_whl.js → ExecutionDetailPage-DO38vZ_F.js} +4 -4
  3. package/dist/{FluidGridsProvider-B30VcLdX.js → FluidGridsProvider-B9RR_CI_.js} +2 -309
  4. package/dist/{HistoryPage-DueEld8g.js → HistoryPage-CA42pU85.js} +1 -1
  5. package/dist/{InsightsPage-DQ7KCR9h.js → InsightsPage-CBoN_Mj9.js} +2 -2
  6. package/dist/{ManagedAiPolicyAuthority-C0YPTJMS.js → ManagedAiPolicyAuthority-CKihmbJE.js} +2 -2
  7. package/dist/{MissingNodesInstallModal-Cj31oMDX.js → MissingNodesInstallModal-Dm0nMBXM.js} +1 -1
  8. package/dist/{TemplateConfigurationModal-BAPCG8y-.js → TemplateConfigurationModal-Bs_V-E4u.js} +1 -1
  9. package/dist/{TemplateDetailPanel-CZ1uxEQL.js → TemplateDetailPanel-MlT39VLG.js} +1 -1
  10. package/dist/{TemplatesPage-DWdgZnIH.js → TemplatesPage-CHVpWBuw.js} +5 -4
  11. package/dist/{WorkflowSearchRedirect-C8vhSZK9.js → WorkflowSearchRedirect-3gyHcYY2.js} +13 -9
  12. package/dist/{WorkflowShareDialog-DnBQA3V6.js → WorkflowShareDialog-0Ai1HED-.js} +2 -1
  13. package/dist/{WorkflowsList-74jjJFsJ.js → WorkflowsList-CJ3KmMHX.js} +5 -4
  14. package/dist/agent-tools.d.ts +3 -0
  15. package/dist/agent-tools.js +5 -0
  16. package/dist/{agentTools-D5AW7zHn.js → agentTools-B1IK1JEO.js} +2 -2
  17. package/dist/{canvasNoteTools-BqQTTCll.js → canvasNoteTools-eewVHVuy.js} +3 -2
  18. package/dist/executions.js +1 -1
  19. package/dist/{flow-builder-BR8p5tXG.js → flow-builder-C_3sY3pZ.js} +12 -157
  20. package/dist/fluidgridsEvents-CNdcrUNN.js +310 -0
  21. package/dist/history.js +1 -1
  22. package/dist/index-CHeY7_A1.d.ts +105 -0
  23. package/dist/{index-CLqh2u28.d.ts → index-DRf25-D3.d.ts} +7 -105
  24. package/dist/index.d.ts +3 -2
  25. package/dist/index.js +21 -946
  26. package/dist/marksStore-DGCXjTmZ.js +151 -0
  27. package/dist/{node-detail-view-Dnhqdn8C.js → node-detail-view-CAws5qjg.js} +3 -3
  28. package/dist/observability.d.ts +1 -1
  29. package/dist/observability.js +1 -1
  30. package/dist/{quick-config-panel-C4tSpCrt.js → quick-config-panel-DOzNkSVV.js} +2 -2
  31. package/dist/settings.js +1 -1
  32. package/dist/templates.js +1 -1
  33. package/dist/uiMarkTools-nlmzsHQM.js +937 -0
  34. package/dist/{useExecutions-CNEN1ENQ.js → useExecutions-DkS0FTfw.js} +2 -1
  35. package/dist/{useObservability-CmFFXmKb.js → useObservability-BkxhHZsX.js} +2 -1
  36. package/dist/{useRunHistory-DhU_mrzF.js → useRunHistory-DHehG09Z.js} +1 -1
  37. package/dist/{useWorkflows-D01LC39Y.js → useWorkflows-DyhtoVwp.js} +25 -5
  38. package/dist/workflow-builder.js +2 -2
  39. package/dist/workflow-route.d.ts +33 -0
  40. package/dist/workflow-route.js +4 -0
  41. package/dist/workflowRouteData-BkfVOc-O.js +169 -0
  42. package/dist/workflows-list.js +1 -1
  43. package/package.json +9 -1
@@ -1,7 +1,7 @@
1
1
  "use client";
2
- import { At as useSaveStatusStore, J as paramsFromOperation, K as nodeTitle, L as createConfiguredNode, W as fixedParameterState, Y as selectedOperationOf, _ as registryNodeData, f as isNodeConfigsInitialized, o as NODE_CONFIGS, pt as autosaveAllowedFor, xt as isFlowComplete } from "./FluidGridsProvider-B30VcLdX.js";
2
+ import { At as useSaveStatusStore, J as paramsFromOperation, K as nodeTitle, L as createConfiguredNode, W as fixedParameterState, Y as selectedOperationOf, _ as registryNodeData, f as isNodeConfigsInitialized, o as NODE_CONFIGS, pt as autosaveAllowedFor, xt as isFlowComplete } from "./FluidGridsProvider-B9RR_CI_.js";
3
3
  import { E as resolveOutputHandles, H as useFlowStore, T as resolveInputHandles } from "./node-operation-selection--oy-yEq_.js";
4
- import { I as computeAttachPosition, kt as isNodeTypeHiddenFromPalette } from "./flow-builder-BR8p5tXG.js";
4
+ import { Et as isNodeTypeHiddenFromPalette, N as computeAttachPosition } from "./flow-builder-C_3sY3pZ.js";
5
5
  import { AgentToolError, defineAgentTool } from "@burdenoff/fe-libs/shared/agent-tools";
6
6
  import { z } from "zod";
7
7
 
@@ -1,7 +1,8 @@
1
1
  "use client";
2
- import { g as notesKeyOf, v as useAgentMarksStore, y as toPlainText } from "./flow-builder-BR8p5tXG.js";
3
- import { J as paramsFromOperation, K as nodeTitle, Y as selectedOperationOf } from "./FluidGridsProvider-B30VcLdX.js";
2
+ import { n as useAgentMarksStore, r as toPlainText } from "./marksStore-DGCXjTmZ.js";
3
+ import { J as paramsFromOperation, K as nodeTitle, Y as selectedOperationOf } from "./FluidGridsProvider-B9RR_CI_.js";
4
4
  import { H as useFlowStore } from "./node-operation-selection--oy-yEq_.js";
5
+ import { g as notesKeyOf } from "./flow-builder-C_3sY3pZ.js";
5
6
  import { AgentToolError, defineAgentTool } from "@burdenoff/fe-libs/shared/agent-tools";
6
7
  import { z } from "zod";
7
8
 
@@ -1,4 +1,4 @@
1
1
  "use client";
2
- import { t as ExecutionDetailPage, y as ExecutionsListPage } from "./ExecutionDetailPage-itor_whl.js";
2
+ import { t as ExecutionDetailPage, y as ExecutionsListPage } from "./ExecutionDetailPage-DO38vZ_F.js";
3
3
 
4
4
  export { ExecutionDetailPage, ExecutionsListPage };
@@ -1,17 +1,19 @@
1
1
  "use client";
2
2
  import { A as nodeAccent, B as NODE_TYPE_DRAG_DATA_FORMAT, G as isTriggerOperation, H as useFlowStore, M as isImageIcon, T as resolveInputHandles, U as useIsValidConnection, V as STICKY_NOTE_TYPE, g as toCodeMirrorDiagnostics, j as NodeTypeIcon, r as CODE_WORKFLOW_NODE_TYPE, z as NODE_OPERATION_DRAG_DATA_FORMAT } from "./node-operation-selection--oy-yEq_.js";
3
- import { $ as isStringOptionList, $n as usePaletteGates, $t as inAppLeaveTarget, A as StoreNodeProductsByTypeDocument, An as isQuotaExhaustedFailure, At as useSaveStatusStore, B as useRunGuard, Bt as shouldReleaseForIdle, C as GetMyNodeInstallationsDocument, Ct as useSaveWorkflow, D as InstallWorkflowNodeDocument, E as InstallPurchasedNodeDocument, En as RUNS_QUOTA_NAME, F as getNodeMetadata, Ft as leaseCallQueue, G as nodeSubtitle, Gt as sessionBeforeReload, H as asRecord, Ht as EDIT_SESSION_ID, I as buildOperationSeed, It as leaseCallSequence, J as paramsFromOperation, Jt as AUTOSAVE_DEBOUNCE_MS, K as nodeTitle, Kt as rememberOwnStatusChange, Lt as phaseAfterAcquire, M as UninstallOrganizationPrivateNodeDocument, Mn as useNodeRegistryRevision, Mt as useEditLeaseStore, N as UninstallWorkflowNodeDocument, Nt as bannerOf, On as collectExtensions, Ot as refusalOfQuota, Pn as loadDefinitionJson, Pt as isLocked, R as useInsertNode, Rt as phaseAfterTakeOver, S as CreateStoreOrderDocument, St as useFlowValidator, T as InstallOrganizationPrivateNodeDocument, Tn as BILLING_PLANS_PATH, U as coerceNumber, Un as FLUIDGRIDS_FLAGS, Ut as forgetSessionForReload, V as workflowParameterIssues, Vt as tickAction, Wt as rememberSessionForReload, X as useNodeConfig, Xn as useDurableParityEnabled, Xt as canAutosave, Yn as useDurableFunctionNodesEnabled, Yt as AUTOSAVE_RETRY_DELAYS_MS, Zn as useFluidGridsFlag, _t as leavingLosesChanges, a as NODES_METADATA, ar as matchesAdapterProvider, at as casesFromRules, b as BrowseWorkflowNodesDocument, bn as emitWorkflowCreated, bt as watchLeavingLosesChanges, c as ensureInstalledNodeTypesLoaded, cn as structuredParameterType, cr as getNodeDetail, d as ensureRegistryNodeTypesLoaded, dn as isParamVisible, dr as useBuilderReadOnly, dt as useGuardedNavigate, en as saveFailureActionOf, er as usePhaseCFlags, et as optionListText, f as isNodeConfigsInitialized, fn as useFluidGridsAnalytics, ft as useManualSave, g as registerWorkflowNodeTypes, gt as editingLeaseLocked, ht as editStateFor, i as AVAILABLE_NODES, ir as isOptionalAdapter, it as SwitchRulesEditor, jn as useCanvasEdges, jt as useEditLeaseLocked, k as OrganizationPrivateNodesDocument, kt as saveIndicatorOf, l as ensureNodeConfigsLoaded, lr as buildStickyNode, lt as boundFieldsOf, m as refetchStoreNodes, mn as emitNodeInstalled, mt as departingSave, nn as useNodeExecution, nr as useWorkflowTestsEnabled, nt as resolveLoadOptionsSpec, o as NODE_CONFIGS, on as formatParameterValue, or as newConnectionProviderKey, ot as FieldTree, p as onNodeTypesUpdate, pn as openRunQuotaUpgradePrompt, pr as getGlobalStoreClient, pt as autosaveAllowedFor, q as optionText, qt as rememberRevision, rr as connectionsForAdapter, rt as ConditionTreeBuilder, s as NODE_TYPES, sn as parseParameterValue, sr as replaceAdapterConnections, st as parseMappingValue, t as FluidGridsContext, tn as workflowFingerprint, tt as optionListValues, ur as BuilderReadOnlyProvider, ut as missingRequiredParameters, v as scheduleNodePaletteLoad, vn as emitTemplateUsed, vt as savedEverythingBeforeLeaving, w as GetNodeInstallableVersionsDocument, x as BrowseWorkflowTemplatesDocument, xt as isFlowComplete, yn as emitUpgradeClicked, yt as touchesSavedFields, z as MissingParametersDialog, zt as releasesOnClose } from "./FluidGridsProvider-B30VcLdX.js";
3
+ import { $ as isStringOptionList, $t as inAppLeaveTarget, A as StoreNodeProductsByTypeDocument, At as useSaveStatusStore, B as useRunGuard, Bn as connectionsForAdapter, Bt as shouldReleaseForIdle, C as GetMyNodeInstallationsDocument, Ct as useSaveWorkflow, D as InstallWorkflowNodeDocument, E as InstallPurchasedNodeDocument, En as FLUIDGRIDS_FLAGS, F as getNodeMetadata, Ft as leaseCallQueue, G as nodeSubtitle, Gn as getNodeDetail, Gt as sessionBeforeReload, H as asRecord, Hn as matchesAdapterProvider, Ht as EDIT_SESSION_ID, I as buildOperationSeed, In as usePaletteGates, It as leaseCallSequence, J as paramsFromOperation, Jn as useBuilderReadOnly, Jt as AUTOSAVE_DEBOUNCE_MS, K as nodeTitle, Kn as buildStickyNode, Kt as rememberOwnStatusChange, Ln as usePhaseCFlags, Lt as phaseAfterAcquire, M as UninstallOrganizationPrivateNodeDocument, Mn as useDurableFunctionNodesEnabled, Mt as useEditLeaseStore, N as UninstallWorkflowNodeDocument, Nn as useDurableParityEnabled, Nt as bannerOf, Ot as refusalOfQuota, Pn as useFluidGridsFlag, Pt as isLocked, R as useInsertNode, Rt as phaseAfterTakeOver, S as CreateStoreOrderDocument, St as useFlowValidator, T as InstallOrganizationPrivateNodeDocument, U as coerceNumber, Un as newConnectionProviderKey, Ut as forgetSessionForReload, V as workflowParameterIssues, Vn as isOptionalAdapter, Vt as tickAction, Wn as replaceAdapterConnections, Wt as rememberSessionForReload, X as useNodeConfig, Xn as getGlobalStoreClient, Xt as canAutosave, Yt as AUTOSAVE_RETRY_DELAYS_MS, _n as loadDefinitionJson, _t as leavingLosesChanges, a as NODES_METADATA, at as casesFromRules, b as BrowseWorkflowNodesDocument, bt as watchLeavingLosesChanges, c as ensureInstalledNodeTypesLoaded, cn as structuredParameterType, d as ensureRegistryNodeTypesLoaded, dn as isParamVisible, dt as useGuardedNavigate, en as saveFailureActionOf, et as optionListText, f as isNodeConfigsInitialized, fn as useFluidGridsAnalytics, ft as useManualSave, g as registerWorkflowNodeTypes, gt as editingLeaseLocked, hn as useNodeRegistryRevision, ht as editStateFor, i as AVAILABLE_NODES, it as SwitchRulesEditor, jt as useEditLeaseLocked, k as OrganizationPrivateNodesDocument, kt as saveIndicatorOf, l as ensureNodeConfigsLoaded, lt as boundFieldsOf, m as refetchStoreNodes, mn as useCanvasEdges, mt as departingSave, nn as useNodeExecution, nt as resolveLoadOptionsSpec, o as NODE_CONFIGS, on as formatParameterValue, ot as FieldTree, p as onNodeTypesUpdate, pn as openRunQuotaUpgradePrompt, pt as autosaveAllowedFor, q as optionText, qn as BuilderReadOnlyProvider, qt as rememberRevision, rt as ConditionTreeBuilder, s as NODE_TYPES, sn as parseParameterValue, st as parseMappingValue, t as FluidGridsContext, tn as workflowFingerprint, tt as optionListValues, ut as missingRequiredParameters, v as scheduleNodePaletteLoad, vt as savedEverythingBeforeLeaving, w as GetNodeInstallableVersionsDocument, x as BrowseWorkflowTemplatesDocument, xt as isFlowComplete, yt as touchesSavedFields, z as MissingParametersDialog, zn as useWorkflowTestsEnabled, zt as releasesOnClose } from "./FluidGridsProvider-B9RR_CI_.js";
4
4
  import { r as useTr } from "./TranslationBridge-Da-TPgQm.js";
5
5
  import { Bi as describeOperationError, Br as WorkflowGitRepositoryDocument, Ct as LinkWorkflowGitRepositoryDocument, Dr as WorkflowDefinitionDocument, Ei as WorkspaceRunsQuotaDocument, Ht as PreviewScheduleDocument, Ir as WorkflowGenerationTemplatesDocument, J as DeleteWorkflowRolloutDocument, Kt as PushWorkflowToGitDocument, Li as emitFluidGridsEvent, Lr as WorkflowGitCommitsDocument, Mt as NodeSchemaIntrospectionDocument, Ni as waitForFluidGridsClient, Nr as WorkflowEnvironmentsDocument, Oi as getFluidGridsClient, Pt as NodeUsageStatusDocument, Qt as RemoveNodeFromWorkflowsDocument, Rr as WorkflowGitDiffDocument, Si as WorkflowVersioningDocument, Ui as throwIfResultError, Vn as TakeOverWorkflowEditLeaseDocument, Wr as WorkflowPromotionRequestsDocument, Xn as UnlinkWorkflowGitRepositoryDocument, Yt as RejectWorkflowPromotionDocument, Z as DeployWorkflowVersionToDevDocument, Zt as ReleaseWorkflowEditLeaseDocument, cr as UpdateWorkflowEnvironmentPolicyDocument, i as ActivateWorkflowVersionCheckedDocument, jn as SetWorkflowRolloutDocument, jr as WorkflowEditLeaseDocument, ki as getFluidGridsClientSafe, mr as WebhookTestListenerDocument, n as AcquireWorkflowEditLeaseDocument, nn as RequestWorkflowPromotionDocument, oa as __exportAll, on as RestoreWorkflowFromGitDocument, qi as getFluidGridsConfig, u as ApproveWorkflowPromotionDocument, wr as WorkflowCallInputsDocument, wt as ListenForWebhookTestEventDocument, x as CancelWorkflowPromotionDocument, xi as WorkflowVersionDrainageDocument, yr as WorkflowAuthoringDocument, zn as StopWebhookTestListenerDocument, zr as WorkflowGitPushesDocument } from "./node-endpoint-configs-DHFGA5MQ.js";
6
6
  import { D as describeSchedule, H as pauseSchedule, _ as useResource, c as FieldError, d as NativeSelect, et as triggerSchedule, nt as unpauseSchedule, p as StatusPill, r as describeRule, s as isAgentNodeType, v as backfillSchedule } from "./agent-form-BvMWhQ42.js";
7
7
  import { CF as WorkflowExportFormat, Eo as CodeReplaceStatus, PD as ScheduleType, QF as WorkflowTestExpectedStatus, SF as WorkflowEnvironment, VF as WorkflowScheduleOverlapPolicy, hI as FLUIDGRIDS_PERMISSIONS, vI as SdkPermissionButton, xI as useFluidGridsPermission, xu as DrainageStatus, yI as SdkPermissionGate, yP as VersioningBehavior } from "./graphql-types-XcDLtFwU.js";
8
8
  import { a as useConnections, r as useAgentsUsingConnection, t as useAgentDefinitionList, wt as useRunFromNodeEligibilityQuery } from "./useAgentDefinitions-NFtLytDR.js";
9
+ import { a as emitTemplateUsed, f as BILLING_PLANS_PATH, g as collectExtensions, m as RUNS_QUOTA_NAME, o as emitUpgradeClicked, s as emitWorkflowCreated, t as emitNodeInstalled, y as isQuotaExhaustedFailure } from "./fluidgridsEvents-CNdcrUNN.js";
9
10
  import { F as normaliseAssertRules, I as operatorSpec, L as readAssertRulesSetting, M as ASSERT_OPERATORS, N as describeAssertRuleProblem, P as emptyAssertRuleRow, R as rowsFromRules, _ as buildNodeDisplayMap, a as TEST_STATUS_TONE_CLASS, b as EntityTagPicker, c as draftToInput, d as isTestRunOpen, f as nextSortOrder, g as testStatusTone, h as testStatusLabel, i as useWorkflowTests, l as emptyTestCaseDraft, m as testRunSummaryText, n as useWorkflowProposal, p as pinnedOutputsFromCanvas, s as draftFromTestCase, t as WorkflowProposalCard, u as enabledCaseIds, z as ruleFromRow } from "./WorkflowProposalCard-8Vr56kQa.js";
10
11
  import { t as cn$1 } from "./cn-QqidFIgr.js";
11
12
  import { i as Button$2, t as PublishCustomNodeAction } from "./PublishCustomNodeAction-D2F7oN0S.js";
12
- import { O as CreateWorkflowRefusalDialog, b as lineOfNode, h as fileBaseName, i as useWorkflowCodeExport, n as downloadWorkflowCodeExport, t as WorkflowShareDialog, v as isLosslessReport, w as sortFidelityItems, x as orderedExportFiles, y as isLossyFidelityItem } from "./WorkflowShareDialog-DnBQA3V6.js";
13
+ import { n as useAgentMarksStore } from "./marksStore-DGCXjTmZ.js";
14
+ import { O as CreateWorkflowRefusalDialog, b as lineOfNode, h as fileBaseName, i as useWorkflowCodeExport, n as downloadWorkflowCodeExport, t as WorkflowShareDialog, v as isLosslessReport, w as sortFidelityItems, x as orderedExportFiles, y as isLossyFidelityItem } from "./WorkflowShareDialog-0Ai1HED-.js";
13
15
  import { t as FluidGridsDocsLink } from "./FluidGridsDocsLink-JxkBpOeb.js";
14
- import { a as useDeactivateWorkflow, d as useRestoreWorkflowVersion, o as useDeleteWorkflow, t as useActivateWorkflow, v as useWorkflowVersions } from "./useWorkflows-D01LC39Y.js";
16
+ import { a as useDeactivateWorkflow, d as useRestoreWorkflowVersion, o as useDeleteWorkflow, t as useActivateWorkflow, v as useWorkflowVersions } from "./useWorkflows-DyhtoVwp.js";
15
17
  import { n as VersionLifecycleBar, r as countLifecycle, t as VersionDiffDialog } from "./VersionDiffDialog-Dq2xlPFI.js";
16
18
  import { n as useRequestedProposal } from "./useRequestedProposal-B7uPXfZB.js";
17
19
  import { t as AiCreditBalanceSlot } from "./aiCreditsBridge-BuE92tKo.js";
@@ -10572,7 +10574,7 @@ function buildNodeCheck(requiredNodeTypes, installedAppIds) {
10572
10574
  }
10573
10575
 
10574
10576
  // src/hooks/store/useTemplateImportFlow.tsx
10575
- const LazyTemplateConfigurationModal = lazy(() => import("./TemplateConfigurationModal-BAPCG8y-.js").then((m) => ({ default: m.TemplateConfigurationModal })));
10577
+ const LazyTemplateConfigurationModal = lazy(() => import("./TemplateConfigurationModal-Bs_V-E4u.js").then((m) => ({ default: m.TemplateConfigurationModal })));
10576
10578
  /**
10577
10579
  * "Use this template", the same everywhere it is offered: the builder's
10578
10580
  * template panel, the Templates page and the template preview page
@@ -12749,7 +12751,7 @@ function TemplatesGrid({ templates, loading, hasMore, onLoadMore, onTemplateClic
12749
12751
  }
12750
12752
 
12751
12753
  // src/builder/components/flow-builder/components/templates/TemplatesModal.tsx
12752
- const LazyTemplateDetailPanel = lazy(() => import("./TemplateDetailPanel-CZ1uxEQL.js").then((m) => ({ default: m.TemplateDetailPanel })));
12754
+ const LazyTemplateDetailPanel = lazy(() => import("./TemplateDetailPanel-MlT39VLG.js").then((m) => ({ default: m.TemplateDetailPanel })));
12753
12755
  /**
12754
12756
  * Modal for browsing and selecting workflow templates
12755
12757
  * Features:
@@ -20692,153 +20694,6 @@ function WebhookRunFollower() {
20692
20694
  return null;
20693
20695
  }
20694
20696
 
20695
- // src/agentMarks/plainText.ts
20696
- /**
20697
- * ★ BOFF-11584: the text of a callout or note is model output, and the model
20698
- * has read workflow content people wrote. It is shown as plain text only:
20699
- * React renders it as a text node (never `dangerouslySetInnerHTML`, never a
20700
- * markdown renderer), so markup, links and images in it stay inert characters.
20701
- *
20702
- * This keeps it short and printable as well: control characters (other than
20703
- * line breaks) and bidirectional controls, which can disguise what a line
20704
- * says, are removed; runs of blank lines collapse; the result is clamped.
20705
- */
20706
- const BIDI_CONTROLS = /* @__PURE__ */ new Set([
20707
- 1564,
20708
- 8206,
20709
- 8207,
20710
- 8234,
20711
- 8235,
20712
- 8236,
20713
- 8237,
20714
- 8238,
20715
- 8294,
20716
- 8295,
20717
- 8296,
20718
- 8297
20719
- ]);
20720
- function isDroppedCharacter(code) {
20721
- if (code === 10) return false;
20722
- if (code <= 31) return true;
20723
- if (code >= 127 && code <= 159) return true;
20724
- return BIDI_CONTROLS.has(code);
20725
- }
20726
- function toPlainText(text, max) {
20727
- let kept = "";
20728
- for (const character of text.replace(/\r\n?/g, "\n").replace(/\t/g, " ")) if (!isDroppedCharacter(character.codePointAt(0) ?? 0)) kept += character;
20729
- const cleaned = kept.replace(/ {2,}/g, " ").replace(/ *\n */g, "\n").replace(/\n{3,}/g, "\n\n").trim();
20730
- if (cleaned.length <= max) return cleaned;
20731
- return `${cleaned.slice(0, max - 1).trimEnd()}…`;
20732
- }
20733
-
20734
- // src/agentMarks/marksStore.ts
20735
- /** The text of a mark is model output: kept as plain text, never markup. */
20736
- const CALLOUT_LABEL_MAX = 200;
20737
- const NOTE_MESSAGE_MAX = 280;
20738
- /** A workflow holds at most this many notes, resolved ones included. */
20739
- const MAX_NOTES_PER_WORKFLOW = 20;
20740
- let sequence = 0;
20741
- const nextId = (prefix) => {
20742
- sequence += 1;
20743
- return `${prefix}${sequence}`;
20744
- };
20745
- const useAgentMarksStore = create()((set, get) => ({
20746
- callouts: [],
20747
- notes: [],
20748
- nextNumber: {},
20749
- openNoteId: null,
20750
- flash: null,
20751
- actions: {
20752
- addCallout: ({ label, target, element, route }) => {
20753
- const callout = {
20754
- id: nextId("c"),
20755
- label: toPlainText(label, 200),
20756
- target,
20757
- route,
20758
- element: element ? new WeakRef(element) : null
20759
- };
20760
- set((state) => ({ callouts: [...state.callouts, callout].slice(-3) }));
20761
- return callout;
20762
- },
20763
- rebindCallout: (id, element) => set((state) => ({ callouts: state.callouts.map((callout) => callout.id === id ? {
20764
- ...callout,
20765
- element: new WeakRef(element)
20766
- } : callout) })),
20767
- removeCallout: (id) => set((state) => ({ callouts: state.callouts.filter((callout) => callout.id !== id) })),
20768
- clearCallouts: () => {
20769
- const count = get().callouts.length;
20770
- if (count > 0) set({ callouts: [] });
20771
- return count;
20772
- },
20773
- dropCalloutsOffRoute: (route) => {
20774
- const { callouts } = get();
20775
- const kept = callouts.filter((callout) => callout.route === route);
20776
- if (kept.length !== callouts.length) set({ callouts: kept });
20777
- return callouts.length - kept.length;
20778
- },
20779
- addNote: (input) => {
20780
- const { notes, nextNumber } = get();
20781
- if (notes.filter((note) => note.workflowKey === input.workflowKey).length >= 20) return null;
20782
- const number = nextNumber[input.workflowKey] ?? 1;
20783
- const note = {
20784
- id: nextId("n"),
20785
- number,
20786
- workflowKey: input.workflowKey,
20787
- nodeId: input.nodeId,
20788
- nodeLabel: toPlainText(input.nodeLabel, 80),
20789
- paramKey: input.paramKey ?? null,
20790
- kind: input.kind,
20791
- message: toPlainText(input.message, 280),
20792
- resolved: false
20793
- };
20794
- set({
20795
- notes: [...notes, note],
20796
- nextNumber: {
20797
- ...nextNumber,
20798
- [input.workflowKey]: number + 1
20799
- }
20800
- });
20801
- return note;
20802
- },
20803
- setResolved: (id, resolved) => set((state) => ({ notes: state.notes.map((note) => note.id === id ? {
20804
- ...note,
20805
- resolved
20806
- } : note) })),
20807
- removeNote: (id) => set((state) => ({
20808
- notes: state.notes.filter((note) => note.id !== id),
20809
- openNoteId: state.openNoteId === id ? null : state.openNoteId
20810
- })),
20811
- clearNotes: (workflowKey) => {
20812
- const { notes, openNoteId } = get();
20813
- const kept = workflowKey === void 0 ? [] : notes.filter((note) => note.workflowKey !== workflowKey);
20814
- const removed = notes.length - kept.length;
20815
- if (removed > 0) set({
20816
- notes: kept,
20817
- openNoteId: kept.some((note) => note.id === openNoteId) ? openNoteId : null
20818
- });
20819
- return removed;
20820
- },
20821
- openNote: (id) => set({ openNoteId: id }),
20822
- flashNode: (nodeId) => {
20823
- sequence += 1;
20824
- set({ flash: {
20825
- nodeId,
20826
- token: sequence
20827
- } });
20828
- }
20829
- }
20830
- }));
20831
- /** Reset everything (tests, and sign-out if a host wants it). */
20832
- function resetAgentMarks() {
20833
- useAgentMarksStore.setState({
20834
- callouts: [],
20835
- notes: [],
20836
- nextNumber: {},
20837
- openNoteId: null,
20838
- flash: null
20839
- });
20840
- }
20841
-
20842
20697
  // src/builder/agentNotes/notesKey.ts
20843
20698
  /**
20844
20699
  * ★ BOFF-11584: which workflow a canvas note belongs to. A saved workflow is
@@ -27575,8 +27430,8 @@ function EditLeaseBanner() {
27575
27430
  }
27576
27431
 
27577
27432
  // src/builder/components/flow-builder/flow-builder.tsx
27578
- const LazyNodeDetailView = lazy(() => import("./node-detail-view-Dnhqdn8C.js").then((m) => ({ default: m.NodeDetailView })));
27579
- const LazyQuickConfigPanel = lazy(() => import("./quick-config-panel-C4tSpCrt.js").then((m) => ({ default: m.QuickConfigPanel })));
27433
+ const LazyNodeDetailView = lazy(() => import("./node-detail-view-CAws5qjg.js").then((m) => ({ default: m.NodeDetailView })));
27434
+ const LazyQuickConfigPanel = lazy(() => import("./quick-config-panel-DOzNkSVV.js").then((m) => ({ default: m.QuickConfigPanel })));
27580
27435
  const edgeTypes = { deletable: CustomDeletableEdge };
27581
27436
  const edgeOptions = {
27582
27437
  type: "deletable",
@@ -27636,7 +27491,7 @@ const FlowBuilder = ({ readOnly = false }) => {
27636
27491
  const [agentTools, setAgentTools] = useState([]);
27637
27492
  useEffect(() => {
27638
27493
  let cancelled = false;
27639
- import("./agentTools-D5AW7zHn.js").then(({ createBuilderAgentTools }) => {
27494
+ import("./agentTools-B1IK1JEO.js").then(({ createBuilderAgentTools }) => {
27640
27495
  if (cancelled) return;
27641
27496
  setAgentTools(createBuilderAgentTools({ durableFunctionsEnabled: () => paletteGatesRef.current }));
27642
27497
  }).catch((error) => {
@@ -27691,7 +27546,7 @@ const FlowBuilder = ({ readOnly = false }) => {
27691
27546
  const [noteTools, setNoteTools] = useState([]);
27692
27547
  useEffect(() => {
27693
27548
  let cancelled = false;
27694
- import("./canvasNoteTools-BqQTTCll.js").then(({ createCanvasNoteTools }) => {
27549
+ import("./canvasNoteTools-eewVHVuy.js").then(({ createCanvasNoteTools }) => {
27695
27550
  if (cancelled) return;
27696
27551
  setNoteTools(createCanvasNoteTools({ focusNode: (nodeId) => fitViewRef.current({
27697
27552
  nodes: [{ id: nodeId }],
@@ -27999,4 +27854,4 @@ const FlowBuilderPage = ({ workflow, readOnly = false }) => {
27999
27854
  ] });
28000
27855
  };
28001
27856
 
28002
- export { NodeParamsForm as $, DialogFooter$1 as A, isRunControlNodeType as At, getWorkflowNodeTypes as B, templatePreview as C, Input$1 as Ct, DialogClose as D, filterPaletteNodes as Dt, Dialog$1 as E, WORKFLOW_TEST_NODE_TYPES as Et, DialogTrigger$1 as F, NodeEditorTabBody as G, useWorkflowTemplates as H, computeAttachPosition as I, RunnerStatusPill as J, NodeSettingsPanel as K, useTemplateImportFlow as L, DialogOverlay as M, DialogPortal as N, DialogContent$1 as O, isDurableFunctionNodeType as Ot, DialogTitle$1 as P, useRunners as Q, buildNodeCheck as R, TemplateCard as S, CardTitle$1 as St, badgeVariants as T, RUN_CONTROL_NODE_TYPES as Tt, useInstalledNodes as U, useImportWorkflowTemplate as V, NodeExecutionActions as W, runnerInstallCommand as X, RUNNER_INSTALL_SCRIPT_URL as Y, useRunnerActions as Z, resetAgentMarks as _, Card$1 as _t, useAiWorkflowTemplates as a, CodeEditorField as at, JsonView as b, CardFooter as bt, RunsUsageMeter as c, ReadOnlyFieldset as ct, readRunsQuota as d, SchedulePanel as dt, useGlobalStoreClient as et, runsQuotaLevel as f, NodeEditorTabs as ft, notesKeyOf as g, FluidGridsMark as gt, useWorkflowReloadStore as h, useNodeSelectedEvent as ht, enrichDraftNodes as i, PopoverTrigger$1 as it, DialogHeader$1 as j, DialogDescription$1 as k, isNodeTypeHiddenFromPalette as kt, RunsUsageMeterView as l, useNodeEditorTab as lt, releaseLeaseKeptForReload as m, NodeInputFields as mt, AI_DRAFT_MAX_PROMPT_LENGTH as n, Popover$1 as nt, BUILDER_FULLSCREEN_ATTRIBUTE as o, ConnectionSelector as ot, summarizeRunsQuota as p, TabButton as pt, RunOnSection as q, draftToCanvas as r, PopoverContent$1 as rt, BUILDER_FULLSCREEN_EVENT as s, ConnectionFormDialog as st, FlowBuilderPage as t, NDV_Z_INDEX as tt, useRunsQuota as u, SCHEDULE_NODE_TYPE as ut, useAgentMarksStore as v, CardContent$1 as vt, Badge$1 as w, DURABLE_FUNCTION_NODE_TYPES as wt, TableView as x, CardHeader$1 as xt, toPlainText as y, CardDescription$1 as yt, buildRequiredNodeTypes as z };
27857
+ export { Popover$1 as $, DialogPortal as A, useInstalledNodes as B, Dialog$1 as C, WORKFLOW_TEST_NODE_TYPES as Ct, DialogFooter$1 as D, isRunControlNodeType as Dt, DialogDescription$1 as E, isNodeTypeHiddenFromPalette as Et, buildNodeCheck as F, RunnerStatusPill as G, NodeEditorTabBody as H, buildRequiredNodeTypes as I, useRunnerActions as J, RUNNER_INSTALL_SCRIPT_URL as K, getWorkflowNodeTypes as L, DialogTrigger$1 as M, computeAttachPosition as N, DialogHeader$1 as O, useTemplateImportFlow as P, NDV_Z_INDEX as Q, useImportWorkflowTemplate as R, badgeVariants as S, RUN_CONTROL_NODE_TYPES as St, DialogContent$1 as T, isDurableFunctionNodeType as Tt, NodeSettingsPanel as U, NodeExecutionActions as V, RunOnSection as W, NodeParamsForm as X, useRunners as Y, useGlobalStoreClient as Z, JsonView as _, CardFooter as _t, useAiWorkflowTemplates as a, ReadOnlyFieldset as at, templatePreview as b, Input$1 as bt, RunsUsageMeter as c, SchedulePanel as ct, readRunsQuota as d, NodeInputFields as dt, PopoverContent$1 as et, runsQuotaLevel as f, useNodeSelectedEvent as ft, notesKeyOf as g, CardDescription$1 as gt, useWorkflowReloadStore as h, CardContent$1 as ht, enrichDraftNodes as i, ConnectionFormDialog as it, DialogTitle$1 as j, DialogOverlay as k, RunsUsageMeterView as l, NodeEditorTabs as lt, releaseLeaseKeptForReload as m, Card$1 as mt, AI_DRAFT_MAX_PROMPT_LENGTH as n, CodeEditorField as nt, BUILDER_FULLSCREEN_ATTRIBUTE as o, useNodeEditorTab as ot, summarizeRunsQuota as p, FluidGridsMark as pt, runnerInstallCommand as q, draftToCanvas as r, ConnectionSelector as rt, BUILDER_FULLSCREEN_EVENT as s, SCHEDULE_NODE_TYPE as st, FlowBuilderPage as t, PopoverTrigger$1 as tt, useRunsQuota as u, TabButton as ut, TableView as v, CardHeader$1 as vt, DialogClose as w, filterPaletteNodes as wt, Badge$1 as x, DURABLE_FUNCTION_NODE_TYPES as xt, TemplateCard as y, CardTitle$1 as yt, useWorkflowTemplates as z };
@@ -0,0 +1,310 @@
1
+ "use client";
2
+ // src/billing/quota.ts
3
+ /**
4
+ * Plan-quota refusals for the FluidGrids SDK.
5
+ *
6
+ * wspace-workflow-svc meters two quotas with `@usage`, and the gateway refuses
7
+ * a call past either one with `429 QUOTA_EXHAUSTED`:
8
+ *
9
+ * - `fluidgrids.runs.monthly` — every mutation that starts a run:
10
+ * `triggerWorkflow`, `runFromNode`, `replayWorkflowRun`, `retryWorkflowRuns`
11
+ * and `listenForWebhookTestEvent`.
12
+ * - `fluidgrids.workflows.count` — the mutations that create a workflow
13
+ * (save, duplicate, template import). Those keep their local
14
+ * `QuotaExhaustedDialog`.
15
+ * - `fluidgrids.nodes.count` — node additions are counted by workflow save;
16
+ * the same save dialog handles its refusal.
17
+ *
18
+ * A run refusal opens the shell's shared upgrade prompt — see
19
+ * `openRunQuotaUpgradePrompt` in `./upgradePrompt`. This module is the pure
20
+ * detection half, so it imports nothing from `@burdenoff/fe-libs`.
21
+ *
22
+ * ★★ Why this does not just call fe-libs `isQuotaExhaustedError`. That helper
23
+ * reads the Apollo 3 shapes (`graphQLErrors`, `networkError.result.errors`, a
24
+ * code in the message). Under Apollo 4 — what every host runs — the refusal
25
+ * never takes those shapes:
26
+ *
27
+ * - the gateway answers `429`, and Apollo 4's HTTP link turns any non-2xx
28
+ * `application/json` response into a `ServerError` whose GraphQL body is
29
+ * only in `bodyText` (message: "Response not successful: Received status
30
+ * code 429");
31
+ * - a 2xx GraphQL error arrives as `CombinedGraphQLErrors`, whose list is
32
+ * `.errors`, not `.graphQLErrors`;
33
+ * - `throwIfResultError` wraps either one in a plain `Error`, keeping the
34
+ * original as `cause`.
35
+ *
36
+ * None of those match, so the refusal read as an ordinary failure. This walker
37
+ * reads all of them, and the Apollo 3 shapes too.
38
+ */
39
+ /** The monthly run allowance every run-starting mutation is metered against. */
40
+ const RUNS_QUOTA_NAME = "fluidgrids.runs.monthly";
41
+ /** The workflow-count allowance save / duplicate / template import consume. */
42
+ const WORKFLOWS_QUOTA_NAME = "fluidgrids.workflows.count";
43
+ /**
44
+ * Where an upgrade CTA sends the user: the plan picker, not the billing
45
+ * overview. Matches the shared `UpgradePromptModal` default and the shell nav.
46
+ */
47
+ const BILLING_PLANS_PATH = "/billing/plans";
48
+ const QUOTA_EXHAUSTED_CODE = "QUOTA_EXHAUSTED";
49
+ const QUOTA_NOT_PROVISIONED_CODE = "QUOTA_NOT_PROVISIONED";
50
+ function asRecord$1(value) {
51
+ return typeof value === "object" && value !== null ? value : null;
52
+ }
53
+ /** The `extensions` of each entry of an `errors`-like list. */
54
+ function extensionsOfList(list) {
55
+ if (!Array.isArray(list)) return [];
56
+ const found = [];
57
+ for (const entry of list) {
58
+ const extensions = asRecord$1(asRecord$1(entry)?.extensions);
59
+ if (extensions) found.push(extensions);
60
+ }
61
+ return found;
62
+ }
63
+ /** The GraphQL `errors[].extensions` inside a raw response body, if it is JSON. */
64
+ function extensionsOfBody(bodyText) {
65
+ if (typeof bodyText !== "string" || !bodyText.includes("errors")) return [];
66
+ try {
67
+ return extensionsOfList(asRecord$1(JSON.parse(bodyText))?.errors);
68
+ } catch {
69
+ return [];
70
+ }
71
+ }
72
+ /** Bounds the `cause` walk; real chains are one or two links long. */
73
+ const MAX_CAUSE_DEPTH = 5;
74
+ /**
75
+ * Every `extensions` object reachable on a thrown value, across the Apollo 3
76
+ * and Apollo 4 shapes and the `cause` chain `throwIfResultError` adds.
77
+ */
78
+ function collectExtensions(error) {
79
+ const found = [];
80
+ const seen = /* @__PURE__ */ new Set();
81
+ let current = error;
82
+ for (let depth = 0; depth < MAX_CAUSE_DEPTH; depth += 1) {
83
+ const host = asRecord$1(current);
84
+ if (!host || seen.has(host)) break;
85
+ seen.add(host);
86
+ const direct = asRecord$1(host.extensions);
87
+ if (direct) found.push(direct);
88
+ found.push(...extensionsOfList(host.errors));
89
+ found.push(...extensionsOfList(host.graphQLErrors));
90
+ const networkError = asRecord$1(host.networkError);
91
+ found.push(...extensionsOfList(asRecord$1(networkError?.result)?.errors));
92
+ found.push(...extensionsOfBody(networkError?.bodyText));
93
+ found.push(...extensionsOfList(asRecord$1(host.result)?.errors));
94
+ found.push(...extensionsOfBody(host.bodyText));
95
+ current = host.cause;
96
+ }
97
+ return found;
98
+ }
99
+ /** Every GraphQL `extensions.code` carried by `error` or its causes. */
100
+ function errorCodesOf(error) {
101
+ return collectExtensions(error).map((ext) => ext.code).filter((code) => typeof code === "string");
102
+ }
103
+ function stringField(extensions, key) {
104
+ const value = extensions[key];
105
+ return typeof value === "string" && value.length > 0 ? value : null;
106
+ }
107
+ /**
108
+ * The refusal kind one GraphQL `extensions` object reports, or null.
109
+ *
110
+ * The gateway sets both `code` and `quotaBlock` on a quota refusal
111
+ * (`sendQuotaExhausted` in wspace-public-gateway); either is enough here, so
112
+ * a refusal relayed with only one of them (a proxy, an older gateway build)
113
+ * still reads as one.
114
+ */
115
+ function refusalKindOf(extensions) {
116
+ if (extensions.code === "QUOTA_NOT_PROVISIONED" || extensions.quotaBlock === "not-provisioned") return "not-provisioned";
117
+ if (extensions.code === "QUOTA_EXHAUSTED" || extensions.quotaBlock === "exhausted") return "exhausted";
118
+ return null;
119
+ }
120
+ /**
121
+ * The quota refusal carried by `error`, or null when it is not one.
122
+ *
123
+ * Keyed on `extensions.code` (or the gateway's `extensions.quotaBlock`), never
124
+ * on the HTTP status or the message: both refusals are 429s, and only those
125
+ * fields tell "used up" from "never granted". `not-provisioned` wins when both
126
+ * appear.
127
+ */
128
+ function findQuotaRefusal(error) {
129
+ const all = collectExtensions(error);
130
+ const notProvisioned = all.find((ext) => refusalKindOf(ext) === "not-provisioned");
131
+ if (notProvisioned) return {
132
+ kind: "not-provisioned",
133
+ quotaName: stringField(notProvisioned, "quotaName"),
134
+ limitLeft: null
135
+ };
136
+ const exhausted = all.find((ext) => refusalKindOf(ext) === "exhausted");
137
+ if (exhausted) {
138
+ const limitLeft = exhausted.limitLeft;
139
+ return {
140
+ kind: "exhausted",
141
+ quotaName: stringField(exhausted, "quotaName"),
142
+ limitLeft: typeof limitLeft === "number" ? limitLeft : null
143
+ };
144
+ }
145
+ return null;
146
+ }
147
+ /** True when `error` is an exhausted (not merely unprovisioned) plan quota. */
148
+ function isQuotaExhaustedFailure(error) {
149
+ return findQuotaRefusal(error)?.kind === "exhausted";
150
+ }
151
+
152
+ // src/analytics/fluidgridsEvents.ts
153
+ /** `component` stamped on every event so devtools/OTel can tell the emitter. */
154
+ const FLUIDGRIDS_ANALYTICS_COMPONENT = "fluidgrids-fe-sdk";
155
+ /** Upper bound for a slug-like dimension; anything longer is not a slug. */
156
+ const MAX_DIMENSION_LENGTH = 64;
157
+ const SLUG_PATTERN = /^[A-Za-z0-9][A-Za-z0-9_./:-]*$/;
158
+ /**
159
+ * Keep a dimension only when it is a short slug (`integration/slack`,
160
+ * `trigger_webhook`, `marketing`). Anything else — spaces, free text, a very
161
+ * long value — is dropped rather than risk sending user data.
162
+ */
163
+ function toDimension(value) {
164
+ if (typeof value !== "string") return void 0;
165
+ const trimmed = value.trim();
166
+ if (!trimmed || trimmed.length > MAX_DIMENSION_LENGTH) return void 0;
167
+ return SLUG_PATTERN.test(trimmed) ? trimmed : void 0;
168
+ }
169
+ /** Non-empty string id, or undefined. */
170
+ function idOrUndefined(value) {
171
+ return typeof value === "string" && value.length > 0 ? value : void 0;
172
+ }
173
+ /** A finite, non-negative integer count, or undefined. */
174
+ function countOrUndefined(value) {
175
+ return typeof value === "number" && Number.isFinite(value) && value >= 0 ? Math.round(value) : void 0;
176
+ }
177
+ function emit(bus, name, payload) {
178
+ if (!bus) return;
179
+ const clean = Object.fromEntries(Object.entries(payload).filter(([, value]) => value !== void 0));
180
+ try {
181
+ bus.emit(name, clean, { component: FLUIDGRIDS_ANALYTICS_COMPONENT });
182
+ } catch (error) {
183
+ console.warn(`[fluidgrids analytics] failed to emit ${name}`, error);
184
+ }
185
+ }
186
+ function asRecord(value) {
187
+ return typeof value === "object" && value !== null && !Array.isArray(value) ? value : null;
188
+ }
189
+ /**
190
+ * The executable node list of a workflow definition, wherever it sits: the
191
+ * flow store's `{ nodes }`, a saved `definitionJson` (`{ data: { nodes } }`) or
192
+ * a raw list.
193
+ */
194
+ function nodesOf(definition) {
195
+ if (Array.isArray(definition)) return definition;
196
+ const record = asRecord(definition);
197
+ if (!record) return [];
198
+ if (Array.isArray(record.nodes)) return record.nodes;
199
+ const data = asRecord(record.data);
200
+ if (data && Array.isArray(data.nodes)) return data.nodes;
201
+ return [];
202
+ }
203
+ function isTriggerNode(node) {
204
+ if ((typeof node.type === "string" ? node.type.toLowerCase() : "").includes("trigger")) return true;
205
+ const data = asRecord(node.data);
206
+ return data?.isTrigger === true || data?.category === "trigger";
207
+ }
208
+ /** Node-type slug of the workflow's trigger node, when it has one. */
209
+ function triggerTypeOf(definition) {
210
+ const trigger = nodesOf(definition).find(isTriggerNode);
211
+ return trigger ? toDimension(trigger.type) : void 0;
212
+ }
213
+ /** Number of executable nodes on the canvas. */
214
+ function nodeCountOf(definition) {
215
+ const nodes = nodesOf(definition);
216
+ return nodes.length > 0 ? nodes.length : void 0;
217
+ }
218
+ /** `fluidgrids.workflow.created` — a new workflow exists in the workspace. */
219
+ function emitWorkflowCreated(bus, fact) {
220
+ emit(bus, "fluidgrids.workflow.created", {
221
+ workspaceId: idOrUndefined(fact.workspaceId),
222
+ workflowId: idOrUndefined(fact.workflowId),
223
+ source: fact.source,
224
+ triggerType: triggerTypeOf(fact.definition),
225
+ nodeCount: nodeCountOf(fact.definition)
226
+ });
227
+ }
228
+ /** `fluidgrids.workflow.published` — a version was activated. */
229
+ function emitWorkflowPublished(bus, fact) {
230
+ emit(bus, "fluidgrids.workflow.published", {
231
+ workspaceId: idOrUndefined(fact.workspaceId),
232
+ workflowId: idOrUndefined(fact.workflowId),
233
+ triggerType: triggerTypeOf(fact.definition),
234
+ nodeCount: nodeCountOf(fact.definition)
235
+ });
236
+ }
237
+ /** `fluidgrids.workflow.run_started` — the backend accepted a run. */
238
+ function emitRunStarted(bus, fact) {
239
+ emit(bus, "fluidgrids.workflow.run_started", {
240
+ workspaceId: idOrUndefined(fact.workspaceId),
241
+ workflowId: idOrUndefined(fact.workflowId),
242
+ executionId: idOrUndefined(fact.executionId),
243
+ trigger: fact.trigger
244
+ });
245
+ }
246
+ /**
247
+ * `fluidgrids.workflow.run_failed` — a run this user started ended FAILED.
248
+ * `errorCode` is the run's machine error classification (`TIMEOUT`,
249
+ * `VALIDATION`, …), never its message.
250
+ */
251
+ function emitRunFailed(bus, fact) {
252
+ emit(bus, "fluidgrids.workflow.run_failed", {
253
+ workspaceId: idOrUndefined(fact.workspaceId),
254
+ workflowId: idOrUndefined(fact.workflowId),
255
+ executionId: idOrUndefined(fact.executionId),
256
+ trigger: fact.trigger,
257
+ errorCode: toDimension(fact.errorCode),
258
+ durationMs: countOrUndefined(fact.durationMs)
259
+ });
260
+ }
261
+ /** `fluidgrids.template.used` — a store template became a workflow. */
262
+ function emitTemplateUsed(bus, fact) {
263
+ emit(bus, "fluidgrids.template.used", {
264
+ workspaceId: idOrUndefined(fact.workspaceId),
265
+ templateId: idOrUndefined(fact.templateId),
266
+ category: toDimension(fact.category)
267
+ });
268
+ }
269
+ /** `fluidgrids.node.installed` — a store node was installed. */
270
+ function emitNodeInstalled(bus, fact) {
271
+ emit(bus, "fluidgrids.node.installed", {
272
+ workspaceId: idOrUndefined(fact.workspaceId),
273
+ nodeType: toDimension(fact.nodeType),
274
+ source: fact.source
275
+ });
276
+ }
277
+ /** `fluidgrids.quota.workflow_limit_hit` — a create was refused at the limit. */
278
+ function emitWorkflowLimitHit(bus, fact) {
279
+ emit(bus, "fluidgrids.quota.workflow_limit_hit", {
280
+ workspaceId: idOrUndefined(fact.workspaceId),
281
+ quotaKey: WORKFLOWS_QUOTA_NAME,
282
+ surface: fact.surface
283
+ });
284
+ }
285
+ /** `fluidgrids.quota.run_limit_hit` — a run was refused at the monthly limit. */
286
+ function emitRunLimitHit(bus, fact) {
287
+ emit(bus, "fluidgrids.quota.run_limit_hit", {
288
+ workspaceId: idOrUndefined(fact.workspaceId),
289
+ quotaKey: toDimension(fact.quotaKey) ?? "fluidgrids.runs.monthly",
290
+ surface: fact.surface
291
+ });
292
+ }
293
+ /** `fluidgrids.billing.upgrade_clicked` — a FluidGrids upgrade CTA was clicked. */
294
+ function emitUpgradeClicked(bus, fact) {
295
+ emit(bus, "fluidgrids.billing.upgrade_clicked", {
296
+ workspaceId: idOrUndefined(fact.workspaceId),
297
+ surface: fact.surface,
298
+ quotaKey: toDimension(fact.quotaKey)
299
+ });
300
+ }
301
+ /**
302
+ * Map a run's backend mode/trigger to the analytics trigger dimension. The
303
+ * builder's debug paths are always `TEST`; anything else a person started by
304
+ * hand is `manual`.
305
+ */
306
+ function runTriggerFromMode(mode) {
307
+ return typeof mode === "string" && mode.toUpperCase() === "TEST" ? "test" : "manual";
308
+ }
309
+
310
+ export { errorCodesOf as _, emitTemplateUsed as a, emitWorkflowLimitHit as c, runTriggerFromMode as d, BILLING_PLANS_PATH as f, collectExtensions as g, WORKFLOWS_QUOTA_NAME as h, emitRunStarted as i, emitWorkflowPublished as l, RUNS_QUOTA_NAME as m, emitRunFailed as n, emitUpgradeClicked as o, QUOTA_EXHAUSTED_CODE as p, emitRunLimitHit as r, emitWorkflowCreated as s, emitNodeInstalled as t, nodesOf as u, findQuotaRefusal as v, isQuotaExhaustedFailure as y };
package/dist/history.js CHANGED
@@ -1,4 +1,4 @@
1
1
  "use client";
2
- import { t as HistoryPage } from "./HistoryPage-DueEld8g.js";
2
+ import { t as HistoryPage } from "./HistoryPage-CA42pU85.js";
3
3
 
4
4
  export { HistoryPage };