@burdenoff/fluidgrids-fe-sdk 2026.1111.16 → 2026.1111.17

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 (112) hide show
  1. package/README.md +41 -0
  2. package/dist/AiStudioPage-kJHSsIcj.js +774 -0
  3. package/dist/ApprovalInboxPage-dbBDSJ-f.js +558 -0
  4. package/dist/DataSinkDashboardPage-1h2QsMzH.js +270 -0
  5. package/dist/DataTablesPage-BZy2z0LB.js +1690 -0
  6. package/dist/EntityTagPicker-BqRNsLCQ.js +135 -0
  7. package/dist/{ExecutionDetailPage-D-0_POAf.js → ExecutionDetailPage-BdcZmLT4.js} +799 -4420
  8. package/dist/ExecutionDetailPage-DvQ667OE.d.ts +10 -0
  9. package/dist/ExecutionsListPage-BCUJoAIE.js +2742 -0
  10. package/dist/{FailureTriagePanel-BHiduL7A.js → FailureTriagePanel-B9hDQymi.js} +4 -97
  11. package/dist/{FluidGridsProvider-DmvFADFa.js → FluidGridsProvider-dvZSNtSW.js} +10 -350
  12. package/dist/HistoryPage-BLoRpJ1R.d.ts +6 -0
  13. package/dist/{HistoryPage-BbUgxx1I.js → HistoryPage-U0tqupBN.js} +6 -4
  14. package/dist/HumanRequestCard-D-ooVPDn.js +439 -0
  15. package/dist/{InsightsPage-s6f5bU-8.js → InsightsPage-CALo16eB.js} +17 -328
  16. package/dist/ManagedAiPolicyAuthority-BxwJ3ptd.js +40 -0
  17. package/dist/{ManagedAiPolicyAuthority-CGux_DaV.d.ts → ManagedAiPolicyAuthority-DM3t3wNr.d.ts} +1 -5
  18. package/dist/ManagedAiPolicyAuthorityContext-CNkxIOZ1.js +10 -0
  19. package/dist/{MissingNodesInstallModal-B-9gHy2K.js → MissingNodesInstallModal-CMybsI8h.js} +3 -2
  20. package/dist/{NodesPage-ClvhUfbh.js → NodesPage-Bf5PhfBK.js} +7 -3
  21. package/dist/NodesPage-DEbnz9iU.d.ts +6 -0
  22. package/dist/{PublishCustomNodeAction-D2F7oN0S.js → PublishCustomNodeAction-5XXnSA3H.js} +3 -45
  23. package/dist/QuotaExhaustedDialog-7IFSaLyi.js +54 -0
  24. package/dist/RunnerStatusPill-Ctg4TJcP.js +187 -0
  25. package/dist/RunnersPage-CLCOCclc.js +467 -0
  26. package/dist/{ManagedAiPolicyAuthority-DsSaz-vg.js → SettingsPage-CgkRlCM5.js} +19 -50
  27. package/dist/SettingsPage-DMHQFj5-.d.ts +9 -0
  28. package/dist/TagFilterSelect-DCBOH6Ou.js +41 -0
  29. package/dist/TaskQueuesPage-9VgSnLdL.js +951 -0
  30. package/dist/TemplateCard-DsC0KNH1.js +1416 -0
  31. package/dist/{TemplateConfigurationModal-D_Mvgxqa.js → TemplateConfigurationModal-BhGWIzpm.js} +3 -2
  32. package/dist/{TemplateDetailPanel-DfFfUcOe.js → TemplateDetailPanel-D4cUVr-m.js} +3 -3
  33. package/dist/TemplatePreview-GthzCOSo.js +231 -0
  34. package/dist/TemplatesPage-BG3H-6v6.d.ts +10 -0
  35. package/dist/{TemplatesPage-Cku13bav.js → TemplatesPage-CsDNT54N.js} +11 -228
  36. package/dist/VariablesPage-67WR_lVE.js +949 -0
  37. package/dist/{VersionDiffDialog-Dq2xlPFI.js → VersionDiffDialog-DSN0mU0f.js} +2 -1
  38. package/dist/WorkflowBuilder-DEi_9YOb.js +555 -0
  39. package/dist/{WorkflowSearchRedirect-CaoOOpEl.js → WorkflowBuilder-iPqXgbYr.js} +19 -585
  40. package/dist/{WorkflowProposalCard-8Vr56kQa.js → WorkflowProposalCard-qrEeNyYG.js} +4 -405
  41. package/dist/WorkflowSearchRedirect-DwDNZ_q5.js +36 -0
  42. package/dist/{WorkflowShareDialog-6RRDe-_v.js → WorkflowShareDialog-B_gn968c.js} +6 -52
  43. package/dist/{WorkflowsList-B2j1Pehb.js → WorkflowsList-CA20dVIl.js} +11 -6
  44. package/dist/WorkflowsList-CcNDQge5.d.ts +6 -0
  45. package/dist/agent-form-Bfvm32j1.js +83 -0
  46. package/dist/{agentTools-DJ5o2ekg.js → agentTools-CkRJB7r5.js} +3 -2
  47. package/dist/{ai-usage-D5p7ZeRR.js → ai-usage-glCwHyQz.js} +1 -1
  48. package/dist/api-BrCHB5oA.js +224 -0
  49. package/dist/api-C8e0iV-Q.js +55 -0
  50. package/dist/button-DG7y_FVJ.js +48 -0
  51. package/dist/{canvasNoteTools-D3zUdEeg.js → canvasNoteTools-CQIc7Oxg.js} +2 -2
  52. package/dist/client-C9XSzSXr.js +1147 -0
  53. package/dist/{codec-client-DstqyzTN.js → codec-client-CJ95Rmqo.js} +1 -1
  54. package/dist/constants-B2lhWNoN.js +202 -0
  55. package/dist/constants-XdvUxeWK.d.ts +162 -0
  56. package/dist/dialog-Cjb4lB4D.js +105 -0
  57. package/dist/executions.d.ts +1 -1
  58. package/dist/executions.js +2 -1
  59. package/dist/feature-flags-DM5myWaD.js +296 -0
  60. package/dist/flags.d.ts +3 -0
  61. package/dist/flags.js +4 -0
  62. package/dist/{flow-builder-DEzT8TQu.js → flow-builder-y2Y1iG4Y.js} +70 -1731
  63. package/dist/{node-endpoint-configs-DHFGA5MQ.js → graphql-operation-types-kX-MMjgW.js} +1 -1194
  64. package/dist/{graphql-types-XcDLtFwU.js → graphql-types-CDKVWH2R.js} +2 -202
  65. package/dist/history.d.ts +1 -1
  66. package/dist/history.js +1 -1
  67. package/dist/index-72XFgvbn.d.ts +132 -0
  68. package/dist/index-BcdtKBM-.d.ts +56 -0
  69. package/dist/{index-B3BWqafN.d.ts → index-DjiFgEQl.d.ts} +5 -131
  70. package/dist/{index-DRf25-D3.d.ts → index-W2o__Nm6.d.ts} +32 -214
  71. package/dist/index.d.ts +13 -9
  72. package/dist/index.js +50 -5300
  73. package/dist/{node-detail-view-LNqeIqN-.js → node-detail-view-B91kXzIy.js} +11 -8
  74. package/dist/node-endpoint-configs-B5bjNMDW.js +37 -0
  75. package/dist/node-registry-refresh-Dy0uRg9f.js +84 -0
  76. package/dist/nodes.d.ts +1 -1
  77. package/dist/nodes.js +1 -1
  78. package/dist/observability.d.ts +1 -1
  79. package/dist/observability.js +2 -1
  80. package/dist/{quick-config-panel-D3ogsaFL.js → quick-config-panel-DggPl1vY.js} +2 -2
  81. package/dist/rolldown-runtime-hDbaFkMy.js +18 -0
  82. package/dist/run-display-BycKYSU0.js +46 -0
  83. package/dist/run-list-links-ByYC0OlV.js +98 -0
  84. package/dist/settings.d.ts +2 -1
  85. package/dist/settings.js +2 -1
  86. package/dist/shared-CMfn30xT.js +196 -0
  87. package/dist/templates.d.ts +1 -1
  88. package/dist/templates.js +2 -1
  89. package/dist/theme-provider-B3mIuz2d.js +11 -0
  90. package/dist/{useAgentDefinitions-NFtLytDR.js → useAgentDefinitions-Dpz0HDTq.js} +2 -1
  91. package/dist/useDurableParity-CzUQMFJ3.js +415 -0
  92. package/dist/useEntityTags-DhnsZcTl.js +236 -0
  93. package/dist/{useExecutions-DAzeWHS6.js → useExecutions-9aLuOt1c.js} +4 -3
  94. package/dist/{useObservability-COCZ0hUS.js → useObservability-CfEw3ZFD.js} +2 -2
  95. package/dist/{useRunHistory-CsYUbouO.js → useRunHistory-B1xJDwl1.js} +4 -3
  96. package/dist/{useWorkflows-w4Dx2fF2.js → useWorkflows-BlVVu8NM.js} +3 -2
  97. package/dist/utils-uaL5UVxb.js +65 -0
  98. package/dist/workflow-builder.d.ts +1 -1
  99. package/dist/workflow-builder.js +4 -2
  100. package/dist/workflow-host.d.ts +6 -0
  101. package/dist/workflow-host.js +9 -0
  102. package/dist/workflow-pages.d.ts +55 -0
  103. package/dist/workflow-pages.js +113 -0
  104. package/dist/workflows-list.d.ts +1 -1
  105. package/dist/workflows-list.js +1 -1
  106. package/package.json +13 -1
  107. package/dist/ExecutionDetailPage-MvsnOnE1.d.ts +0 -4
  108. package/dist/HistoryPage-BqUizaFv.d.ts +0 -3
  109. package/dist/NodesPage-C97-9K2Y.d.ts +0 -3
  110. package/dist/TemplatesPage-D0qnXzHh.d.ts +0 -4
  111. package/dist/WorkflowsList-0d5GSKdh.d.ts +0 -3
  112. package/dist/agent-form-BvMWhQ42.js +0 -496
@@ -0,0 +1,949 @@
1
+ "use client";
2
+ import { t as __exportAll } from "./rolldown-runtime-hDbaFkMy.js";
3
+ import { r as useTr } from "./TranslationBridge-Da-TPgQm.js";
4
+ import { i as SdkPermissionButton, t as FLUIDGRIDS_PERMISSIONS } from "./constants-B2lhWNoN.js";
5
+ import { _ as throwIfResultError, n as getFluidGridsClient } from "./client-C9XSzSXr.js";
6
+ import { useCallback, useEffect, useState } from "react";
7
+ import { useNavigate } from "react-router";
8
+ import { Icon } from "@iconify/react";
9
+ import { jsx, jsxs } from "react/jsx-runtime";
10
+ import { toast } from "sonner";
11
+ import { gql } from "@apollo/client";
12
+ import { Badge, Card, CardHeader, Dialog, DialogContent, DialogFooter, DialogHeader, DialogTitle, Input, Label, Select, SelectContent, SelectItem, SelectTrigger, SelectValue, Switch, Table, TableBody, TableCell, TableHead, TableHeader, TableRow, Tabs, TabsContent, TabsList, TabsTrigger } from "@burdenoff/fe-libs/ui";
13
+ import { Button as Button$1 } from "@burdenoff/fe-libs/button";
14
+
15
+ // src/modules/variables/hooks/useVariables.ts
16
+ /**
17
+ * Custom hooks for workflow Variables + external secrets provider config
18
+ * (BOFF-7517). Queries/mutates wspace-workflow-svc via the federated
19
+ * GraphQL gateway — mirrors the connections module's hook pattern
20
+ * (`modules/connections/hooks/useConnections.ts`).
21
+ */
22
+ const VARIABLE_FIELDS = gql`
23
+ fragment WorkflowVariableFields on WorkflowVariable {
24
+ id
25
+ scope
26
+ workspaceId
27
+ projectId
28
+ key
29
+ description
30
+ isSecret
31
+ externalProvider
32
+ externalRef
33
+ value
34
+ createdAt
35
+ updatedAt
36
+ createdBy
37
+ updatedBy
38
+ }
39
+ `;
40
+ const GET_WORKFLOW_VARIABLES = gql`
41
+ ${VARIABLE_FIELDS}
42
+ query GetWorkflowVariables($scope: VariableScope, $projectId: ID) {
43
+ workflowVariables(scope: $scope, projectId: $projectId) {
44
+ variables {
45
+ ...WorkflowVariableFields
46
+ }
47
+ total
48
+ }
49
+ }
50
+ `;
51
+ const CREATE_WORKFLOW_VARIABLE = gql`
52
+ ${VARIABLE_FIELDS}
53
+ mutation CreateWorkflowVariable($input: CreateWorkflowVariableInput!) {
54
+ createWorkflowVariable(input: $input) {
55
+ success
56
+ message
57
+ variable {
58
+ ...WorkflowVariableFields
59
+ }
60
+ }
61
+ }
62
+ `;
63
+ const UPDATE_WORKFLOW_VARIABLE = gql`
64
+ ${VARIABLE_FIELDS}
65
+ mutation UpdateWorkflowVariable(
66
+ $id: ID!
67
+ $input: UpdateWorkflowVariableInput!
68
+ ) {
69
+ updateWorkflowVariable(id: $id, input: $input) {
70
+ success
71
+ message
72
+ variable {
73
+ ...WorkflowVariableFields
74
+ }
75
+ }
76
+ }
77
+ `;
78
+ const DELETE_WORKFLOW_VARIABLE = gql`
79
+ mutation DeleteWorkflowVariable($id: ID!) {
80
+ deleteWorkflowVariable(id: $id) {
81
+ success
82
+ message
83
+ }
84
+ }
85
+ `;
86
+ const REVEAL_WORKFLOW_VARIABLE_VALUE = gql`
87
+ mutation RevealWorkflowVariableValue($id: ID!) {
88
+ revealWorkflowVariableValue(id: $id) {
89
+ success
90
+ message
91
+ value
92
+ }
93
+ }
94
+ `;
95
+ const GET_SECRETS_PROVIDER_CONFIGS = gql`
96
+ query GetSecretsProviderConfigs {
97
+ secretsProviderConfigs {
98
+ id
99
+ workspaceId
100
+ provider
101
+ awsSecretsManagerPrefix
102
+ awsRegion
103
+ vaultAddress
104
+ vaultMountPath
105
+ azureKeyVaultUri
106
+ gcpProjectId
107
+ isEnabled
108
+ lastTestedAt
109
+ lastTestStatus
110
+ lastTestMessage
111
+ createdAt
112
+ updatedAt
113
+ }
114
+ }
115
+ `;
116
+ const SAVE_SECRETS_PROVIDER_CONFIG = gql`
117
+ mutation SaveSecretsProviderConfig($input: SaveSecretsProviderConfigInput!) {
118
+ saveSecretsProviderConfig(input: $input) {
119
+ success
120
+ message
121
+ config {
122
+ id
123
+ provider
124
+ awsSecretsManagerPrefix
125
+ awsRegion
126
+ isEnabled
127
+ lastTestedAt
128
+ lastTestStatus
129
+ lastTestMessage
130
+ }
131
+ }
132
+ }
133
+ `;
134
+ const TEST_SECRETS_PROVIDER_CONNECTION = gql`
135
+ mutation TestSecretsProviderConnection($provider: SecretProviderType!) {
136
+ testSecretsProviderConnection(provider: $provider) {
137
+ success
138
+ message
139
+ }
140
+ }
141
+ `;
142
+ function useVariables(filter) {
143
+ const [variables, setVariables] = useState([]);
144
+ const [total, setTotal] = useState(0);
145
+ const [loading, setLoading] = useState(true);
146
+ const [error, setError] = useState(null);
147
+ const scope = filter?.scope;
148
+ const projectId = filter?.projectId;
149
+ const fetchData = useCallback(async () => {
150
+ setLoading(true);
151
+ setError(null);
152
+ try {
153
+ const result = await getFluidGridsClient().query({
154
+ query: GET_WORKFLOW_VARIABLES,
155
+ variables: {
156
+ scope,
157
+ projectId
158
+ },
159
+ fetchPolicy: "network-only"
160
+ });
161
+ setVariables(result.data?.workflowVariables?.variables ?? []);
162
+ setTotal(result.data?.workflowVariables?.total ?? 0);
163
+ } catch (err) {
164
+ setError(err);
165
+ } finally {
166
+ setLoading(false);
167
+ }
168
+ }, [scope, projectId]);
169
+ useEffect(() => {
170
+ fetchData();
171
+ }, [fetchData]);
172
+ return {
173
+ variables,
174
+ total,
175
+ loading,
176
+ error,
177
+ refetch: fetchData
178
+ };
179
+ }
180
+ function useCreateVariable() {
181
+ const [loading, setLoading] = useState(false);
182
+ const [error, setError] = useState(null);
183
+ return {
184
+ createVariable: useCallback(async (input) => {
185
+ setLoading(true);
186
+ setError(null);
187
+ try {
188
+ const client = getFluidGridsClient();
189
+ const response = throwIfResultError(await client.mutate({
190
+ mutation: CREATE_WORKFLOW_VARIABLE,
191
+ variables: { input }
192
+ })).data?.createWorkflowVariable;
193
+ if (!response?.success) throw new Error(response?.message ?? "Failed to create variable");
194
+ return response.variable;
195
+ } catch (err) {
196
+ setError(err);
197
+ throw err;
198
+ } finally {
199
+ setLoading(false);
200
+ }
201
+ }, []),
202
+ loading,
203
+ error
204
+ };
205
+ }
206
+ function useUpdateVariable() {
207
+ const [loading, setLoading] = useState(false);
208
+ const [error, setError] = useState(null);
209
+ return {
210
+ updateVariable: useCallback(async (id, input) => {
211
+ setLoading(true);
212
+ setError(null);
213
+ try {
214
+ const client = getFluidGridsClient();
215
+ const response = throwIfResultError(await client.mutate({
216
+ mutation: UPDATE_WORKFLOW_VARIABLE,
217
+ variables: {
218
+ id,
219
+ input
220
+ }
221
+ })).data?.updateWorkflowVariable;
222
+ if (!response?.success) throw new Error(response?.message ?? "Failed to update variable");
223
+ return response.variable;
224
+ } catch (err) {
225
+ setError(err);
226
+ throw err;
227
+ } finally {
228
+ setLoading(false);
229
+ }
230
+ }, []),
231
+ loading,
232
+ error
233
+ };
234
+ }
235
+ function useDeleteVariable() {
236
+ const [loading, setLoading] = useState(false);
237
+ const [error, setError] = useState(null);
238
+ return {
239
+ deleteVariable: useCallback(async (id) => {
240
+ setLoading(true);
241
+ setError(null);
242
+ try {
243
+ const client = getFluidGridsClient();
244
+ const response = throwIfResultError(await client.mutate({
245
+ mutation: DELETE_WORKFLOW_VARIABLE,
246
+ variables: { id }
247
+ })).data?.deleteWorkflowVariable;
248
+ if (!response?.success) throw new Error(response?.message ?? "Failed to delete variable");
249
+ return true;
250
+ } catch (err) {
251
+ setError(err);
252
+ throw err;
253
+ } finally {
254
+ setLoading(false);
255
+ }
256
+ }, []),
257
+ loading,
258
+ error
259
+ };
260
+ }
261
+ function useRevealVariableValue() {
262
+ const [loading, setLoading] = useState(false);
263
+ const [error, setError] = useState(null);
264
+ return {
265
+ revealValue: useCallback(async (id) => {
266
+ setLoading(true);
267
+ setError(null);
268
+ try {
269
+ const client = getFluidGridsClient();
270
+ const response = throwIfResultError(await client.mutate({
271
+ mutation: REVEAL_WORKFLOW_VARIABLE_VALUE,
272
+ variables: { id }
273
+ })).data?.revealWorkflowVariableValue;
274
+ if (!response?.success) throw new Error(response?.message ?? "Failed to reveal value");
275
+ return response.value ?? "";
276
+ } catch (err) {
277
+ setError(err);
278
+ throw err;
279
+ } finally {
280
+ setLoading(false);
281
+ }
282
+ }, []),
283
+ loading,
284
+ error
285
+ };
286
+ }
287
+ function useSecretsProviderConfigs() {
288
+ const [configs, setConfigs] = useState([]);
289
+ const [loading, setLoading] = useState(true);
290
+ const [error, setError] = useState(null);
291
+ const fetchData = useCallback(async () => {
292
+ setLoading(true);
293
+ setError(null);
294
+ try {
295
+ const result = await getFluidGridsClient().query({
296
+ query: GET_SECRETS_PROVIDER_CONFIGS,
297
+ fetchPolicy: "network-only"
298
+ });
299
+ setConfigs(result.data?.secretsProviderConfigs ?? []);
300
+ } catch (err) {
301
+ setError(err);
302
+ } finally {
303
+ setLoading(false);
304
+ }
305
+ }, []);
306
+ useEffect(() => {
307
+ fetchData();
308
+ }, [fetchData]);
309
+ return {
310
+ configs,
311
+ loading,
312
+ error,
313
+ refetch: fetchData
314
+ };
315
+ }
316
+ function useSaveSecretsProviderConfig() {
317
+ const [loading, setLoading] = useState(false);
318
+ const [error, setError] = useState(null);
319
+ return {
320
+ saveConfig: useCallback(async (input) => {
321
+ setLoading(true);
322
+ setError(null);
323
+ try {
324
+ const client = getFluidGridsClient();
325
+ const response = throwIfResultError(await client.mutate({
326
+ mutation: SAVE_SECRETS_PROVIDER_CONFIG,
327
+ variables: { input }
328
+ })).data?.saveSecretsProviderConfig;
329
+ if (!response?.success) throw new Error(response?.message ?? "Failed to save provider configuration");
330
+ return response.config;
331
+ } catch (err) {
332
+ setError(err);
333
+ throw err;
334
+ } finally {
335
+ setLoading(false);
336
+ }
337
+ }, []),
338
+ loading,
339
+ error
340
+ };
341
+ }
342
+ function useTestSecretsProviderConnection() {
343
+ const [loading, setLoading] = useState(false);
344
+ const [error, setError] = useState(null);
345
+ return {
346
+ testConnection: useCallback(async (provider) => {
347
+ setLoading(true);
348
+ setError(null);
349
+ try {
350
+ const client = getFluidGridsClient();
351
+ return throwIfResultError(await client.mutate({
352
+ mutation: TEST_SECRETS_PROVIDER_CONNECTION,
353
+ variables: { provider }
354
+ })).data?.testSecretsProviderConnection ?? {
355
+ success: false,
356
+ message: "Unknown error"
357
+ };
358
+ } catch (err) {
359
+ setError(err);
360
+ throw err;
361
+ } finally {
362
+ setLoading(false);
363
+ }
364
+ }, []),
365
+ loading,
366
+ error
367
+ };
368
+ }
369
+
370
+ // src/modules/variables/pages/VariablesPage.tsx
371
+ /**
372
+ * Variables Page (BOFF-7517)
373
+ *
374
+ * Workspace/project-scoped `$vars` key-value store management: list/create/
375
+ * edit/delete variables, mask secret values (dots + explicit "Reveal"
376
+ * action), and configure/test the external secrets provider (AWS Secrets
377
+ * Manager first).
378
+ */
379
+ var VariablesPage_exports = /* @__PURE__ */ __exportAll({ VariablesPage: () => VariablesPage });
380
+ function VariableValueCell({ variable }) {
381
+ const tr = useTr();
382
+ const { revealValue, loading } = useRevealVariableValue();
383
+ const [revealed, setRevealed] = useState(null);
384
+ const isMasked = variable.isSecret || variable.externalProvider !== "NONE";
385
+ const handleReveal = useCallback(async () => {
386
+ try {
387
+ const value = await revealValue(variable.id);
388
+ setRevealed(value);
389
+ setTimeout(() => setRevealed(null), 15e3);
390
+ } catch (err) {
391
+ toast.error(err instanceof Error ? err.message : tr("fluidgrids.variables.revealFailed", "Failed to reveal value"));
392
+ }
393
+ }, [
394
+ revealValue,
395
+ variable.id,
396
+ tr
397
+ ]);
398
+ if (variable.externalProvider !== "NONE" && revealed === null) return /* @__PURE__ */ jsxs("div", {
399
+ className: "flex items-center gap-2",
400
+ children: [
401
+ /* @__PURE__ */ jsx(Badge, {
402
+ variant: "outline",
403
+ className: "font-mono text-xs",
404
+ children: variable.externalProvider
405
+ }),
406
+ variable.externalRef && /* @__PURE__ */ jsx("span", {
407
+ className: "text-xs text-text-secondary truncate max-w-[160px]",
408
+ title: variable.externalRef,
409
+ children: variable.externalRef
410
+ }),
411
+ /* @__PURE__ */ jsx("button", {
412
+ onClick: handleReveal,
413
+ disabled: loading,
414
+ className: "text-xs text-text-secondary hover:text-text-primary underline",
415
+ children: tr("fluidgrids.variables.reveal", "Reveal")
416
+ })
417
+ ]
418
+ });
419
+ if (!isMasked) return /* @__PURE__ */ jsx("code", {
420
+ className: "text-sm text-text-primary",
421
+ children: variable.value ?? ""
422
+ });
423
+ if (revealed !== null) return /* @__PURE__ */ jsxs("div", {
424
+ className: "flex items-center gap-2",
425
+ children: [/* @__PURE__ */ jsx("code", {
426
+ className: "text-sm text-text-primary break-all",
427
+ children: revealed
428
+ }), /* @__PURE__ */ jsx("button", {
429
+ onClick: () => setRevealed(null),
430
+ className: "text-xs text-text-secondary hover:text-text-primary underline shrink-0",
431
+ children: tr("fluidgrids.variables.hide", "Hide")
432
+ })]
433
+ });
434
+ return /* @__PURE__ */ jsxs("div", {
435
+ className: "flex items-center gap-2",
436
+ children: [/* @__PURE__ */ jsx("span", {
437
+ className: "tracking-widest text-text-secondary select-none",
438
+ children: "••••••••"
439
+ }), /* @__PURE__ */ jsx("button", {
440
+ onClick: handleReveal,
441
+ disabled: loading,
442
+ className: "text-xs text-text-secondary hover:text-text-primary underline",
443
+ children: loading ? tr("fluidgrids.variables.revealing", "Revealing…") : tr("fluidgrids.variables.reveal", "Reveal")
444
+ })]
445
+ });
446
+ }
447
+ function VariableFormDialog({ open, onOpenChange, variable, onSaved }) {
448
+ const tr = useTr();
449
+ const { createVariable, loading: creating } = useCreateVariable();
450
+ const { updateVariable, loading: updating } = useUpdateVariable();
451
+ const isEdit = !!variable;
452
+ const [key, setKey] = useState(variable?.key ?? "");
453
+ const [description, setDescription] = useState(variable?.description ?? "");
454
+ const [isSecret, setIsSecret] = useState(variable?.isSecret ?? false);
455
+ const [value, setValue] = useState("");
456
+ const [scope, setScope] = useState(variable?.scope ?? "WORKSPACE");
457
+ const resetForm = useCallback(() => {
458
+ setKey(variable?.key ?? "");
459
+ setDescription(variable?.description ?? "");
460
+ setIsSecret(variable?.isSecret ?? false);
461
+ setValue("");
462
+ setScope(variable?.scope ?? "WORKSPACE");
463
+ }, [variable]);
464
+ const handleSubmit = useCallback(async () => {
465
+ try {
466
+ if (isEdit && variable) {
467
+ await updateVariable(variable.id, {
468
+ description: description || void 0,
469
+ isSecret,
470
+ ...value ? { value } : {}
471
+ });
472
+ toast.success(tr("fluidgrids.variables.updated", "Variable updated"));
473
+ } else {
474
+ if (!key.trim()) {
475
+ toast.error(tr("fluidgrids.variables.keyRequired", "Key is required"));
476
+ return;
477
+ }
478
+ await createVariable({
479
+ key: key.trim(),
480
+ description: description || void 0,
481
+ isSecret,
482
+ value,
483
+ scope
484
+ });
485
+ toast.success(tr("fluidgrids.variables.created", "Variable created"));
486
+ }
487
+ onSaved();
488
+ onOpenChange(false);
489
+ } catch (err) {
490
+ toast.error(err instanceof Error ? err.message : tr("fluidgrids.variables.saveFailed", "Failed to save variable"));
491
+ }
492
+ }, [
493
+ isEdit,
494
+ variable,
495
+ key,
496
+ description,
497
+ isSecret,
498
+ value,
499
+ scope,
500
+ createVariable,
501
+ updateVariable,
502
+ onSaved,
503
+ onOpenChange,
504
+ tr
505
+ ]);
506
+ return /* @__PURE__ */ jsx(Dialog, {
507
+ open,
508
+ onOpenChange: (next) => {
509
+ if (next) resetForm();
510
+ onOpenChange(next);
511
+ },
512
+ children: /* @__PURE__ */ jsxs(DialogContent, {
513
+ className: "max-w-md",
514
+ children: [
515
+ /* @__PURE__ */ jsx(DialogHeader, { children: /* @__PURE__ */ jsx(DialogTitle, { children: isEdit ? tr("fluidgrids.variables.editTitle", "Edit variable") : tr("fluidgrids.variables.createTitle", "New variable") }) }),
516
+ /* @__PURE__ */ jsxs("div", {
517
+ className: "space-y-4 py-2",
518
+ children: [
519
+ /* @__PURE__ */ jsxs("div", {
520
+ className: "space-y-1.5",
521
+ children: [
522
+ /* @__PURE__ */ jsx(Label, {
523
+ htmlFor: "variable-key",
524
+ children: tr("fluidgrids.variables.keyLabel", "Key")
525
+ }),
526
+ /* @__PURE__ */ jsx(Input, {
527
+ id: "variable-key",
528
+ value: key,
529
+ onChange: (e) => setKey(e.target.value),
530
+ disabled: isEdit,
531
+ placeholder: "API_URL"
532
+ }),
533
+ /* @__PURE__ */ jsx("p", {
534
+ className: "text-xs text-text-secondary",
535
+ children: tr("fluidgrids.variables.keyHint", "Use it in expressions as {{ $vars.KEY }} or ${vars.KEY}")
536
+ })
537
+ ]
538
+ }),
539
+ !isEdit && /* @__PURE__ */ jsxs("div", {
540
+ className: "space-y-1.5",
541
+ children: [/* @__PURE__ */ jsx(Label, {
542
+ htmlFor: "variable-scope",
543
+ children: tr("fluidgrids.variables.scopeLabel", "Scope")
544
+ }), /* @__PURE__ */ jsxs(Select, {
545
+ value: scope,
546
+ onValueChange: (v) => setScope(v),
547
+ children: [/* @__PURE__ */ jsx(SelectTrigger, {
548
+ id: "variable-scope",
549
+ children: /* @__PURE__ */ jsx(SelectValue, {})
550
+ }), /* @__PURE__ */ jsxs(SelectContent, { children: [/* @__PURE__ */ jsx(SelectItem, {
551
+ value: "WORKSPACE",
552
+ children: tr("fluidgrids.variables.scopeWorkspace", "Workspace")
553
+ }), /* @__PURE__ */ jsx(SelectItem, {
554
+ value: "PROJECT",
555
+ children: tr("fluidgrids.variables.scopeProject", "Project")
556
+ })] })]
557
+ })]
558
+ }),
559
+ /* @__PURE__ */ jsxs("div", {
560
+ className: "space-y-1.5",
561
+ children: [/* @__PURE__ */ jsx(Label, {
562
+ htmlFor: "variable-description",
563
+ children: tr("fluidgrids.variables.descriptionLabel", "Description")
564
+ }), /* @__PURE__ */ jsx(Input, {
565
+ id: "variable-description",
566
+ value: description,
567
+ onChange: (e) => setDescription(e.target.value),
568
+ placeholder: tr("fluidgrids.variables.descriptionPlaceholder", "Optional")
569
+ })]
570
+ }),
571
+ /* @__PURE__ */ jsxs("div", {
572
+ className: "flex items-center justify-between py-1",
573
+ children: [/* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx(Label, {
574
+ htmlFor: "variable-secret",
575
+ children: tr("fluidgrids.variables.secretLabel", "Secret value")
576
+ }), /* @__PURE__ */ jsx("p", {
577
+ className: "text-xs text-text-secondary",
578
+ children: tr("fluidgrids.variables.secretHint", "Masked in the UI and never printed to run logs")
579
+ })] }), /* @__PURE__ */ jsx(Switch, {
580
+ id: "variable-secret",
581
+ checked: isSecret,
582
+ onCheckedChange: setIsSecret
583
+ })]
584
+ }),
585
+ /* @__PURE__ */ jsxs("div", {
586
+ className: "space-y-1.5",
587
+ children: [/* @__PURE__ */ jsx(Label, {
588
+ htmlFor: "variable-value",
589
+ children: tr("fluidgrids.variables.valueLabel", "Value")
590
+ }), /* @__PURE__ */ jsx(Input, {
591
+ id: "variable-value",
592
+ type: isSecret ? "password" : "text",
593
+ value,
594
+ onChange: (e) => setValue(e.target.value),
595
+ placeholder: isEdit ? tr("fluidgrids.variables.valueLeaveBlank", "Leave blank to keep the current value") : ""
596
+ })]
597
+ })
598
+ ]
599
+ }),
600
+ /* @__PURE__ */ jsxs(DialogFooter, { children: [/* @__PURE__ */ jsx(Button$1, {
601
+ variant: "outline",
602
+ onClick: () => onOpenChange(false),
603
+ children: tr("fluidgrids.variables.cancel", "Cancel")
604
+ }), /* @__PURE__ */ jsx(Button$1, {
605
+ "data-agent": "confirm",
606
+ onClick: handleSubmit,
607
+ disabled: creating || updating,
608
+ children: creating || updating ? tr("fluidgrids.variables.saving", "Saving…") : tr("fluidgrids.variables.save", "Save")
609
+ })] })
610
+ ]
611
+ })
612
+ });
613
+ }
614
+ function VariablesTab() {
615
+ const tr = useTr();
616
+ const { variables, loading, refetch } = useVariables();
617
+ const { deleteVariable } = useDeleteVariable();
618
+ const [dialogOpen, setDialogOpen] = useState(false);
619
+ const [editing, setEditing] = useState(null);
620
+ const handleCreate = useCallback(() => {
621
+ setEditing(null);
622
+ setDialogOpen(true);
623
+ }, []);
624
+ const handleEdit = useCallback((variable) => {
625
+ setEditing(variable);
626
+ setDialogOpen(true);
627
+ }, []);
628
+ const handleDelete = useCallback(async (variable) => {
629
+ if (!window.confirm(tr("fluidgrids.variables.confirmDelete", `Delete variable "${variable.key}"?`))) return;
630
+ try {
631
+ await deleteVariable(variable.id);
632
+ toast.success(tr("fluidgrids.variables.deleted", "Variable deleted"));
633
+ refetch();
634
+ } catch (err) {
635
+ toast.error(err instanceof Error ? err.message : tr("fluidgrids.variables.deleteFailed", "Failed to delete variable"));
636
+ }
637
+ }, [
638
+ deleteVariable,
639
+ refetch,
640
+ tr
641
+ ]);
642
+ return /* @__PURE__ */ jsxs("div", { children: [
643
+ /* @__PURE__ */ jsxs("div", {
644
+ className: "flex items-center justify-between mb-4",
645
+ children: [/* @__PURE__ */ jsx("p", {
646
+ className: "text-sm text-text-secondary",
647
+ children: tr("fluidgrids.variables.tabDescription", "Reference these in any node parameter as {{ $vars.KEY }} (new expressions) or ${vars.KEY} (legacy).")
648
+ }), /* @__PURE__ */ jsx(SdkPermissionButton, {
649
+ permission: FLUIDGRIDS_PERMISSIONS.VARIABLE_CREATE,
650
+ deniedTooltip: tr("fluidgrids.variables.createDeniedTooltip", "You don't have permission to create variables"),
651
+ children: /* @__PURE__ */ jsxs(Button$1, {
652
+ onClick: handleCreate,
653
+ size: "sm",
654
+ "data-tour": "fluidgrids-variables-create",
655
+ children: [/* @__PURE__ */ jsx(Icon, {
656
+ icon: "mdi:plus",
657
+ className: "mr-1.5",
658
+ width: 16
659
+ }), tr("fluidgrids.variables.newVariable", "New Variable")]
660
+ })
661
+ })]
662
+ }),
663
+ /* @__PURE__ */ jsx(Card, {
664
+ className: "border border-border-secondary bg-background-secondary",
665
+ "data-tour": "fluidgrids-variables-table",
666
+ children: /* @__PURE__ */ jsxs(Table, { children: [/* @__PURE__ */ jsx(TableHeader, { children: /* @__PURE__ */ jsxs(TableRow, { children: [
667
+ /* @__PURE__ */ jsx(TableHead, { children: tr("fluidgrids.variables.colKey", "Key") }),
668
+ /* @__PURE__ */ jsx(TableHead, { children: tr("fluidgrids.variables.colScope", "Scope") }),
669
+ /* @__PURE__ */ jsx(TableHead, { children: tr("fluidgrids.variables.colValue", "Value") }),
670
+ /* @__PURE__ */ jsx(TableHead, {
671
+ className: "text-right",
672
+ children: tr("fluidgrids.variables.colActions", "Actions")
673
+ })
674
+ ] }) }), /* @__PURE__ */ jsxs(TableBody, { children: [
675
+ loading && /* @__PURE__ */ jsx(TableRow, { children: /* @__PURE__ */ jsx(TableCell, {
676
+ colSpan: 4,
677
+ className: "text-center text-text-secondary py-8",
678
+ children: tr("fluidgrids.variables.loading", "Loading…")
679
+ }) }),
680
+ !loading && variables.length === 0 && /* @__PURE__ */ jsx(TableRow, { children: /* @__PURE__ */ jsx(TableCell, {
681
+ colSpan: 4,
682
+ className: "text-center text-text-secondary py-8",
683
+ children: tr("fluidgrids.variables.empty", "No variables yet")
684
+ }) }),
685
+ variables.map((variable) => /* @__PURE__ */ jsxs(TableRow, { children: [
686
+ /* @__PURE__ */ jsxs(TableCell, { children: [/* @__PURE__ */ jsxs("div", {
687
+ className: "flex items-center gap-2",
688
+ children: [/* @__PURE__ */ jsx("code", {
689
+ className: "text-sm font-medium text-text-primary",
690
+ children: variable.key
691
+ }), variable.isSecret && /* @__PURE__ */ jsx(Badge, {
692
+ variant: "outline",
693
+ className: "text-[10px]",
694
+ children: tr("fluidgrids.variables.secretBadge", "SECRET")
695
+ })]
696
+ }), variable.description && /* @__PURE__ */ jsx("p", {
697
+ className: "text-xs text-text-secondary mt-0.5",
698
+ children: variable.description
699
+ })] }),
700
+ /* @__PURE__ */ jsx(TableCell, {
701
+ className: "text-text-secondary text-sm",
702
+ children: variable.scope
703
+ }),
704
+ /* @__PURE__ */ jsx(TableCell, { children: /* @__PURE__ */ jsx(VariableValueCell, { variable }) }),
705
+ /* @__PURE__ */ jsx(TableCell, {
706
+ className: "text-right",
707
+ children: /* @__PURE__ */ jsxs("div", {
708
+ className: "flex items-center justify-end gap-1",
709
+ children: [/* @__PURE__ */ jsx(SdkPermissionButton, {
710
+ permission: FLUIDGRIDS_PERMISSIONS.VARIABLE_UPDATE,
711
+ deniedTooltip: tr("fluidgrids.variables.editDeniedTooltip", "You don't have permission to edit variables"),
712
+ children: /* @__PURE__ */ jsx("button", {
713
+ onClick: () => handleEdit(variable),
714
+ className: "p-1.5 rounded hover:bg-background-tertiary text-text-secondary hover:text-text-primary",
715
+ title: tr("fluidgrids.variables.edit", "Edit"),
716
+ children: /* @__PURE__ */ jsx(Icon, {
717
+ icon: "mdi:pencil-outline",
718
+ width: 16
719
+ })
720
+ })
721
+ }), /* @__PURE__ */ jsx(SdkPermissionButton, {
722
+ permission: FLUIDGRIDS_PERMISSIONS.VARIABLE_DELETE,
723
+ deniedTooltip: tr("fluidgrids.variables.deleteDeniedTooltip", "You don't have permission to delete variables"),
724
+ children: /* @__PURE__ */ jsx("button", {
725
+ onClick: () => handleDelete(variable),
726
+ className: "p-1.5 rounded hover:bg-background-tertiary text-text-secondary hover:text-status-error-text",
727
+ title: tr("fluidgrids.variables.delete", "Delete"),
728
+ children: /* @__PURE__ */ jsx(Icon, {
729
+ icon: "mdi:trash-can-outline",
730
+ width: 16
731
+ })
732
+ })
733
+ })]
734
+ })
735
+ })
736
+ ] }, variable.id))
737
+ ] })] })
738
+ }),
739
+ /* @__PURE__ */ jsx(VariableFormDialog, {
740
+ open: dialogOpen,
741
+ onOpenChange: setDialogOpen,
742
+ variable: editing,
743
+ onSaved: refetch
744
+ })
745
+ ] });
746
+ }
747
+ function ExternalProvidersTab() {
748
+ const tr = useTr();
749
+ const { configs, loading, refetch } = useSecretsProviderConfigs();
750
+ const { saveConfig, loading: saving } = useSaveSecretsProviderConfig();
751
+ const { testConnection, loading: testing } = useTestSecretsProviderConnection();
752
+ const awsConfig = configs.find((c) => c.provider === "AWS_SECRETS_MANAGER");
753
+ const [prefix, setPrefix] = useState("");
754
+ const [region, setRegion] = useState("ap-south-1");
755
+ const [enabled, setEnabled] = useState(false);
756
+ const [lastTest, setLastTest] = useState(null);
757
+ const [hydratedConfigId, setHydratedConfigId] = useState(null);
758
+ useEffect(() => {
759
+ if (!awsConfig || awsConfig.id === hydratedConfigId) return;
760
+ setPrefix(awsConfig.awsSecretsManagerPrefix ?? "");
761
+ setRegion(awsConfig.awsRegion ?? "ap-south-1");
762
+ setEnabled(awsConfig.isEnabled);
763
+ setLastTest(awsConfig.lastTestStatus ? {
764
+ success: awsConfig.lastTestStatus === "SUCCESS",
765
+ message: awsConfig.lastTestMessage ?? ""
766
+ } : null);
767
+ setHydratedConfigId(awsConfig.id);
768
+ }, [awsConfig, hydratedConfigId]);
769
+ const handleSave = useCallback(async () => {
770
+ try {
771
+ await saveConfig({
772
+ provider: "AWS_SECRETS_MANAGER",
773
+ awsSecretsManagerPrefix: prefix || void 0,
774
+ awsRegion: region || void 0,
775
+ isEnabled: enabled
776
+ });
777
+ toast.success(tr("fluidgrids.variables.providerSaved", "Provider configuration saved"));
778
+ refetch();
779
+ } catch (err) {
780
+ toast.error(err instanceof Error ? err.message : tr("fluidgrids.variables.providerSaveFailed", "Failed to save"));
781
+ }
782
+ }, [
783
+ saveConfig,
784
+ prefix,
785
+ region,
786
+ enabled,
787
+ refetch,
788
+ tr
789
+ ]);
790
+ const handleTest = useCallback(async () => {
791
+ try {
792
+ const result = await testConnection("AWS_SECRETS_MANAGER");
793
+ setLastTest(result);
794
+ if (result.success) toast.success(result.message);
795
+ else toast.error(result.message);
796
+ } catch (err) {
797
+ toast.error(err instanceof Error ? err.message : tr("fluidgrids.variables.testFailed", "Connection test failed"));
798
+ }
799
+ }, [testConnection, tr]);
800
+ if (loading) return /* @__PURE__ */ jsx("p", {
801
+ className: "text-text-secondary text-sm",
802
+ children: tr("fluidgrids.variables.loading", "Loading…")
803
+ });
804
+ return /* @__PURE__ */ jsxs("div", {
805
+ className: "space-y-4 max-w-xl",
806
+ children: [/* @__PURE__ */ jsx(Card, {
807
+ className: "border border-border-secondary bg-background-secondary",
808
+ children: /* @__PURE__ */ jsxs(CardHeader, {
809
+ className: "pb-3 space-y-4",
810
+ children: [
811
+ /* @__PURE__ */ jsxs("div", {
812
+ className: "flex items-center gap-2",
813
+ children: [/* @__PURE__ */ jsx(Icon, {
814
+ icon: "mdi:aws",
815
+ width: 20,
816
+ className: "text-text-secondary"
817
+ }), /* @__PURE__ */ jsx("h3", {
818
+ className: "text-sm font-semibold text-text-primary",
819
+ children: tr("fluidgrids.variables.awsProviderTitle", "AWS Secrets Manager")
820
+ })]
821
+ }),
822
+ /* @__PURE__ */ jsx("p", {
823
+ className: "text-xs text-text-secondary",
824
+ children: tr("fluidgrids.variables.awsProviderDescription", "A variable can reference a secret stored in AWS Secrets Manager instead of storing its own value. Only secrets under the prefix below are reachable.")
825
+ }),
826
+ /* @__PURE__ */ jsxs("div", {
827
+ className: "space-y-1.5",
828
+ children: [/* @__PURE__ */ jsx(Label, {
829
+ htmlFor: "aws-prefix",
830
+ children: tr("fluidgrids.variables.awsPrefixLabel", "Secrets Manager prefix")
831
+ }), /* @__PURE__ */ jsx(Input, {
832
+ id: "aws-prefix",
833
+ value: prefix,
834
+ onChange: (e) => setPrefix(e.target.value),
835
+ placeholder: "boff/prod/wspace/workflow/vars/"
836
+ })]
837
+ }),
838
+ /* @__PURE__ */ jsxs("div", {
839
+ className: "space-y-1.5",
840
+ children: [/* @__PURE__ */ jsx(Label, {
841
+ htmlFor: "aws-region",
842
+ children: tr("fluidgrids.variables.awsRegionLabel", "Region")
843
+ }), /* @__PURE__ */ jsx(Input, {
844
+ id: "aws-region",
845
+ value: region,
846
+ onChange: (e) => setRegion(e.target.value)
847
+ })]
848
+ }),
849
+ /* @__PURE__ */ jsxs("div", {
850
+ className: "flex items-center justify-between",
851
+ children: [/* @__PURE__ */ jsx(Label, {
852
+ htmlFor: "aws-enabled",
853
+ children: tr("fluidgrids.variables.awsEnabledLabel", "Enabled")
854
+ }), /* @__PURE__ */ jsx(Switch, {
855
+ id: "aws-enabled",
856
+ checked: enabled,
857
+ onCheckedChange: setEnabled
858
+ })]
859
+ }),
860
+ lastTest && /* @__PURE__ */ jsx("div", {
861
+ className: `text-xs rounded-md px-3 py-2 border ${lastTest.success ? "border-status-success-border bg-status-success-bg-subtle text-status-success-text" : "border-status-error-border bg-status-error-bg-subtle text-status-error-text"}`,
862
+ children: lastTest.message
863
+ }),
864
+ /* @__PURE__ */ jsxs("div", {
865
+ className: "flex items-center gap-2 pt-1",
866
+ children: [/* @__PURE__ */ jsx(Button$1, {
867
+ "data-agent": "confirm",
868
+ onClick: handleSave,
869
+ disabled: saving,
870
+ size: "sm",
871
+ children: saving ? tr("fluidgrids.variables.saving", "Saving…") : tr("fluidgrids.variables.save", "Save")
872
+ }), /* @__PURE__ */ jsx(Button$1, {
873
+ onClick: handleTest,
874
+ disabled: testing,
875
+ variant: "outline",
876
+ size: "sm",
877
+ children: testing ? tr("fluidgrids.variables.testing", "Testing…") : tr("fluidgrids.variables.testConnection", "Test connection")
878
+ })]
879
+ })
880
+ ]
881
+ })
882
+ }), /* @__PURE__ */ jsx("p", {
883
+ className: "text-xs text-text-secondary",
884
+ children: tr("fluidgrids.variables.otherProvidersNote", "HashiCorp Vault, Azure Key Vault, and GCP Secret Manager are not available yet.")
885
+ })]
886
+ });
887
+ }
888
+ function VariablesPage() {
889
+ const tr = useTr();
890
+ const navigate = useNavigate();
891
+ const [activeTab, setActiveTab] = useState("variables");
892
+ return /* @__PURE__ */ jsxs("div", {
893
+ className: "p-4 sm:p-6 bg-background-primary min-h-screen",
894
+ children: [/* @__PURE__ */ jsxs("div", {
895
+ className: "flex flex-col sm:flex-row sm:items-center sm:justify-between gap-4 mb-6",
896
+ "data-tour": "fluidgrids-variables-header",
897
+ children: [/* @__PURE__ */ jsxs("div", { children: [/* @__PURE__ */ jsx("h1", {
898
+ className: "text-2xl sm:text-3xl font-bold text-text-primary",
899
+ children: tr("fluidgrids.variables.pageTitle", "Variables")
900
+ }), /* @__PURE__ */ jsx("p", {
901
+ className: "text-text-secondary mt-1",
902
+ children: tr("fluidgrids.variables.pageSubtitle", "Reusable values workflows can reference as $vars")
903
+ })] }), /* @__PURE__ */ jsxs(Button$1, {
904
+ variant: "outline",
905
+ onClick: () => navigate("../list"),
906
+ children: [/* @__PURE__ */ jsx(Icon, {
907
+ icon: "mdi:arrow-left",
908
+ className: "mr-2",
909
+ width: 16
910
+ }), tr("fluidgrids.variables.backToWorkflows", "Back to Workflows")]
911
+ })]
912
+ }), /* @__PURE__ */ jsxs(Tabs, {
913
+ value: activeTab,
914
+ onValueChange: setActiveTab,
915
+ className: "w-full",
916
+ children: [
917
+ /* @__PURE__ */ jsxs(TabsList, {
918
+ className: "bg-background-secondary border border-border-secondary mb-6",
919
+ "data-tour": "fluidgrids-variables-tabs",
920
+ children: [/* @__PURE__ */ jsxs(TabsTrigger, {
921
+ value: "variables",
922
+ className: "gap-1.5",
923
+ children: [/* @__PURE__ */ jsx(Icon, {
924
+ icon: "mdi:variable",
925
+ width: 16
926
+ }), tr("fluidgrids.variables.variablesTab", "Variables")]
927
+ }), /* @__PURE__ */ jsxs(TabsTrigger, {
928
+ value: "providers",
929
+ className: "gap-1.5",
930
+ children: [/* @__PURE__ */ jsx(Icon, {
931
+ icon: "mdi:key-chain-variant",
932
+ width: 16
933
+ }), tr("fluidgrids.variables.providersTab", "External Providers")]
934
+ })]
935
+ }),
936
+ /* @__PURE__ */ jsx(TabsContent, {
937
+ value: "variables",
938
+ children: /* @__PURE__ */ jsx(VariablesTab, {})
939
+ }),
940
+ /* @__PURE__ */ jsx(TabsContent, {
941
+ value: "providers",
942
+ children: /* @__PURE__ */ jsx(ExternalProvidersTab, {})
943
+ })
944
+ ]
945
+ })]
946
+ });
947
+ }
948
+
949
+ export { useRevealVariableValue as a, useTestSecretsProviderConnection as c, useDeleteVariable as i, useUpdateVariable as l, VariablesPage_exports as n, useSaveSecretsProviderConfig as o, useCreateVariable as r, useSecretsProviderConfigs as s, VariablesPage as t, useVariables as u };