@shipfox/client-workflows 5.0.0 → 6.0.2

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 (122) hide show
  1. package/.turbo/turbo-build.log +1 -1
  2. package/CHANGELOG.md +68 -0
  3. package/dist/components/workflow-run-list/types.d.ts +12 -0
  4. package/dist/components/workflow-run-list/types.d.ts.map +1 -1
  5. package/dist/components/workflow-run-list/types.js.map +1 -1
  6. package/dist/components/workflow-run-list/workflow-run-list-view.d.ts +1 -1
  7. package/dist/components/workflow-run-list/workflow-run-list-view.d.ts.map +1 -1
  8. package/dist/components/workflow-run-list/workflow-run-list-view.js +32 -11
  9. package/dist/components/workflow-run-list/workflow-run-list-view.js.map +1 -1
  10. package/dist/components/workflow-run-list/workflow-run-list.d.ts +1 -1
  11. package/dist/components/workflow-run-list/workflow-run-list.d.ts.map +1 -1
  12. package/dist/components/workflow-run-list/workflow-run-list.js +7 -2
  13. package/dist/components/workflow-run-list/workflow-run-list.js.map +1 -1
  14. package/dist/components/workflow-run-summary/workflow-run-summary.d.ts +2 -3
  15. package/dist/components/workflow-run-summary/workflow-run-summary.d.ts.map +1 -1
  16. package/dist/components/workflow-run-summary/workflow-run-summary.js.map +1 -1
  17. package/dist/components/workflow-run-view/job-card.d.ts.map +1 -1
  18. package/dist/components/workflow-run-view/job-card.js +9 -8
  19. package/dist/components/workflow-run-view/job-card.js.map +1 -1
  20. package/dist/components/workflow-run-view/workflow-run-view.js.map +1 -1
  21. package/dist/core/entities/job-execution.d.ts +11 -6
  22. package/dist/core/entities/job-execution.d.ts.map +1 -1
  23. package/dist/core/entities/job-execution.js +0 -19
  24. package/dist/core/entities/job-execution.js.map +1 -1
  25. package/dist/core/entities/job.d.ts +32 -10
  26. package/dist/core/entities/job.d.ts.map +1 -1
  27. package/dist/core/entities/job.js +0 -22
  28. package/dist/core/entities/job.js.map +1 -1
  29. package/dist/core/entities/step-attempt.d.ts +28 -3
  30. package/dist/core/entities/step-attempt.d.ts.map +1 -1
  31. package/dist/core/entities/step-attempt.js +0 -17
  32. package/dist/core/entities/step-attempt.js.map +1 -1
  33. package/dist/core/entities/step.d.ts +6 -6
  34. package/dist/core/entities/step.d.ts.map +1 -1
  35. package/dist/core/entities/step.js +19 -49
  36. package/dist/core/entities/step.js.map +1 -1
  37. package/dist/core/entities/workflow-run-attempt.d.ts +0 -2
  38. package/dist/core/entities/workflow-run-attempt.d.ts.map +1 -1
  39. package/dist/core/entities/workflow-run-attempt.js +0 -12
  40. package/dist/core/entities/workflow-run-attempt.js.map +1 -1
  41. package/dist/core/entities/workflow-run.d.ts +6 -7
  42. package/dist/core/entities/workflow-run.d.ts.map +1 -1
  43. package/dist/core/entities/workflow-run.js +1 -67
  44. package/dist/core/entities/workflow-run.js.map +1 -1
  45. package/dist/core/workflow-run.d.ts +9 -9
  46. package/dist/core/workflow-run.d.ts.map +1 -1
  47. package/dist/core/workflow-run.js +6 -6
  48. package/dist/core/workflow-run.js.map +1 -1
  49. package/dist/feature.d.ts +13 -0
  50. package/dist/feature.d.ts.map +1 -1
  51. package/dist/feature.js +17 -16
  52. package/dist/feature.js.map +1 -1
  53. package/dist/hooks/api/workflow-run-mapper.d.ts +12 -0
  54. package/dist/hooks/api/workflow-run-mapper.d.ts.map +1 -0
  55. package/dist/hooks/api/workflow-run-mapper.js +207 -0
  56. package/dist/hooks/api/workflow-run-mapper.js.map +1 -0
  57. package/dist/hooks/api/workflow-runs.d.ts +25 -55
  58. package/dist/hooks/api/workflow-runs.d.ts.map +1 -1
  59. package/dist/hooks/api/workflow-runs.js +95 -51
  60. package/dist/hooks/api/workflow-runs.js.map +1 -1
  61. package/dist/index.d.ts +2 -2
  62. package/dist/index.d.ts.map +1 -1
  63. package/dist/index.js +1 -1
  64. package/dist/index.js.map +1 -1
  65. package/dist/pages/project-workflows-page.d.ts.map +1 -1
  66. package/dist/pages/project-workflows-page.js +14 -14
  67. package/dist/pages/project-workflows-page.js.map +1 -1
  68. package/dist/pages/workflow-run-page.d.ts +3 -1
  69. package/dist/pages/workflow-run-page.d.ts.map +1 -1
  70. package/dist/pages/workflow-run-page.js +21 -14
  71. package/dist/pages/workflow-run-page.js.map +1 -1
  72. package/dist/routes/inputs.d.ts +22 -0
  73. package/dist/routes/inputs.d.ts.map +1 -0
  74. package/dist/routes/inputs.js +76 -0
  75. package/dist/routes/inputs.js.map +1 -0
  76. package/dist/routes/run-detail.d.ts +2 -0
  77. package/dist/routes/run-detail.d.ts.map +1 -1
  78. package/dist/routes/run-detail.js +6 -6
  79. package/dist/routes/run-detail.js.map +1 -1
  80. package/dist/routes/runs.d.ts +2 -0
  81. package/dist/routes/runs.d.ts.map +1 -1
  82. package/dist/routes/runs.js +6 -6
  83. package/dist/routes/runs.js.map +1 -1
  84. package/dist/routes/workflows.js +3 -5
  85. package/dist/routes/workflows.js.map +1 -1
  86. package/dist/tsconfig.test.tsbuildinfo +1 -1
  87. package/package.json +13 -14
  88. package/src/components/workflow-run-list/types.ts +6 -0
  89. package/src/components/workflow-run-list/workflow-run-list-view.tsx +27 -11
  90. package/src/components/workflow-run-list/workflow-run-list.tsx +6 -0
  91. package/src/components/workflow-run-summary/workflow-run-attempt-switcher.test.tsx +5 -6
  92. package/src/components/workflow-run-summary/workflow-run-summary.tsx +3 -3
  93. package/src/components/workflow-run-view/job-card.tsx +20 -11
  94. package/src/components/workflow-run-view/workflow-run-view.test.tsx +3 -3
  95. package/src/components/workflow-run-view/workflow-run-view.tsx +2 -2
  96. package/src/components/workflow-source-panel/workflow-source-panel.stories.tsx +4 -0
  97. package/src/core/entities/job-execution.ts +12 -28
  98. package/src/core/entities/job.ts +44 -45
  99. package/src/core/entities/step-attempt.ts +9 -20
  100. package/src/core/entities/step.ts +38 -66
  101. package/src/core/entities/workflow-run-attempt.ts +0 -14
  102. package/src/core/entities/workflow-run.ts +8 -86
  103. package/src/core/workflow-run.test.ts +13 -11
  104. package/src/core/workflow-run.ts +8 -13
  105. package/src/feature.ts +19 -17
  106. package/src/hooks/api/workflow-run-mapper.ts +246 -0
  107. package/src/hooks/api/workflow-runs.test.tsx +57 -59
  108. package/src/hooks/api/workflow-runs.ts +187 -88
  109. package/src/index.ts +4 -0
  110. package/src/pages/project-workflows-page.test.tsx +1 -1
  111. package/src/pages/project-workflows-page.tsx +31 -26
  112. package/src/pages/workflow-run-page.test.tsx +4 -2
  113. package/src/pages/workflow-run-page.tsx +22 -17
  114. package/src/routes/inputs.test.ts +22 -0
  115. package/src/routes/inputs.ts +58 -0
  116. package/src/routes/run-detail.tsx +12 -8
  117. package/src/routes/runs.tsx +11 -4
  118. package/src/routes/workflows.tsx +3 -3
  119. package/test/fixtures/workflow-run.ts +9 -7
  120. package/test/pages.tsx +20 -5
  121. package/tsconfig.build.tsbuildinfo +1 -1
  122. package/vercel.json +5 -0
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,YAAY,EACV,gBAAgB,EAChB,kBAAkB,EAClB,2BAA2B,EAC3B,kBAAkB,EAClB,gBAAgB,EAChB,SAAS,EACT,IAAI,EACJ,WAAW,EACX,0BAA0B,EAC1B,SAAS,EACT,iBAAiB,EACjB,eAAe,EACf,cAAc,EACd,kBAAkB,EAClB,WAAW,EACX,kBAAkB,EAClB,iBAAiB,EACjB,mBAAmB,EACnB,iBAAiB,EACjB,sBAAsB,EACtB,cAAc,GACf,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EACL,qBAAqB,EACrB,gBAAgB,EAChB,GAAG,EACH,YAAY,EACZ,8BAA8B,EAC9B,qBAAqB,EACrB,kBAAkB,EAClB,uBAAuB,GACxB,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EACL,KAAK,2BAA2B,EAChC,kBAAkB,EAClB,4BAA4B,EAC5B,6BAA6B,EAC7B,2BAA2B,EAC3B,mBAAmB,EACnB,4BAA4B,EAC5B,KAAK,kBAAkB,EACvB,qBAAqB,GACtB,MAAM,8BAA8B,CAAC;AACtC,OAAO,EAAC,oBAAoB,EAAC,MAAM,mCAAmC,CAAC;AACvE,OAAO,EAAC,eAAe,EAAC,MAAM,8BAA8B,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,YAAY,EACV,gBAAgB,EAChB,kBAAkB,EAClB,2BAA2B,EAC3B,kBAAkB,EAClB,gBAAgB,EAChB,SAAS,EACT,oBAAoB,EACpB,IAAI,EACJ,WAAW,EACX,0BAA0B,EAC1B,SAAS,EACT,iBAAiB,EACjB,eAAe,EACf,cAAc,EACd,kBAAkB,EAClB,WAAW,EACX,kBAAkB,EAClB,iBAAiB,EACjB,mBAAmB,EACnB,iBAAiB,EACjB,sBAAsB,EACtB,cAAc,GACf,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EACL,qBAAqB,EACrB,gBAAgB,EAChB,GAAG,EACH,YAAY,EACZ,8BAA8B,EAC9B,qBAAqB,EACrB,kBAAkB,EAClB,uBAAuB,GACxB,MAAM,uBAAuB,CAAC;AAC/B,OAAO,EACL,KAAK,2BAA2B,EAChC,kBAAkB,EAClB,4BAA4B,EAC5B,6BAA6B,EAC7B,2BAA2B,EAC3B,mBAAmB,EACnB,4BAA4B,EAC5B,KAAK,kBAAkB,EACvB,+BAA+B,EAC/B,uBAAuB,EACvB,gCAAgC,EAChC,qBAAqB,GACtB,MAAM,8BAA8B,CAAC;AACtC,OAAO,EAAC,oBAAoB,EAAC,MAAM,mCAAmC,CAAC;AACvE,OAAO,EAAC,eAAe,EAAC,MAAM,8BAA8B,CAAC"}
package/dist/index.js CHANGED
@@ -1,5 +1,5 @@
1
1
  export { isWorkflowRunTerminal, isWorkflowStatus, Job, JobExecution, TERMINAL_WORKFLOW_RUN_STATUSES, WORKFLOW_RUN_STATUSES, workflowRunShortId, workflowRunTriggerLabel } from '#core/workflow-run.js';
2
- export { fireManualWorkflow, useCancelWorkflowRunMutation, useFireManualWorkflowMutation, useWorkflowRunAttemptsQuery, useWorkflowRunQuery, useWorkflowRunsInfiniteQuery, workflowRunsQueryKeys } from './hooks/api/workflow-runs.js';
2
+ export { fireManualWorkflow, useCancelWorkflowRunMutation, useFireManualWorkflowMutation, useWorkflowRunAttemptsQuery, useWorkflowRunQuery, useWorkflowRunsInfiniteQuery, workflowRunAttemptsQueryOptions, workflowRunQueryOptions, workflowRunsInfiniteQueryOptions, workflowRunsQueryKeys } from './hooks/api/workflow-runs.js';
3
3
  export { ProjectWorkflowsPage } from './pages/project-workflows-page.js';
4
4
  export { WorkflowRunPage } from './pages/workflow-run-page.js';
5
5
 
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts"],"sourcesContent":["export type {\n AgentConfigIssue,\n JobDisplayDuration,\n JobExecutionDisplayDuration,\n JobExecutionStatus,\n JobExecutionTime,\n JobStatus,\n Step,\n StepAttempt,\n StepAttemptDisplayDuration,\n StepError,\n StepErrorCategory,\n StepErrorReason,\n StepGateResult,\n StepSourceLocation,\n WorkflowRun,\n WorkflowRunAttempt,\n WorkflowRunDetail,\n WorkflowRunListPage,\n WorkflowRunStatus,\n WorkflowSourceSnapshot,\n WorkflowStatus,\n} from '#core/workflow-run.js';\nexport {\n isWorkflowRunTerminal,\n isWorkflowStatus,\n Job,\n JobExecution,\n TERMINAL_WORKFLOW_RUN_STATUSES,\n WORKFLOW_RUN_STATUSES,\n workflowRunShortId,\n workflowRunTriggerLabel,\n} from '#core/workflow-run.js';\nexport {\n type FireManualWorkflowVariables,\n fireManualWorkflow,\n useCancelWorkflowRunMutation,\n useFireManualWorkflowMutation,\n useWorkflowRunAttemptsQuery,\n useWorkflowRunQuery,\n useWorkflowRunsInfiniteQuery,\n type WorkflowRunFilters,\n workflowRunsQueryKeys,\n} from './hooks/api/workflow-runs.js';\nexport {ProjectWorkflowsPage} from './pages/project-workflows-page.js';\nexport {WorkflowRunPage} from './pages/workflow-run-page.js';\n"],"names":["isWorkflowRunTerminal","isWorkflowStatus","Job","JobExecution","TERMINAL_WORKFLOW_RUN_STATUSES","WORKFLOW_RUN_STATUSES","workflowRunShortId","workflowRunTriggerLabel","fireManualWorkflow","useCancelWorkflowRunMutation","useFireManualWorkflowMutation","useWorkflowRunAttemptsQuery","useWorkflowRunQuery","useWorkflowRunsInfiniteQuery","workflowRunsQueryKeys","ProjectWorkflowsPage","WorkflowRunPage"],"mappings":"AAuBA,SACEA,qBAAqB,EACrBC,gBAAgB,EAChBC,GAAG,EACHC,YAAY,EACZC,8BAA8B,EAC9BC,qBAAqB,EACrBC,kBAAkB,EAClBC,uBAAuB,QAClB,wBAAwB;AAC/B,SAEEC,kBAAkB,EAClBC,4BAA4B,EAC5BC,6BAA6B,EAC7BC,2BAA2B,EAC3BC,mBAAmB,EACnBC,4BAA4B,EAE5BC,qBAAqB,QAChB,+BAA+B;AACtC,SAAQC,oBAAoB,QAAO,oCAAoC;AACvE,SAAQC,eAAe,QAAO,+BAA+B"}
1
+ {"version":3,"sources":["../src/index.ts"],"sourcesContent":["export type {\n AgentConfigIssue,\n JobDisplayDuration,\n JobExecutionDisplayDuration,\n JobExecutionStatus,\n JobExecutionTime,\n JobStatus,\n ManualWorkflowLaunch,\n Step,\n StepAttempt,\n StepAttemptDisplayDuration,\n StepError,\n StepErrorCategory,\n StepErrorReason,\n StepGateResult,\n StepSourceLocation,\n WorkflowRun,\n WorkflowRunAttempt,\n WorkflowRunDetail,\n WorkflowRunListPage,\n WorkflowRunStatus,\n WorkflowSourceSnapshot,\n WorkflowStatus,\n} from '#core/workflow-run.js';\nexport {\n isWorkflowRunTerminal,\n isWorkflowStatus,\n Job,\n JobExecution,\n TERMINAL_WORKFLOW_RUN_STATUSES,\n WORKFLOW_RUN_STATUSES,\n workflowRunShortId,\n workflowRunTriggerLabel,\n} from '#core/workflow-run.js';\nexport {\n type FireManualWorkflowVariables,\n fireManualWorkflow,\n useCancelWorkflowRunMutation,\n useFireManualWorkflowMutation,\n useWorkflowRunAttemptsQuery,\n useWorkflowRunQuery,\n useWorkflowRunsInfiniteQuery,\n type WorkflowRunFilters,\n workflowRunAttemptsQueryOptions,\n workflowRunQueryOptions,\n workflowRunsInfiniteQueryOptions,\n workflowRunsQueryKeys,\n} from './hooks/api/workflow-runs.js';\nexport {ProjectWorkflowsPage} from './pages/project-workflows-page.js';\nexport {WorkflowRunPage} from './pages/workflow-run-page.js';\n"],"names":["isWorkflowRunTerminal","isWorkflowStatus","Job","JobExecution","TERMINAL_WORKFLOW_RUN_STATUSES","WORKFLOW_RUN_STATUSES","workflowRunShortId","workflowRunTriggerLabel","fireManualWorkflow","useCancelWorkflowRunMutation","useFireManualWorkflowMutation","useWorkflowRunAttemptsQuery","useWorkflowRunQuery","useWorkflowRunsInfiniteQuery","workflowRunAttemptsQueryOptions","workflowRunQueryOptions","workflowRunsInfiniteQueryOptions","workflowRunsQueryKeys","ProjectWorkflowsPage","WorkflowRunPage"],"mappings":"AAwBA,SACEA,qBAAqB,EACrBC,gBAAgB,EAChBC,GAAG,EACHC,YAAY,EACZC,8BAA8B,EAC9BC,qBAAqB,EACrBC,kBAAkB,EAClBC,uBAAuB,QAClB,wBAAwB;AAC/B,SAEEC,kBAAkB,EAClBC,4BAA4B,EAC5BC,6BAA6B,EAC7BC,2BAA2B,EAC3BC,mBAAmB,EACnBC,4BAA4B,EAE5BC,+BAA+B,EAC/BC,uBAAuB,EACvBC,gCAAgC,EAChCC,qBAAqB,QAChB,+BAA+B;AACtC,SAAQC,oBAAoB,QAAO,oCAAoC;AACvE,SAAQC,eAAe,QAAO,+BAA+B"}
@@ -1 +1 @@
1
- {"version":3,"file":"project-workflows-page.d.ts","sourceRoot":"","sources":["../../src/pages/project-workflows-page.tsx"],"names":[],"mappings":"AAgCA,wBAAgB,oBAAoB,CAAC,EAAC,SAAS,EAAC,EAAE;IAAC,SAAS,EAAE,MAAM,CAAA;CAAC,+BAMpE"}
1
+ {"version":3,"file":"project-workflows-page.d.ts","sourceRoot":"","sources":["../../src/pages/project-workflows-page.tsx"],"names":[],"mappings":"AAqCA,wBAAgB,oBAAoB,CAAC,EAAC,SAAS,EAAC,EAAE;IAAC,SAAS,EAAE,MAAM,CAAA;CAAC,+BAMpE"}
@@ -32,7 +32,7 @@ function ProjectWorkflowsPageInner({ projectId }) {
32
32
  const sync = definitionsQuery.data?.pages[0]?.sync;
33
33
  async function handleRun(definition) {
34
34
  setRunError(null);
35
- if (!definition.manual_trigger) return;
35
+ if (!definition.manualTrigger) return;
36
36
  try {
37
37
  await fireManual.mutateAsync({
38
38
  projectId,
@@ -87,8 +87,8 @@ function ProjectWorkflowsPageInner({ projectId }) {
87
87
  ]
88
88
  }),
89
89
  /*#__PURE__*/ _jsx(SourceStrip, {
90
- connectionId: projectQuery.data.source.connection_id,
91
- externalRepositoryId: projectQuery.data.source.external_repository_id,
90
+ connectionId: projectQuery.data.source.connectionId,
91
+ externalRepositoryId: projectQuery.data.source.externalRepositoryId,
92
92
  sync: sync,
93
93
  isPending: definitionsQuery.isPending
94
94
  }),
@@ -217,7 +217,7 @@ function WorkflowDefinitionsList({ definitions, isPending, isError, sync, runErr
217
217
  }),
218
218
  /*#__PURE__*/ _jsx(Code, {
219
219
  className: "truncate text-foreground-neutral-muted",
220
- children: definition.config_path ?? 'Manual definition'
220
+ children: definition.configPath ?? 'Manual definition'
221
221
  })
222
222
  ]
223
223
  }),
@@ -232,11 +232,11 @@ function WorkflowDefinitionsList({ definitions, isPending, isError, sync, runErr
232
232
  /*#__PURE__*/ _jsx(TableCell, {
233
233
  className: "text-foreground-neutral-muted",
234
234
  children: /*#__PURE__*/ _jsx(RelativeTime, {
235
- value: definition.updated_at
235
+ value: definition.updatedAt
236
236
  })
237
237
  }),
238
238
  /*#__PURE__*/ _jsx(TableCell, {
239
- children: definition.manual_trigger ? /*#__PURE__*/ _jsx("div", {
239
+ children: definition.manualTrigger ? /*#__PURE__*/ _jsx("div", {
240
240
  className: "flex justify-end opacity-0 transition-opacity group-hover:opacity-100 group-focus-within:opacity-100",
241
241
  children: /*#__PURE__*/ _jsx(Button, {
242
242
  size: "xs",
@@ -282,7 +282,7 @@ function WorkflowDefinitionsList({ definitions, isPending, isError, sync, runErr
282
282
  }),
283
283
  /*#__PURE__*/ _jsx(Code, {
284
284
  className: "break-words text-foreground-neutral-muted",
285
- children: definition.config_path ?? 'Manual definition'
285
+ children: definition.configPath ?? 'Manual definition'
286
286
  })
287
287
  ]
288
288
  })
@@ -297,11 +297,11 @@ function WorkflowDefinitionsList({ definitions, isPending, isError, sync, runErr
297
297
  children: [
298
298
  "Updated ",
299
299
  /*#__PURE__*/ _jsx(RelativeTime, {
300
- value: definition.updated_at
300
+ value: definition.updatedAt
301
301
  })
302
302
  ]
303
303
  }),
304
- definition.manual_trigger ? /*#__PURE__*/ _jsx(Button, {
304
+ definition.manualTrigger ? /*#__PURE__*/ _jsx(Button, {
305
305
  size: "sm",
306
306
  isLoading: isRunning,
307
307
  onClick: ()=>onRun(definition),
@@ -354,7 +354,7 @@ function sourceIcon(source) {
354
354
  return source === 'vcs' ? 'gitBranchLine' : 'terminalLine';
355
355
  }
356
356
  function WorkflowEmptyState({ sync }) {
357
- const message = sync?.status === 'failed' && sync.last_error_code === 'no-workflow-files' ? 'No workflow files found under .shipfox/workflows/.' : sync?.status === 'failed' ? sync.last_error_message ?? 'Workflow definitions could not be synced.' : sync?.status === 'syncing' ? 'Workflow definitions are being discovered.' : sync?.status === 'succeeded' ? 'No workflow definitions found.' : 'Workflow sync has not reported yet.';
357
+ const message = sync?.status === 'failed' && sync.lastErrorCode === 'no-workflow-files' ? 'No workflow files found under .shipfox/workflows/.' : sync?.status === 'failed' ? sync.lastErrorMessage ?? 'Workflow definitions could not be synced.' : sync?.status === 'syncing' ? 'Workflow definitions are being discovered.' : sync?.status === 'succeeded' ? 'No workflow definitions found.' : 'Workflow sync has not reported yet.';
358
358
  return /*#__PURE__*/ _jsx(EmptyState, {
359
359
  icon: "flowChart",
360
360
  title: "No workflows",
@@ -376,7 +376,7 @@ function WorkflowSyncAlert({ sync }) {
376
376
  }),
377
377
  /*#__PURE__*/ _jsx(Text, {
378
378
  size: "sm",
379
- children: sync.last_error_message ?? 'The latest workflow sync failed before definitions updated.'
379
+ children: sync.lastErrorMessage ?? 'The latest workflow sync failed before definitions updated.'
380
380
  })
381
381
  ]
382
382
  })
@@ -384,8 +384,8 @@ function WorkflowSyncAlert({ sync }) {
384
384
  }
385
385
  function DefinitionSheet({ definition, onOpenChange }) {
386
386
  const normalizedJson = definition ? JSON.stringify({
387
- workflow_document: definition.workflow_document,
388
- workflow_model: definition.workflow_model
387
+ workflow_document: definition.workflowDocument,
388
+ workflow_model: definition.workflowModel
389
389
  }, null, 2) : '';
390
390
  return /*#__PURE__*/ _jsx(Sheet, {
391
391
  open: Boolean(definition),
@@ -400,7 +400,7 @@ function DefinitionSheet({ definition, onOpenChange }) {
400
400
  children: definition.name
401
401
  }),
402
402
  /*#__PURE__*/ _jsx(SheetDescription, {
403
- children: definition.config_path ?? 'Manual workflow definition'
403
+ children: definition.configPath ?? 'Manual workflow definition'
404
404
  })
405
405
  ]
406
406
  }),
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/pages/project-workflows-page.tsx"],"sourcesContent":["import type {DefinitionDto, DefinitionSyncSummaryDto} from '@shipfox/api-definitions-dto';\nimport {ApiError} from '@shipfox/client-api';\nimport {SourceStrip, useDefinitionsInfiniteQuery, useProjectQuery} from '@shipfox/client-projects';\nimport {QueryLoadError} from '@shipfox/client-ui';\nimport {Button} from '@shipfox/react-ui/button';\nimport {Callout} from '@shipfox/react-ui/callout';\nimport {EmptyState} from '@shipfox/react-ui/empty-state';\nimport {Icon, type IconName} from '@shipfox/react-ui/icon';\nimport {LoadErrorState} from '@shipfox/react-ui/load-error-state';\nimport {RelativeTime, RelativeTimeProvider} from '@shipfox/react-ui/relative-time';\nimport {\n Sheet,\n SheetBody,\n SheetContent,\n SheetDescription,\n SheetHeader,\n SheetTitle,\n} from '@shipfox/react-ui/sheet';\nimport {Skeleton} from '@shipfox/react-ui/skeleton';\nimport {\n Table,\n TableBody,\n TableCell,\n TableHead,\n TableHeader,\n TableRow,\n} from '@shipfox/react-ui/table';\nimport {toast} from '@shipfox/react-ui/toast';\nimport {Code, Header, Text} from '@shipfox/react-ui/typography';\nimport {useState} from 'react';\nimport {useFireManualWorkflowMutation} from '#hooks/api/workflow-runs.js';\n\nexport function ProjectWorkflowsPage({projectId}: {projectId: string}) {\n return (\n <RelativeTimeProvider>\n <ProjectWorkflowsPageInner projectId={projectId} />\n </RelativeTimeProvider>\n );\n}\n\nfunction ProjectWorkflowsPageInner({projectId}: {projectId: string}) {\n const projectQuery = useProjectQuery(projectId);\n const definitionsQuery = useDefinitionsInfiniteQuery(projectId);\n const fireManual = useFireManualWorkflowMutation();\n const [selectedDefinition, setSelectedDefinition] = useState<DefinitionDto | null>(null);\n const [runError, setRunError] = useState<{definitionId: string; message: string} | null>(null);\n const definitions = definitionsQuery.data?.pages.flatMap((page) => page.definitions) ?? [];\n const sync = definitionsQuery.data?.pages[0]?.sync;\n\n async function handleRun(definition: DefinitionDto) {\n setRunError(null);\n if (!definition.manual_trigger) return;\n try {\n await fireManual.mutateAsync({projectId, definitionId: definition.id});\n toast.success('Run queued');\n } catch (error) {\n const message = errorMessage(error, 'Could not queue run.');\n setRunError({definitionId: definition.id, message});\n toast.error(message);\n }\n }\n\n return (\n <div className=\"flex w-full flex-col gap-24\">\n {projectQuery.isPending ? (\n <div className=\"flex flex-col gap-12\">\n <Skeleton className=\"h-28 w-1/3\" />\n <Skeleton className=\"h-18 w-1/2\" />\n </div>\n ) : null}\n\n {projectQuery.isError && projectQuery.data === undefined ? (\n projectQuery.error instanceof ApiError && projectQuery.error.status === 404 ? (\n <EmptyState\n icon=\"errorWarningLine\"\n title=\"Project not found\"\n description=\"This project doesn't exist, or you don't have access to it.\"\n />\n ) : (\n <QueryLoadError query={projectQuery} subject=\"project\" />\n )\n ) : null}\n\n {projectQuery.data ? (\n <>\n <header className=\"flex flex-col gap-4\">\n <Header variant=\"h2\">Workflows</Header>\n <Text size=\"sm\" className=\"text-foreground-neutral-muted\">\n Synced workflow definitions for this project source.\n </Text>\n </header>\n\n <SourceStrip\n connectionId={projectQuery.data.source.connection_id}\n externalRepositoryId={projectQuery.data.source.external_repository_id}\n sync={sync}\n isPending={definitionsQuery.isPending}\n />\n\n <WorkflowSyncAlert sync={sync} />\n\n <WorkflowDefinitionsList\n definitions={definitions}\n isPending={definitionsQuery.isPending}\n isError={definitionsQuery.isError}\n sync={sync ?? null}\n runError={runError}\n runningDefinitionId={\n fireManual.isPending && fireManual.variables\n ? fireManual.variables.definitionId\n : null\n }\n hasNextPage={definitionsQuery.hasNextPage}\n isFetchingNextPage={definitionsQuery.isFetchingNextPage}\n isFetchNextPageError={definitionsQuery.isFetchNextPageError}\n onRetry={() => definitionsQuery.refetch()}\n onLoadMore={() => definitionsQuery.fetchNextPage()}\n onOpenDefinition={setSelectedDefinition}\n onRun={(definition) => {\n void handleRun(definition);\n }}\n />\n </>\n ) : null}\n\n <DefinitionSheet\n definition={selectedDefinition}\n onOpenChange={(open) => {\n if (!open) setSelectedDefinition(null);\n }}\n />\n </div>\n );\n}\n\nfunction WorkflowDefinitionsList({\n definitions,\n isPending,\n isError,\n sync,\n runError,\n runningDefinitionId,\n hasNextPage,\n isFetchingNextPage,\n isFetchNextPageError,\n onRetry,\n onLoadMore,\n onOpenDefinition,\n onRun,\n}: {\n definitions: DefinitionDto[];\n isPending: boolean;\n isError: boolean;\n sync: DefinitionSyncSummaryDto | null;\n runError: {definitionId: string; message: string} | null;\n runningDefinitionId: string | null;\n hasNextPage: boolean;\n isFetchingNextPage: boolean;\n isFetchNextPageError: boolean;\n onRetry: () => void;\n onLoadMore: () => void;\n onOpenDefinition: (definition: DefinitionDto) => void;\n onRun: (definition: DefinitionDto) => void;\n}) {\n if (isPending) {\n return (\n <div className=\"flex flex-col gap-8\">\n <Skeleton className=\"h-40 w-full\" />\n <Skeleton className=\"h-40 w-full\" />\n <Skeleton className=\"h-40 w-full\" />\n </div>\n );\n }\n\n if (isError && definitions.length === 0) {\n return (\n <LoadErrorState\n title=\"Couldn't load workflows\"\n description=\"Definitions could not be loaded. Source metadata remains visible.\"\n onRetry={onRetry}\n retryLabel=\"Retry loading workflows\"\n />\n );\n }\n\n if (definitions.length === 0) {\n return <WorkflowEmptyState sync={sync} />;\n }\n\n return (\n <>\n <div className=\"hidden rounded-8 border border-border-neutral-base md:block\">\n <Table>\n <TableHeader>\n <TableRow>\n <TableHead className=\"w-40\"></TableHead>\n <TableHead>Workflow</TableHead>\n <TableHead className=\"w-180\">Updated</TableHead>\n <TableHead className=\"w-80 text-right\"></TableHead>\n </TableRow>\n </TableHeader>\n <TableBody>\n {definitions.map((definition) => {\n const runErrorMessage =\n runError?.definitionId === definition.id ? runError.message : null;\n const isRunning = runningDefinitionId === definition.id;\n\n return (\n // The workflow-name cell holds a `<button>` so the row is\n // keyboard-reachable (Tab focuses, Enter/Space activates\n // via native button semantics). The TableRow itself is no\n // longer clickable — a row-level onClick would be invisible\n // to keyboard users and require custom keydown handling.\n // The `group` class on the row still drives the Run button\n // reveal on hover or focus-within.\n <TableRow key={definition.id} className=\"group\">\n <TableCell>\n <Icon\n name={sourceIcon(definition.source)}\n className=\"size-16 text-foreground-neutral-muted\"\n aria-hidden=\"true\"\n />\n </TableCell>\n <TableCell className=\"max-w-260\">\n <div className=\"flex min-w-0 flex-col gap-2\">\n <button\n type=\"button\"\n onClick={() => onOpenDefinition(definition)}\n className=\"flex min-w-0 flex-col gap-2 text-left outline-none focus-visible:shadow-border-interactive-with-active rounded-4\"\n >\n <Text size=\"sm\" bold className=\"truncate\">\n {definition.name}\n </Text>\n <Code className=\"truncate text-foreground-neutral-muted\">\n {definition.config_path ?? 'Manual definition'}\n </Code>\n </button>\n {runErrorMessage ? (\n <Text size=\"xs\" className=\"text-tag-error-text\">\n {runErrorMessage}\n </Text>\n ) : null}\n </div>\n </TableCell>\n <TableCell className=\"text-foreground-neutral-muted\">\n <RelativeTime value={definition.updated_at} />\n </TableCell>\n <TableCell>\n {definition.manual_trigger ? (\n <div className=\"flex justify-end opacity-0 transition-opacity group-hover:opacity-100 group-focus-within:opacity-100\">\n <Button size=\"xs\" isLoading={isRunning} onClick={() => onRun(definition)}>\n Run\n </Button>\n </div>\n ) : null}\n </TableCell>\n </TableRow>\n );\n })}\n </TableBody>\n </Table>\n </div>\n\n <div className=\"flex flex-col rounded-8 border border-border-neutral-base md:hidden\">\n {definitions.map((definition) => {\n const runErrorMessage =\n runError?.definitionId === definition.id ? runError.message : null;\n const isRunning = runningDefinitionId === definition.id;\n\n return (\n <div\n key={definition.id}\n className=\"flex flex-col gap-10 border-b border-border-neutral-base p-12 last:border-b-0\"\n >\n <button\n type=\"button\"\n className=\"flex min-w-0 items-start gap-10 text-left\"\n onClick={() => onOpenDefinition(definition)}\n >\n <Icon\n name={sourceIcon(definition.source)}\n className=\"size-16 shrink-0 text-foreground-neutral-muted\"\n aria-hidden=\"true\"\n />\n <div className=\"flex min-w-0 flex-col gap-4\">\n <Text size=\"sm\" bold className=\"break-words\">\n {definition.name}\n </Text>\n <Code className=\"break-words text-foreground-neutral-muted\">\n {definition.config_path ?? 'Manual definition'}\n </Code>\n </div>\n </button>\n <div className=\"flex items-center justify-between gap-8\">\n <Text size=\"xs\" className=\"text-foreground-neutral-muted\">\n Updated <RelativeTime value={definition.updated_at} />\n </Text>\n {definition.manual_trigger ? (\n <Button size=\"sm\" isLoading={isRunning} onClick={() => onRun(definition)}>\n Run\n </Button>\n ) : null}\n </div>\n {runErrorMessage ? (\n <Text size=\"xs\" className=\"text-tag-error-text\">\n {runErrorMessage}\n </Text>\n ) : null}\n </div>\n );\n })}\n </div>\n\n {isFetchNextPageError ? (\n <Callout role=\"alert\" type=\"error\">\n <div className=\"flex items-center justify-between gap-12\">\n <Text size=\"sm\">Could not load more workflows.</Text>\n <Button size=\"sm\" variant=\"secondary\" onClick={onLoadMore}>\n Retry\n </Button>\n </div>\n </Callout>\n ) : null}\n\n {hasNextPage ? (\n <div className=\"flex justify-center\">\n <Button size=\"sm\" variant=\"secondary\" isLoading={isFetchingNextPage} onClick={onLoadMore}>\n Load more\n </Button>\n </div>\n ) : null}\n </>\n );\n}\n\nfunction sourceIcon(source: 'manual' | 'vcs'): IconName {\n return source === 'vcs' ? ('gitBranchLine' as IconName) : ('terminalLine' as IconName);\n}\n\nfunction WorkflowEmptyState({sync}: {sync: DefinitionSyncSummaryDto | null}) {\n const message =\n sync?.status === 'failed' && sync.last_error_code === 'no-workflow-files'\n ? 'No workflow files found under .shipfox/workflows/.'\n : sync?.status === 'failed'\n ? (sync.last_error_message ?? 'Workflow definitions could not be synced.')\n : sync?.status === 'syncing'\n ? 'Workflow definitions are being discovered.'\n : sync?.status === 'succeeded'\n ? 'No workflow definitions found.'\n : 'Workflow sync has not reported yet.';\n\n return <EmptyState icon=\"flowChart\" title=\"No workflows\" description={message} />;\n}\n\nfunction WorkflowSyncAlert({sync}: {sync: DefinitionSyncSummaryDto | null | undefined}) {\n if (sync?.status !== 'failed') return null;\n\n return (\n <Callout role=\"alert\" type=\"error\">\n <div className=\"flex flex-col gap-4\">\n <Text size=\"sm\" bold>\n Workflow sync failed\n </Text>\n <Text size=\"sm\">\n {sync.last_error_message ?? 'The latest workflow sync failed before definitions updated.'}\n </Text>\n </div>\n </Callout>\n );\n}\n\nfunction DefinitionSheet({\n definition,\n onOpenChange,\n}: {\n definition: DefinitionDto | null;\n onOpenChange: (open: boolean) => void;\n}) {\n const normalizedJson = definition\n ? JSON.stringify(\n {\n workflow_document: definition.workflow_document,\n workflow_model: definition.workflow_model,\n },\n null,\n 2,\n )\n : '';\n\n return (\n <Sheet open={Boolean(definition)} onOpenChange={onOpenChange}>\n <SheetContent className=\"w-full sm:max-w-[560px]\">\n {definition ? (\n <>\n <SheetHeader>\n <SheetTitle>{definition.name}</SheetTitle>\n <SheetDescription>\n {definition.config_path ?? 'Manual workflow definition'}\n </SheetDescription>\n </SheetHeader>\n <SheetBody className=\"gap-18\">\n <div className=\"grid w-full gap-10\">\n <Metadata label=\"Definition id\" value={definition.id} />\n <Metadata label=\"Source\" value={definition.source} />\n <Metadata label=\"Ref\" value={definition.ref ?? 'Not set'} />\n <Metadata label=\"SHA\" value={definition.sha ?? 'Not set'} />\n </div>\n <div className=\"flex w-full flex-col gap-8\">\n <Text size=\"sm\" bold>\n Normalized definition\n </Text>\n <pre className=\"max-h-[52vh] w-full overflow-auto rounded-8 border border-border-neutral-base bg-background-neutral-subtle p-12 scrollbar\">\n <Code as=\"code\" className=\"whitespace-pre text-foreground-neutral-base\">\n {normalizedJson}\n </Code>\n </pre>\n </div>\n </SheetBody>\n </>\n ) : null}\n </SheetContent>\n </Sheet>\n );\n}\n\nfunction Metadata({label, value}: {label: string; value: string}) {\n return (\n <div className=\"min-w-0 py-12 first:pt-0 last:pb-0\">\n <Text size=\"xs\" className=\"text-foreground-neutral-muted\">\n {label}\n </Text>\n <Text size=\"sm\" className=\"break-words\">\n {value}\n </Text>\n </div>\n );\n}\n\nfunction errorMessage(error: unknown, fallback: string) {\n if (error instanceof ApiError && error.message) return error.message;\n if (error instanceof Error && error.message) return error.message;\n return fallback;\n}\n"],"names":["ApiError","SourceStrip","useDefinitionsInfiniteQuery","useProjectQuery","QueryLoadError","Button","Callout","EmptyState","Icon","LoadErrorState","RelativeTime","RelativeTimeProvider","Sheet","SheetBody","SheetContent","SheetDescription","SheetHeader","SheetTitle","Skeleton","Table","TableBody","TableCell","TableHead","TableHeader","TableRow","toast","Code","Header","Text","useState","useFireManualWorkflowMutation","ProjectWorkflowsPage","projectId","ProjectWorkflowsPageInner","projectQuery","definitionsQuery","fireManual","selectedDefinition","setSelectedDefinition","runError","setRunError","definitions","data","pages","flatMap","page","sync","handleRun","definition","manual_trigger","mutateAsync","definitionId","id","success","error","message","errorMessage","div","className","isPending","isError","undefined","status","icon","title","description","query","subject","header","variant","size","connectionId","source","connection_id","externalRepositoryId","external_repository_id","WorkflowSyncAlert","WorkflowDefinitionsList","runningDefinitionId","variables","hasNextPage","isFetchingNextPage","isFetchNextPageError","onRetry","refetch","onLoadMore","fetchNextPage","onOpenDefinition","onRun","DefinitionSheet","onOpenChange","open","length","retryLabel","WorkflowEmptyState","map","runErrorMessage","isRunning","name","sourceIcon","aria-hidden","button","type","onClick","bold","config_path","value","updated_at","isLoading","role","last_error_code","last_error_message","normalizedJson","JSON","stringify","workflow_document","workflow_model","Boolean","Metadata","label","ref","sha","pre","as","fallback","Error"],"mappings":"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"}
1
+ {"version":3,"sources":["../../src/pages/project-workflows-page.tsx"],"sourcesContent":["import {ApiError} from '@shipfox/client-api';\nimport {\n type Definition,\n type DefinitionSyncSummary,\n SourceStrip,\n useDefinitionsInfiniteQuery,\n useProjectQuery,\n} from '@shipfox/client-projects';\nimport {QueryLoadError} from '@shipfox/client-ui';\nimport {Button} from '@shipfox/react-ui/button';\nimport {Callout} from '@shipfox/react-ui/callout';\nimport {EmptyState} from '@shipfox/react-ui/empty-state';\nimport {Icon, type IconName} from '@shipfox/react-ui/icon';\nimport {LoadErrorState} from '@shipfox/react-ui/load-error-state';\nimport {RelativeTime, RelativeTimeProvider} from '@shipfox/react-ui/relative-time';\nimport {\n Sheet,\n SheetBody,\n SheetContent,\n SheetDescription,\n SheetHeader,\n SheetTitle,\n} from '@shipfox/react-ui/sheet';\nimport {Skeleton} from '@shipfox/react-ui/skeleton';\nimport {\n Table,\n TableBody,\n TableCell,\n TableHead,\n TableHeader,\n TableRow,\n} from '@shipfox/react-ui/table';\nimport {toast} from '@shipfox/react-ui/toast';\nimport {Code, Header, Text} from '@shipfox/react-ui/typography';\nimport {useState} from 'react';\nimport {useFireManualWorkflowMutation} from '#hooks/api/workflow-runs.js';\n\nexport function ProjectWorkflowsPage({projectId}: {projectId: string}) {\n return (\n <RelativeTimeProvider>\n <ProjectWorkflowsPageInner projectId={projectId} />\n </RelativeTimeProvider>\n );\n}\n\nfunction ProjectWorkflowsPageInner({projectId}: {projectId: string}) {\n const projectQuery = useProjectQuery(projectId);\n const definitionsQuery = useDefinitionsInfiniteQuery(projectId);\n const fireManual = useFireManualWorkflowMutation();\n const [selectedDefinition, setSelectedDefinition] = useState<Definition | null>(null);\n const [runError, setRunError] = useState<{definitionId: string; message: string} | null>(null);\n const definitions = definitionsQuery.data?.pages.flatMap((page) => page.definitions) ?? [];\n const sync = definitionsQuery.data?.pages[0]?.sync;\n\n async function handleRun(definition: Definition) {\n setRunError(null);\n if (!definition.manualTrigger) return;\n try {\n await fireManual.mutateAsync({projectId, definitionId: definition.id});\n toast.success('Run queued');\n } catch (error) {\n const message = errorMessage(error, 'Could not queue run.');\n setRunError({definitionId: definition.id, message});\n toast.error(message);\n }\n }\n\n return (\n <div className=\"flex w-full flex-col gap-24\">\n {projectQuery.isPending ? (\n <div className=\"flex flex-col gap-12\">\n <Skeleton className=\"h-28 w-1/3\" />\n <Skeleton className=\"h-18 w-1/2\" />\n </div>\n ) : null}\n\n {projectQuery.isError && projectQuery.data === undefined ? (\n projectQuery.error instanceof ApiError && projectQuery.error.status === 404 ? (\n <EmptyState\n icon=\"errorWarningLine\"\n title=\"Project not found\"\n description=\"This project doesn't exist, or you don't have access to it.\"\n />\n ) : (\n <QueryLoadError query={projectQuery} subject=\"project\" />\n )\n ) : null}\n\n {projectQuery.data ? (\n <>\n <header className=\"flex flex-col gap-4\">\n <Header variant=\"h2\">Workflows</Header>\n <Text size=\"sm\" className=\"text-foreground-neutral-muted\">\n Synced workflow definitions for this project source.\n </Text>\n </header>\n\n <SourceStrip\n connectionId={projectQuery.data.source.connectionId}\n externalRepositoryId={projectQuery.data.source.externalRepositoryId}\n sync={sync}\n isPending={definitionsQuery.isPending}\n />\n\n <WorkflowSyncAlert sync={sync} />\n\n <WorkflowDefinitionsList\n definitions={definitions}\n isPending={definitionsQuery.isPending}\n isError={definitionsQuery.isError}\n sync={sync ?? null}\n runError={runError}\n runningDefinitionId={\n fireManual.isPending && fireManual.variables\n ? fireManual.variables.definitionId\n : null\n }\n hasNextPage={definitionsQuery.hasNextPage}\n isFetchingNextPage={definitionsQuery.isFetchingNextPage}\n isFetchNextPageError={definitionsQuery.isFetchNextPageError}\n onRetry={() => definitionsQuery.refetch()}\n onLoadMore={() => definitionsQuery.fetchNextPage()}\n onOpenDefinition={setSelectedDefinition}\n onRun={(definition) => {\n void handleRun(definition);\n }}\n />\n </>\n ) : null}\n\n <DefinitionSheet\n definition={selectedDefinition}\n onOpenChange={(open) => {\n if (!open) setSelectedDefinition(null);\n }}\n />\n </div>\n );\n}\n\nfunction WorkflowDefinitionsList({\n definitions,\n isPending,\n isError,\n sync,\n runError,\n runningDefinitionId,\n hasNextPage,\n isFetchingNextPage,\n isFetchNextPageError,\n onRetry,\n onLoadMore,\n onOpenDefinition,\n onRun,\n}: {\n definitions: Definition[];\n isPending: boolean;\n isError: boolean;\n sync: DefinitionSyncSummary | null;\n runError: {definitionId: string; message: string} | null;\n runningDefinitionId: string | null;\n hasNextPage: boolean;\n isFetchingNextPage: boolean;\n isFetchNextPageError: boolean;\n onRetry: () => void;\n onLoadMore: () => void;\n onOpenDefinition: (definition: Definition) => void;\n onRun: (definition: Definition) => void;\n}) {\n if (isPending) {\n return (\n <div className=\"flex flex-col gap-8\">\n <Skeleton className=\"h-40 w-full\" />\n <Skeleton className=\"h-40 w-full\" />\n <Skeleton className=\"h-40 w-full\" />\n </div>\n );\n }\n\n if (isError && definitions.length === 0) {\n return (\n <LoadErrorState\n title=\"Couldn't load workflows\"\n description=\"Definitions could not be loaded. Source metadata remains visible.\"\n onRetry={onRetry}\n retryLabel=\"Retry loading workflows\"\n />\n );\n }\n\n if (definitions.length === 0) {\n return <WorkflowEmptyState sync={sync} />;\n }\n\n return (\n <>\n <div className=\"hidden rounded-8 border border-border-neutral-base md:block\">\n <Table>\n <TableHeader>\n <TableRow>\n <TableHead className=\"w-40\"></TableHead>\n <TableHead>Workflow</TableHead>\n <TableHead className=\"w-180\">Updated</TableHead>\n <TableHead className=\"w-80 text-right\"></TableHead>\n </TableRow>\n </TableHeader>\n <TableBody>\n {definitions.map((definition) => {\n const runErrorMessage =\n runError?.definitionId === definition.id ? runError.message : null;\n const isRunning = runningDefinitionId === definition.id;\n\n return (\n // The workflow-name cell holds a `<button>` so the row is\n // keyboard-reachable (Tab focuses, Enter/Space activates\n // via native button semantics). The TableRow itself is no\n // longer clickable — a row-level onClick would be invisible\n // to keyboard users and require custom keydown handling.\n // The `group` class on the row still drives the Run button\n // reveal on hover or focus-within.\n <TableRow key={definition.id} className=\"group\">\n <TableCell>\n <Icon\n name={sourceIcon(definition.source)}\n className=\"size-16 text-foreground-neutral-muted\"\n aria-hidden=\"true\"\n />\n </TableCell>\n <TableCell className=\"max-w-260\">\n <div className=\"flex min-w-0 flex-col gap-2\">\n <button\n type=\"button\"\n onClick={() => onOpenDefinition(definition)}\n className=\"flex min-w-0 flex-col gap-2 text-left outline-none focus-visible:shadow-border-interactive-with-active rounded-4\"\n >\n <Text size=\"sm\" bold className=\"truncate\">\n {definition.name}\n </Text>\n <Code className=\"truncate text-foreground-neutral-muted\">\n {definition.configPath ?? 'Manual definition'}\n </Code>\n </button>\n {runErrorMessage ? (\n <Text size=\"xs\" className=\"text-tag-error-text\">\n {runErrorMessage}\n </Text>\n ) : null}\n </div>\n </TableCell>\n <TableCell className=\"text-foreground-neutral-muted\">\n <RelativeTime value={definition.updatedAt} />\n </TableCell>\n <TableCell>\n {definition.manualTrigger ? (\n <div className=\"flex justify-end opacity-0 transition-opacity group-hover:opacity-100 group-focus-within:opacity-100\">\n <Button size=\"xs\" isLoading={isRunning} onClick={() => onRun(definition)}>\n Run\n </Button>\n </div>\n ) : null}\n </TableCell>\n </TableRow>\n );\n })}\n </TableBody>\n </Table>\n </div>\n\n <div className=\"flex flex-col rounded-8 border border-border-neutral-base md:hidden\">\n {definitions.map((definition) => {\n const runErrorMessage =\n runError?.definitionId === definition.id ? runError.message : null;\n const isRunning = runningDefinitionId === definition.id;\n\n return (\n <div\n key={definition.id}\n className=\"flex flex-col gap-10 border-b border-border-neutral-base p-12 last:border-b-0\"\n >\n <button\n type=\"button\"\n className=\"flex min-w-0 items-start gap-10 text-left\"\n onClick={() => onOpenDefinition(definition)}\n >\n <Icon\n name={sourceIcon(definition.source)}\n className=\"size-16 shrink-0 text-foreground-neutral-muted\"\n aria-hidden=\"true\"\n />\n <div className=\"flex min-w-0 flex-col gap-4\">\n <Text size=\"sm\" bold className=\"break-words\">\n {definition.name}\n </Text>\n <Code className=\"break-words text-foreground-neutral-muted\">\n {definition.configPath ?? 'Manual definition'}\n </Code>\n </div>\n </button>\n <div className=\"flex items-center justify-between gap-8\">\n <Text size=\"xs\" className=\"text-foreground-neutral-muted\">\n Updated <RelativeTime value={definition.updatedAt} />\n </Text>\n {definition.manualTrigger ? (\n <Button size=\"sm\" isLoading={isRunning} onClick={() => onRun(definition)}>\n Run\n </Button>\n ) : null}\n </div>\n {runErrorMessage ? (\n <Text size=\"xs\" className=\"text-tag-error-text\">\n {runErrorMessage}\n </Text>\n ) : null}\n </div>\n );\n })}\n </div>\n\n {isFetchNextPageError ? (\n <Callout role=\"alert\" type=\"error\">\n <div className=\"flex items-center justify-between gap-12\">\n <Text size=\"sm\">Could not load more workflows.</Text>\n <Button size=\"sm\" variant=\"secondary\" onClick={onLoadMore}>\n Retry\n </Button>\n </div>\n </Callout>\n ) : null}\n\n {hasNextPage ? (\n <div className=\"flex justify-center\">\n <Button size=\"sm\" variant=\"secondary\" isLoading={isFetchingNextPage} onClick={onLoadMore}>\n Load more\n </Button>\n </div>\n ) : null}\n </>\n );\n}\n\nfunction sourceIcon(source: 'manual' | 'vcs'): IconName {\n return source === 'vcs' ? ('gitBranchLine' as IconName) : ('terminalLine' as IconName);\n}\n\nfunction WorkflowEmptyState({sync}: {sync: DefinitionSyncSummary | null}) {\n const message =\n sync?.status === 'failed' && sync.lastErrorCode === 'no-workflow-files'\n ? 'No workflow files found under .shipfox/workflows/.'\n : sync?.status === 'failed'\n ? (sync.lastErrorMessage ?? 'Workflow definitions could not be synced.')\n : sync?.status === 'syncing'\n ? 'Workflow definitions are being discovered.'\n : sync?.status === 'succeeded'\n ? 'No workflow definitions found.'\n : 'Workflow sync has not reported yet.';\n\n return <EmptyState icon=\"flowChart\" title=\"No workflows\" description={message} />;\n}\n\nfunction WorkflowSyncAlert({sync}: {sync: DefinitionSyncSummary | null | undefined}) {\n if (sync?.status !== 'failed') return null;\n\n return (\n <Callout role=\"alert\" type=\"error\">\n <div className=\"flex flex-col gap-4\">\n <Text size=\"sm\" bold>\n Workflow sync failed\n </Text>\n <Text size=\"sm\">\n {sync.lastErrorMessage ?? 'The latest workflow sync failed before definitions updated.'}\n </Text>\n </div>\n </Callout>\n );\n}\n\nfunction DefinitionSheet({\n definition,\n onOpenChange,\n}: {\n definition: Definition | null;\n onOpenChange: (open: boolean) => void;\n}) {\n const normalizedJson = definition\n ? JSON.stringify(\n {\n workflow_document: definition.workflowDocument,\n workflow_model: definition.workflowModel,\n },\n null,\n 2,\n )\n : '';\n\n return (\n <Sheet open={Boolean(definition)} onOpenChange={onOpenChange}>\n <SheetContent className=\"w-full sm:max-w-[560px]\">\n {definition ? (\n <>\n <SheetHeader>\n <SheetTitle>{definition.name}</SheetTitle>\n <SheetDescription>\n {definition.configPath ?? 'Manual workflow definition'}\n </SheetDescription>\n </SheetHeader>\n <SheetBody className=\"gap-18\">\n <div className=\"grid w-full gap-10\">\n <Metadata label=\"Definition id\" value={definition.id} />\n <Metadata label=\"Source\" value={definition.source} />\n <Metadata label=\"Ref\" value={definition.ref ?? 'Not set'} />\n <Metadata label=\"SHA\" value={definition.sha ?? 'Not set'} />\n </div>\n <div className=\"flex w-full flex-col gap-8\">\n <Text size=\"sm\" bold>\n Normalized definition\n </Text>\n <pre className=\"max-h-[52vh] w-full overflow-auto rounded-8 border border-border-neutral-base bg-background-neutral-subtle p-12 scrollbar\">\n <Code as=\"code\" className=\"whitespace-pre text-foreground-neutral-base\">\n {normalizedJson}\n </Code>\n </pre>\n </div>\n </SheetBody>\n </>\n ) : null}\n </SheetContent>\n </Sheet>\n );\n}\n\nfunction Metadata({label, value}: {label: string; value: string}) {\n return (\n <div className=\"min-w-0 py-12 first:pt-0 last:pb-0\">\n <Text size=\"xs\" className=\"text-foreground-neutral-muted\">\n {label}\n </Text>\n <Text size=\"sm\" className=\"break-words\">\n {value}\n </Text>\n </div>\n );\n}\n\nfunction errorMessage(error: unknown, fallback: string) {\n if (error instanceof ApiError && error.message) return error.message;\n if (error instanceof Error && error.message) return error.message;\n return fallback;\n}\n"],"names":["ApiError","SourceStrip","useDefinitionsInfiniteQuery","useProjectQuery","QueryLoadError","Button","Callout","EmptyState","Icon","LoadErrorState","RelativeTime","RelativeTimeProvider","Sheet","SheetBody","SheetContent","SheetDescription","SheetHeader","SheetTitle","Skeleton","Table","TableBody","TableCell","TableHead","TableHeader","TableRow","toast","Code","Header","Text","useState","useFireManualWorkflowMutation","ProjectWorkflowsPage","projectId","ProjectWorkflowsPageInner","projectQuery","definitionsQuery","fireManual","selectedDefinition","setSelectedDefinition","runError","setRunError","definitions","data","pages","flatMap","page","sync","handleRun","definition","manualTrigger","mutateAsync","definitionId","id","success","error","message","errorMessage","div","className","isPending","isError","undefined","status","icon","title","description","query","subject","header","variant","size","connectionId","source","externalRepositoryId","WorkflowSyncAlert","WorkflowDefinitionsList","runningDefinitionId","variables","hasNextPage","isFetchingNextPage","isFetchNextPageError","onRetry","refetch","onLoadMore","fetchNextPage","onOpenDefinition","onRun","DefinitionSheet","onOpenChange","open","length","retryLabel","WorkflowEmptyState","map","runErrorMessage","isRunning","name","sourceIcon","aria-hidden","button","type","onClick","bold","configPath","value","updatedAt","isLoading","role","lastErrorCode","lastErrorMessage","normalizedJson","JSON","stringify","workflow_document","workflowDocument","workflow_model","workflowModel","Boolean","Metadata","label","ref","sha","pre","as","fallback","Error"],"mappings":"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"}
@@ -1,8 +1,10 @@
1
+ import { type WorkflowRunsSearch } from '#routes/inputs.js';
1
2
  interface WorkflowRunPageProps {
2
3
  workspaceId: string;
3
4
  projectId: string;
4
5
  workflowRunId?: string | undefined;
6
+ search?: WorkflowRunsSearch;
5
7
  }
6
- export declare function WorkflowRunPage({ workspaceId, projectId, workflowRunId }: WorkflowRunPageProps): import("react").JSX.Element;
8
+ export declare function WorkflowRunPage({ workspaceId, projectId, workflowRunId, search, }: WorkflowRunPageProps): import("react").JSX.Element;
7
9
  export {};
8
10
  //# sourceMappingURL=workflow-run-page.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"workflow-run-page.d.ts","sourceRoot":"","sources":["../../src/pages/workflow-run-page.tsx"],"names":[],"mappings":"AAaA,UAAU,oBAAoB;IAC5B,WAAW,EAAE,MAAM,CAAC;IACpB,SAAS,EAAE,MAAM,CAAC;IAClB,aAAa,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;CACpC;AAoCD,wBAAgB,eAAe,CAAC,EAAC,WAAW,EAAE,SAAS,EAAE,aAAa,EAAC,EAAE,oBAAoB,+BAmC5F"}
1
+ {"version":3,"file":"workflow-run-page.d.ts","sourceRoot":"","sources":["../../src/pages/workflow-run-page.tsx"],"names":[],"mappings":"AAMA,OAAO,EAAC,KAAK,kBAAkB,EAA0B,MAAM,mBAAmB,CAAC;AAGnF,UAAU,oBAAoB;IAC5B,WAAW,EAAE,MAAM,CAAC;IACpB,SAAS,EAAE,MAAM,CAAC;IAClB,aAAa,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACnC,MAAM,CAAC,EAAE,kBAAkB,CAAC;CAC7B;AAoCD,wBAAgB,eAAe,CAAC,EAC9B,WAAW,EACX,SAAS,EACT,aAAa,EACb,MAAW,GACZ,EAAE,oBAAoB,+BAsCtB"}
@@ -1,10 +1,10 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
- import { useNavigate, useSearch } from '@tanstack/react-router';
2
+ import { useNavigate } from '@tanstack/react-router';
3
3
  import { useCallback, useEffect } from 'react';
4
4
  import { WorkflowRunList } from '#components/workflow-run-list/workflow-run-list.js';
5
5
  import { WorkflowRunView } from '#components/workflow-run-view/index.js';
6
- import { withoutWorkflowRunSelectionSearch, withWorkflowRunSelectionSearch, workflowRunSelectionFromSearch } from '#core/workflow-run-url-state.js';
7
6
  import { useWorkflowRunsInfiniteQuery } from '#hooks/api/workflow-runs.js';
7
+ import { workflowRunSearchParams } from '#routes/inputs.js';
8
8
  import { WorkflowRunFirstTimeUse } from './workflow-run-first-time-use.js';
9
9
  /**
10
10
  * Resolve which surface the runs path should show from a single read of the runs list:
@@ -12,7 +12,7 @@ import { WorkflowRunFirstTimeUse } from './workflow-run-first-time-use.js';
12
12
  * never empty (navigation happens in an effect since it mutates history);
13
13
  * - report `hasNoRuns` once the list has loaded with zero runs, so a brand-new project lands
14
14
  * on the first-time-use surface instead of an empty rail and a perpetual detail skeleton.
15
- */ function useWorkflowRunPageTarget(workspaceId, projectId, workflowRunId) {
15
+ */ function useWorkflowRunPageTarget(workspaceId, projectId, workflowRunId, search) {
16
16
  const navigate = useNavigate();
17
17
  const { data, isPending } = useWorkflowRunsInfiniteQuery(projectId, {});
18
18
  const firstWorkflowRunId = data?.pages[0]?.runs[0]?.id;
@@ -29,7 +29,7 @@ import { WorkflowRunFirstTimeUse } from './workflow-run-first-time-use.js';
29
29
  pid: projectId,
30
30
  workflowRunId: firstWorkflowRunId
31
31
  },
32
- search: (previous)=>withoutWorkflowRunSelectionSearch(previous),
32
+ search: workflowRunSearchParams(search, {}),
33
33
  replace: true
34
34
  });
35
35
  }, [
@@ -38,25 +38,24 @@ import { WorkflowRunFirstTimeUse } from './workflow-run-first-time-use.js';
38
38
  projectId,
39
39
  workflowRunId,
40
40
  isLoaded,
41
- firstWorkflowRunId
41
+ firstWorkflowRunId,
42
+ search
42
43
  ]);
43
44
  return {
44
45
  hasNoRuns: isLoaded && firstWorkflowRunId === undefined
45
46
  };
46
47
  }
47
- export function WorkflowRunPage({ workspaceId, projectId, workflowRunId }) {
48
- const { hasNoRuns } = useWorkflowRunPageTarget(workspaceId, projectId, workflowRunId);
48
+ export function WorkflowRunPage({ workspaceId, projectId, workflowRunId, search = {} }) {
49
+ const { hasNoRuns } = useWorkflowRunPageTarget(workspaceId, projectId, workflowRunId, search);
49
50
  const navigate = useNavigate();
50
- const search = useSearch({
51
- strict: false
52
- });
53
- const selection = workflowRunSelectionFromSearch(search);
51
+ const selection = search;
54
52
  const onSelectionChange = useCallback((nextSelection)=>{
55
53
  navigate({
56
- search: (previous)=>withWorkflowRunSelectionSearch(previous, nextSelection)
54
+ search: workflowRunSearchParams(search, nextSelection)
57
55
  });
58
56
  }, [
59
- navigate
57
+ navigate,
58
+ search
60
59
  ]);
61
60
  if (!workflowRunId && hasNoRuns) {
62
61
  return /*#__PURE__*/ _jsx(WorkflowRunFirstTimeUse, {});
@@ -67,7 +66,15 @@ export function WorkflowRunPage({ workspaceId, projectId, workflowRunId }) {
67
66
  /*#__PURE__*/ _jsx(WorkflowRunList, {
68
67
  workspaceId: workspaceId,
69
68
  projectId: projectId,
70
- selectedWorkflowRunId: workflowRunId
69
+ selectedWorkflowRunId: workflowRunId,
70
+ search: search.search ?? '',
71
+ statusFilter: search.status ?? 'all',
72
+ onFiltersChange: (filters)=>navigate({
73
+ search: workflowRunSearchParams({
74
+ ...search,
75
+ ...filters
76
+ })
77
+ })
71
78
  }),
72
79
  /*#__PURE__*/ _jsx(WorkflowRunView, {
73
80
  workspaceId: workspaceId,
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/pages/workflow-run-page.tsx"],"sourcesContent":["import {useNavigate, useSearch} from '@tanstack/react-router';\nimport {useCallback, useEffect} from 'react';\nimport {WorkflowRunList} from '#components/workflow-run-list/workflow-run-list.js';\nimport {WorkflowRunView} from '#components/workflow-run-view/index.js';\nimport {\n type WorkflowRunSelectionInput,\n withoutWorkflowRunSelectionSearch,\n withWorkflowRunSelectionSearch,\n workflowRunSelectionFromSearch,\n} from '#core/workflow-run-url-state.js';\nimport {useWorkflowRunsInfiniteQuery} from '#hooks/api/workflow-runs.js';\nimport {WorkflowRunFirstTimeUse} from './workflow-run-first-time-use.js';\n\ninterface WorkflowRunPageProps {\n workspaceId: string;\n projectId: string;\n workflowRunId?: string | undefined;\n}\n\n/**\n * Resolve which surface the runs path should show from a single read of the runs list:\n * - when opened without a workflow run id, point the URL at the most recent run so the detail pane is\n * never empty (navigation happens in an effect since it mutates history);\n * - report `hasNoRuns` once the list has loaded with zero runs, so a brand-new project lands\n * on the first-time-use surface instead of an empty rail and a perpetual detail skeleton.\n */\nfunction useWorkflowRunPageTarget(\n workspaceId: string,\n projectId: string,\n workflowRunId: string | undefined,\n) {\n const navigate = useNavigate();\n const {data, isPending} = useWorkflowRunsInfiniteQuery(projectId, {});\n const firstWorkflowRunId = data?.pages[0]?.runs[0]?.id;\n // Gate on data presence, not `!isError`: a transient refetch error after a prior success\n // keeps `data`, so the redirect (and the no-runs surface) still resolve from it instead of\n // stalling on the rail while active-run polling hits a blip.\n const isLoaded = !isPending && data !== undefined;\n\n useEffect(() => {\n if (workflowRunId || !isLoaded || !firstWorkflowRunId) return;\n navigate({\n to: '/workspaces/$wid/projects/$pid/runs/$workflowRunId',\n params: {wid: workspaceId, pid: projectId, workflowRunId: firstWorkflowRunId},\n search: ((previous: Record<string, unknown>) =>\n withoutWorkflowRunSelectionSearch(previous)) as never,\n replace: true,\n });\n }, [navigate, workspaceId, projectId, workflowRunId, isLoaded, firstWorkflowRunId]);\n\n return {hasNoRuns: isLoaded && firstWorkflowRunId === undefined};\n}\n\nexport function WorkflowRunPage({workspaceId, projectId, workflowRunId}: WorkflowRunPageProps) {\n const {hasNoRuns} = useWorkflowRunPageTarget(workspaceId, projectId, workflowRunId);\n const navigate = useNavigate();\n const search = useSearch({strict: false}) as Record<string, unknown>;\n const selection = workflowRunSelectionFromSearch(search);\n const onSelectionChange = useCallback(\n (nextSelection: WorkflowRunSelectionInput) => {\n navigate({\n search: ((previous: Record<string, unknown>) =>\n withWorkflowRunSelectionSearch(previous, nextSelection)) as never,\n });\n },\n [navigate],\n );\n\n if (!workflowRunId && hasNoRuns) {\n return <WorkflowRunFirstTimeUse />;\n }\n\n return (\n <div className=\"flex min-h-0 flex-1 overflow-hidden\">\n <WorkflowRunList\n workspaceId={workspaceId}\n projectId={projectId}\n selectedWorkflowRunId={workflowRunId}\n />\n <WorkflowRunView\n workspaceId={workspaceId}\n projectId={projectId}\n workflowRunId={workflowRunId}\n selection={selection}\n onSelectionChange={onSelectionChange}\n />\n </div>\n );\n}\n"],"names":["useNavigate","useSearch","useCallback","useEffect","WorkflowRunList","WorkflowRunView","withoutWorkflowRunSelectionSearch","withWorkflowRunSelectionSearch","workflowRunSelectionFromSearch","useWorkflowRunsInfiniteQuery","WorkflowRunFirstTimeUse","useWorkflowRunPageTarget","workspaceId","projectId","workflowRunId","navigate","data","isPending","firstWorkflowRunId","pages","runs","id","isLoaded","undefined","to","params","wid","pid","search","previous","replace","hasNoRuns","WorkflowRunPage","strict","selection","onSelectionChange","nextSelection","div","className","selectedWorkflowRunId"],"mappings":";AAAA,SAAQA,WAAW,EAAEC,SAAS,QAAO,yBAAyB;AAC9D,SAAQC,WAAW,EAAEC,SAAS,QAAO,QAAQ;AAC7C,SAAQC,eAAe,QAAO,qDAAqD;AACnF,SAAQC,eAAe,QAAO,yCAAyC;AACvE,SAEEC,iCAAiC,EACjCC,8BAA8B,EAC9BC,8BAA8B,QACzB,kCAAkC;AACzC,SAAQC,4BAA4B,QAAO,8BAA8B;AACzE,SAAQC,uBAAuB,QAAO,mCAAmC;AAQzE;;;;;;CAMC,GACD,SAASC,yBACPC,WAAmB,EACnBC,SAAiB,EACjBC,aAAiC;IAEjC,MAAMC,WAAWf;IACjB,MAAM,EAACgB,IAAI,EAAEC,SAAS,EAAC,GAAGR,6BAA6BI,WAAW,CAAC;IACnE,MAAMK,qBAAqBF,MAAMG,KAAK,CAAC,EAAE,EAAEC,IAAI,CAAC,EAAE,EAAEC;IACpD,yFAAyF;IACzF,2FAA2F;IAC3F,6DAA6D;IAC7D,MAAMC,WAAW,CAACL,aAAaD,SAASO;IAExCpB,UAAU;QACR,IAAIW,iBAAiB,CAACQ,YAAY,CAACJ,oBAAoB;QACvDH,SAAS;YACPS,IAAI;YACJC,QAAQ;gBAACC,KAAKd;gBAAae,KAAKd;gBAAWC,eAAeI;YAAkB;YAC5EU,QAAS,CAACC,WACRvB,kCAAkCuB;YACpCC,SAAS;QACX;IACF,GAAG;QAACf;QAAUH;QAAaC;QAAWC;QAAeQ;QAAUJ;KAAmB;IAElF,OAAO;QAACa,WAAWT,YAAYJ,uBAAuBK;IAAS;AACjE;AAEA,OAAO,SAASS,gBAAgB,EAACpB,WAAW,EAAEC,SAAS,EAAEC,aAAa,EAAuB;IAC3F,MAAM,EAACiB,SAAS,EAAC,GAAGpB,yBAAyBC,aAAaC,WAAWC;IACrE,MAAMC,WAAWf;IACjB,MAAM4B,SAAS3B,UAAU;QAACgC,QAAQ;IAAK;IACvC,MAAMC,YAAY1B,+BAA+BoB;IACjD,MAAMO,oBAAoBjC,YACxB,CAACkC;QACCrB,SAAS;YACPa,QAAS,CAACC,WACRtB,+BAA+BsB,UAAUO;QAC7C;IACF,GACA;QAACrB;KAAS;IAGZ,IAAI,CAACD,iBAAiBiB,WAAW;QAC/B,qBAAO,KAACrB;IACV;IAEA,qBACE,MAAC2B;QAAIC,WAAU;;0BACb,KAAClC;gBACCQ,aAAaA;gBACbC,WAAWA;gBACX0B,uBAAuBzB;;0BAEzB,KAACT;gBACCO,aAAaA;gBACbC,WAAWA;gBACXC,eAAeA;gBACfoB,WAAWA;gBACXC,mBAAmBA;;;;AAI3B"}
1
+ {"version":3,"sources":["../../src/pages/workflow-run-page.tsx"],"sourcesContent":["import {useNavigate} from '@tanstack/react-router';\nimport {useCallback, useEffect} from 'react';\nimport {WorkflowRunList} from '#components/workflow-run-list/workflow-run-list.js';\nimport {WorkflowRunView} from '#components/workflow-run-view/index.js';\nimport type {WorkflowRunSelectionInput} from '#core/workflow-run-url-state.js';\nimport {useWorkflowRunsInfiniteQuery} from '#hooks/api/workflow-runs.js';\nimport {type WorkflowRunsSearch, workflowRunSearchParams} from '#routes/inputs.js';\nimport {WorkflowRunFirstTimeUse} from './workflow-run-first-time-use.js';\n\ninterface WorkflowRunPageProps {\n workspaceId: string;\n projectId: string;\n workflowRunId?: string | undefined;\n search?: WorkflowRunsSearch;\n}\n\n/**\n * Resolve which surface the runs path should show from a single read of the runs list:\n * - when opened without a workflow run id, point the URL at the most recent run so the detail pane is\n * never empty (navigation happens in an effect since it mutates history);\n * - report `hasNoRuns` once the list has loaded with zero runs, so a brand-new project lands\n * on the first-time-use surface instead of an empty rail and a perpetual detail skeleton.\n */\nfunction useWorkflowRunPageTarget(\n workspaceId: string,\n projectId: string,\n workflowRunId: string | undefined,\n search: WorkflowRunsSearch,\n) {\n const navigate = useNavigate();\n const {data, isPending} = useWorkflowRunsInfiniteQuery(projectId, {});\n const firstWorkflowRunId = data?.pages[0]?.runs[0]?.id;\n // Gate on data presence, not `!isError`: a transient refetch error after a prior success\n // keeps `data`, so the redirect (and the no-runs surface) still resolve from it instead of\n // stalling on the rail while active-run polling hits a blip.\n const isLoaded = !isPending && data !== undefined;\n\n useEffect(() => {\n if (workflowRunId || !isLoaded || !firstWorkflowRunId) return;\n navigate({\n to: '/workspaces/$wid/projects/$pid/runs/$workflowRunId',\n params: {wid: workspaceId, pid: projectId, workflowRunId: firstWorkflowRunId},\n search: workflowRunSearchParams(search, {}),\n replace: true,\n });\n }, [navigate, workspaceId, projectId, workflowRunId, isLoaded, firstWorkflowRunId, search]);\n\n return {hasNoRuns: isLoaded && firstWorkflowRunId === undefined};\n}\n\nexport function WorkflowRunPage({\n workspaceId,\n projectId,\n workflowRunId,\n search = {},\n}: WorkflowRunPageProps) {\n const {hasNoRuns} = useWorkflowRunPageTarget(workspaceId, projectId, workflowRunId, search);\n const navigate = useNavigate();\n const selection: WorkflowRunSelectionInput = search;\n const onSelectionChange = useCallback(\n (nextSelection: WorkflowRunSelectionInput) => {\n navigate({\n search: workflowRunSearchParams(search, nextSelection) as never,\n });\n },\n [navigate, search],\n );\n\n if (!workflowRunId && hasNoRuns) {\n return <WorkflowRunFirstTimeUse />;\n }\n\n return (\n <div className=\"flex min-h-0 flex-1 overflow-hidden\">\n <WorkflowRunList\n workspaceId={workspaceId}\n projectId={projectId}\n selectedWorkflowRunId={workflowRunId}\n search={search.search ?? ''}\n statusFilter={search.status ?? 'all'}\n onFiltersChange={(filters) =>\n navigate({search: workflowRunSearchParams({...search, ...filters}) as never})\n }\n />\n <WorkflowRunView\n workspaceId={workspaceId}\n projectId={projectId}\n workflowRunId={workflowRunId}\n selection={selection}\n onSelectionChange={onSelectionChange}\n />\n </div>\n );\n}\n"],"names":["useNavigate","useCallback","useEffect","WorkflowRunList","WorkflowRunView","useWorkflowRunsInfiniteQuery","workflowRunSearchParams","WorkflowRunFirstTimeUse","useWorkflowRunPageTarget","workspaceId","projectId","workflowRunId","search","navigate","data","isPending","firstWorkflowRunId","pages","runs","id","isLoaded","undefined","to","params","wid","pid","replace","hasNoRuns","WorkflowRunPage","selection","onSelectionChange","nextSelection","div","className","selectedWorkflowRunId","statusFilter","status","onFiltersChange","filters"],"mappings":";AAAA,SAAQA,WAAW,QAAO,yBAAyB;AACnD,SAAQC,WAAW,EAAEC,SAAS,QAAO,QAAQ;AAC7C,SAAQC,eAAe,QAAO,qDAAqD;AACnF,SAAQC,eAAe,QAAO,yCAAyC;AAEvE,SAAQC,4BAA4B,QAAO,8BAA8B;AACzE,SAAiCC,uBAAuB,QAAO,oBAAoB;AACnF,SAAQC,uBAAuB,QAAO,mCAAmC;AASzE;;;;;;CAMC,GACD,SAASC,yBACPC,WAAmB,EACnBC,SAAiB,EACjBC,aAAiC,EACjCC,MAA0B;IAE1B,MAAMC,WAAWb;IACjB,MAAM,EAACc,IAAI,EAAEC,SAAS,EAAC,GAAGV,6BAA6BK,WAAW,CAAC;IACnE,MAAMM,qBAAqBF,MAAMG,KAAK,CAAC,EAAE,EAAEC,IAAI,CAAC,EAAE,EAAEC;IACpD,yFAAyF;IACzF,2FAA2F;IAC3F,6DAA6D;IAC7D,MAAMC,WAAW,CAACL,aAAaD,SAASO;IAExCnB,UAAU;QACR,IAAIS,iBAAiB,CAACS,YAAY,CAACJ,oBAAoB;QACvDH,SAAS;YACPS,IAAI;YACJC,QAAQ;gBAACC,KAAKf;gBAAagB,KAAKf;gBAAWC,eAAeK;YAAkB;YAC5EJ,QAAQN,wBAAwBM,QAAQ,CAAC;YACzCc,SAAS;QACX;IACF,GAAG;QAACb;QAAUJ;QAAaC;QAAWC;QAAeS;QAAUJ;QAAoBJ;KAAO;IAE1F,OAAO;QAACe,WAAWP,YAAYJ,uBAAuBK;IAAS;AACjE;AAEA,OAAO,SAASO,gBAAgB,EAC9BnB,WAAW,EACXC,SAAS,EACTC,aAAa,EACbC,SAAS,CAAC,CAAC,EACU;IACrB,MAAM,EAACe,SAAS,EAAC,GAAGnB,yBAAyBC,aAAaC,WAAWC,eAAeC;IACpF,MAAMC,WAAWb;IACjB,MAAM6B,YAAuCjB;IAC7C,MAAMkB,oBAAoB7B,YACxB,CAAC8B;QACClB,SAAS;YACPD,QAAQN,wBAAwBM,QAAQmB;QAC1C;IACF,GACA;QAAClB;QAAUD;KAAO;IAGpB,IAAI,CAACD,iBAAiBgB,WAAW;QAC/B,qBAAO,KAACpB;IACV;IAEA,qBACE,MAACyB;QAAIC,WAAU;;0BACb,KAAC9B;gBACCM,aAAaA;gBACbC,WAAWA;gBACXwB,uBAAuBvB;gBACvBC,QAAQA,OAAOA,MAAM,IAAI;gBACzBuB,cAAcvB,OAAOwB,MAAM,IAAI;gBAC/BC,iBAAiB,CAACC,UAChBzB,SAAS;wBAACD,QAAQN,wBAAwB;4BAAC,GAAGM,MAAM;4BAAE,GAAG0B,OAAO;wBAAA;oBAAW;;0BAG/E,KAAClC;gBACCK,aAAaA;gBACbC,WAAWA;gBACXC,eAAeA;gBACfkB,WAAWA;gBACXC,mBAAmBA;;;;AAI3B"}
@@ -0,0 +1,22 @@
1
+ import type { WorkflowRunListStatusFilter } from '#components/workflow-run-list/types.js';
2
+ import type { WorkflowRunSelectionInput } from '#core/workflow-run-url-state.js';
3
+ export interface WorkflowRunsSearch extends WorkflowRunSelectionInput {
4
+ search?: string;
5
+ status?: WorkflowRunListStatusFilter;
6
+ }
7
+ export declare function validateWorkflowRunsSearch(input: Record<string, unknown>): WorkflowRunsSearch;
8
+ export declare function workflowRunSearchParams(search: WorkflowRunsSearch, selection?: WorkflowRunSelectionInput): {
9
+ runAttempt?: string;
10
+ stepAttempt?: string;
11
+ step?: string;
12
+ jobExecution?: string;
13
+ job?: string;
14
+ status?: "running" | "failed";
15
+ search?: string;
16
+ };
17
+ export declare function workflowRouteParams(input: Record<string, unknown>): {
18
+ wid: string;
19
+ pid: string;
20
+ workflowRunId?: string;
21
+ };
22
+ //# sourceMappingURL=inputs.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"inputs.d.ts","sourceRoot":"","sources":["../../src/routes/inputs.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAC,2BAA2B,EAAC,MAAM,wCAAwC,CAAC;AACxF,OAAO,KAAK,EAAC,yBAAyB,EAAC,MAAM,iCAAiC,CAAC;AAE/E,MAAM,WAAW,kBAAmB,SAAQ,yBAAyB;IACnE,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,2BAA2B,CAAC;CACtC;AAED,wBAAgB,0BAA0B,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,kBAAkB,CAa7F;AAED,wBAAgB,uBAAuB,CACrC,MAAM,EAAE,kBAAkB,EAC1B,SAAS,GAAE,yBAAkC;;;;;;;;EAW9C;AAED,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG;IACnE,GAAG,EAAE,MAAM,CAAC;IACZ,GAAG,EAAE,MAAM,CAAC;IACZ,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB,CAMA"}
@@ -0,0 +1,76 @@
1
+ export function validateWorkflowRunsSearch(input) {
2
+ const search = string(input.search);
3
+ const status = input.status === 'failed' || input.status === 'running' ? input.status : 'all';
4
+ const runAttempt = positiveInteger(input.runAttempt);
5
+ return {
6
+ ...search ? {
7
+ search
8
+ } : {},
9
+ ...status === 'all' ? {} : {
10
+ status
11
+ },
12
+ ...string(input.job) ? {
13
+ jobId: string(input.job)
14
+ } : {},
15
+ ...string(input.jobExecution) ? {
16
+ jobExecutionId: string(input.jobExecution)
17
+ } : {},
18
+ ...string(input.step) ? {
19
+ stepId: string(input.step)
20
+ } : {},
21
+ ...string(input.stepAttempt) ? {
22
+ stepAttemptId: string(input.stepAttempt)
23
+ } : {},
24
+ ...runAttempt ? {
25
+ runAttempt
26
+ } : {}
27
+ };
28
+ }
29
+ export function workflowRunSearchParams(search, selection = search) {
30
+ return {
31
+ ...search.search ? {
32
+ search: search.search
33
+ } : {},
34
+ ...search.status && search.status !== 'all' ? {
35
+ status: search.status
36
+ } : {},
37
+ ...selection.jobId ? {
38
+ job: selection.jobId
39
+ } : {},
40
+ ...selection.jobExecutionId ? {
41
+ jobExecution: selection.jobExecutionId
42
+ } : {},
43
+ ...selection.stepId ? {
44
+ step: selection.stepId
45
+ } : {},
46
+ ...selection.stepAttemptId ? {
47
+ stepAttempt: selection.stepAttemptId
48
+ } : {},
49
+ ...selection.runAttempt ? {
50
+ runAttempt: String(selection.runAttempt)
51
+ } : {}
52
+ };
53
+ }
54
+ export function workflowRouteParams(input) {
55
+ const wid = string(input.wid);
56
+ const pid = string(input.pid);
57
+ if (!wid || !pid) throw new Error('Workflow route is missing required path parameters.');
58
+ const workflowRunId = string(input.workflowRunId);
59
+ return workflowRunId ? {
60
+ wid,
61
+ pid,
62
+ workflowRunId
63
+ } : {
64
+ wid,
65
+ pid
66
+ };
67
+ }
68
+ function string(value) {
69
+ return typeof value === 'string' && value.length > 0 ? value : undefined;
70
+ }
71
+ function positiveInteger(value) {
72
+ const number = typeof value === 'string' ? Number(value) : value;
73
+ return typeof number === 'number' && Number.isInteger(number) && number > 0 ? number : undefined;
74
+ }
75
+
76
+ //# sourceMappingURL=inputs.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../src/routes/inputs.ts"],"sourcesContent":["import type {WorkflowRunListStatusFilter} from '#components/workflow-run-list/types.js';\nimport type {WorkflowRunSelectionInput} from '#core/workflow-run-url-state.js';\n\nexport interface WorkflowRunsSearch extends WorkflowRunSelectionInput {\n search?: string;\n status?: WorkflowRunListStatusFilter;\n}\n\nexport function validateWorkflowRunsSearch(input: Record<string, unknown>): WorkflowRunsSearch {\n const search = string(input.search);\n const status = input.status === 'failed' || input.status === 'running' ? input.status : 'all';\n const runAttempt = positiveInteger(input.runAttempt);\n return {\n ...(search ? {search} : {}),\n ...(status === 'all' ? {} : {status}),\n ...(string(input.job) ? {jobId: string(input.job)} : {}),\n ...(string(input.jobExecution) ? {jobExecutionId: string(input.jobExecution)} : {}),\n ...(string(input.step) ? {stepId: string(input.step)} : {}),\n ...(string(input.stepAttempt) ? {stepAttemptId: string(input.stepAttempt)} : {}),\n ...(runAttempt ? {runAttempt} : {}),\n };\n}\n\nexport function workflowRunSearchParams(\n search: WorkflowRunsSearch,\n selection: WorkflowRunSelectionInput = search,\n) {\n return {\n ...(search.search ? {search: search.search} : {}),\n ...(search.status && search.status !== 'all' ? {status: search.status} : {}),\n ...(selection.jobId ? {job: selection.jobId} : {}),\n ...(selection.jobExecutionId ? {jobExecution: selection.jobExecutionId} : {}),\n ...(selection.stepId ? {step: selection.stepId} : {}),\n ...(selection.stepAttemptId ? {stepAttempt: selection.stepAttemptId} : {}),\n ...(selection.runAttempt ? {runAttempt: String(selection.runAttempt)} : {}),\n };\n}\n\nexport function workflowRouteParams(input: Record<string, unknown>): {\n wid: string;\n pid: string;\n workflowRunId?: string;\n} {\n const wid = string(input.wid);\n const pid = string(input.pid);\n if (!wid || !pid) throw new Error('Workflow route is missing required path parameters.');\n const workflowRunId = string(input.workflowRunId);\n return workflowRunId ? {wid, pid, workflowRunId} : {wid, pid};\n}\n\nfunction string(value: unknown): string | undefined {\n return typeof value === 'string' && value.length > 0 ? value : undefined;\n}\n\nfunction positiveInteger(value: unknown): number | undefined {\n const number = typeof value === 'string' ? Number(value) : value;\n return typeof number === 'number' && Number.isInteger(number) && number > 0 ? number : undefined;\n}\n"],"names":["validateWorkflowRunsSearch","input","search","string","status","runAttempt","positiveInteger","job","jobId","jobExecution","jobExecutionId","step","stepId","stepAttempt","stepAttemptId","workflowRunSearchParams","selection","String","workflowRouteParams","wid","pid","Error","workflowRunId","value","length","undefined","number","Number","isInteger"],"mappings":"AAQA,OAAO,SAASA,2BAA2BC,KAA8B;IACvE,MAAMC,SAASC,OAAOF,MAAMC,MAAM;IAClC,MAAME,SAASH,MAAMG,MAAM,KAAK,YAAYH,MAAMG,MAAM,KAAK,YAAYH,MAAMG,MAAM,GAAG;IACxF,MAAMC,aAAaC,gBAAgBL,MAAMI,UAAU;IACnD,OAAO;QACL,GAAIH,SAAS;YAACA;QAAM,IAAI,CAAC,CAAC;QAC1B,GAAIE,WAAW,QAAQ,CAAC,IAAI;YAACA;QAAM,CAAC;QACpC,GAAID,OAAOF,MAAMM,GAAG,IAAI;YAACC,OAAOL,OAAOF,MAAMM,GAAG;QAAC,IAAI,CAAC,CAAC;QACvD,GAAIJ,OAAOF,MAAMQ,YAAY,IAAI;YAACC,gBAAgBP,OAAOF,MAAMQ,YAAY;QAAC,IAAI,CAAC,CAAC;QAClF,GAAIN,OAAOF,MAAMU,IAAI,IAAI;YAACC,QAAQT,OAAOF,MAAMU,IAAI;QAAC,IAAI,CAAC,CAAC;QAC1D,GAAIR,OAAOF,MAAMY,WAAW,IAAI;YAACC,eAAeX,OAAOF,MAAMY,WAAW;QAAC,IAAI,CAAC,CAAC;QAC/E,GAAIR,aAAa;YAACA;QAAU,IAAI,CAAC,CAAC;IACpC;AACF;AAEA,OAAO,SAASU,wBACdb,MAA0B,EAC1Bc,YAAuCd,MAAM;IAE7C,OAAO;QACL,GAAIA,OAAOA,MAAM,GAAG;YAACA,QAAQA,OAAOA,MAAM;QAAA,IAAI,CAAC,CAAC;QAChD,GAAIA,OAAOE,MAAM,IAAIF,OAAOE,MAAM,KAAK,QAAQ;YAACA,QAAQF,OAAOE,MAAM;QAAA,IAAI,CAAC,CAAC;QAC3E,GAAIY,UAAUR,KAAK,GAAG;YAACD,KAAKS,UAAUR,KAAK;QAAA,IAAI,CAAC,CAAC;QACjD,GAAIQ,UAAUN,cAAc,GAAG;YAACD,cAAcO,UAAUN,cAAc;QAAA,IAAI,CAAC,CAAC;QAC5E,GAAIM,UAAUJ,MAAM,GAAG;YAACD,MAAMK,UAAUJ,MAAM;QAAA,IAAI,CAAC,CAAC;QACpD,GAAII,UAAUF,aAAa,GAAG;YAACD,aAAaG,UAAUF,aAAa;QAAA,IAAI,CAAC,CAAC;QACzE,GAAIE,UAAUX,UAAU,GAAG;YAACA,YAAYY,OAAOD,UAAUX,UAAU;QAAC,IAAI,CAAC,CAAC;IAC5E;AACF;AAEA,OAAO,SAASa,oBAAoBjB,KAA8B;IAKhE,MAAMkB,MAAMhB,OAAOF,MAAMkB,GAAG;IAC5B,MAAMC,MAAMjB,OAAOF,MAAMmB,GAAG;IAC5B,IAAI,CAACD,OAAO,CAACC,KAAK,MAAM,IAAIC,MAAM;IAClC,MAAMC,gBAAgBnB,OAAOF,MAAMqB,aAAa;IAChD,OAAOA,gBAAgB;QAACH;QAAKC;QAAKE;IAAa,IAAI;QAACH;QAAKC;IAAG;AAC9D;AAEA,SAASjB,OAAOoB,KAAc;IAC5B,OAAO,OAAOA,UAAU,YAAYA,MAAMC,MAAM,GAAG,IAAID,QAAQE;AACjE;AAEA,SAASnB,gBAAgBiB,KAAc;IACrC,MAAMG,SAAS,OAAOH,UAAU,WAAWI,OAAOJ,SAASA;IAC3D,OAAO,OAAOG,WAAW,YAAYC,OAAOC,SAAS,CAACF,WAAWA,SAAS,IAAIA,SAASD;AACzF"}
@@ -1,7 +1,9 @@
1
+ import { validateWorkflowRunsSearch } from './inputs.js';
1
2
  declare const _default: import("@shipfox/client-shell/runtime").RouteImpl<{
2
3
  readonly staticData: {
3
4
  readonly layout: "full-bleed";
4
5
  };
6
+ readonly validateSearch: typeof validateWorkflowRunsSearch;
5
7
  readonly component: () => import("react").JSX.Element;
6
8
  }>;
7
9
  export default _default;
@@ -1 +1 @@
1
- {"version":3,"file":"run-detail.d.ts","sourceRoot":"","sources":["../../src/routes/run-detail.tsx"],"names":[],"mappings":";;;;;;AAIA,wBAUG"}
1
+ {"version":3,"file":"run-detail.d.ts","sourceRoot":"","sources":["../../src/routes/run-detail.tsx"],"names":[],"mappings":"AAEA,OAAO,EAAC,0BAA0B,EAAsB,MAAM,aAAa,CAAC;;;;;;;;AAE5E,wBAcG"}
@@ -1,19 +1,19 @@
1
1
  import { jsx as _jsx } from "react/jsx-runtime";
2
- import { defineRoute } from '@shipfox/client-shell/runtime';
3
- import { useParams } from '@tanstack/react-router';
2
+ import { defineRoute, useRouteParams, useRouteSearch } from '@shipfox/client-shell/runtime';
4
3
  import { WorkflowRunPage } from '#pages/workflow-run-page.js';
4
+ import { validateWorkflowRunsSearch, workflowRouteParams } from './inputs.js';
5
5
  export default defineRoute({
6
6
  staticData: {
7
7
  layout: 'full-bleed'
8
8
  },
9
+ validateSearch: validateWorkflowRunsSearch,
9
10
  component: ()=>{
10
- const { wid, pid, workflowRunId } = useParams({
11
- strict: false
12
- });
11
+ const { wid, pid, workflowRunId } = useRouteParams(workflowRouteParams);
13
12
  return /*#__PURE__*/ _jsx(WorkflowRunPage, {
14
13
  workspaceId: wid,
15
14
  projectId: pid,
16
- workflowRunId: workflowRunId
15
+ workflowRunId: workflowRunId,
16
+ search: useRouteSearch(validateWorkflowRunsSearch)
17
17
  });
18
18
  }
19
19
  });
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/routes/run-detail.tsx"],"sourcesContent":["import {defineRoute} from '@shipfox/client-shell/runtime';\nimport {useParams} from '@tanstack/react-router';\nimport {WorkflowRunPage} from '#pages/workflow-run-page.js';\n\nexport default defineRoute({\n staticData: {layout: 'full-bleed'},\n component: () => {\n const {wid, pid, workflowRunId} = useParams({strict: false}) as {\n wid: string;\n pid: string;\n workflowRunId: string;\n };\n return <WorkflowRunPage workspaceId={wid} projectId={pid} workflowRunId={workflowRunId} />;\n },\n});\n"],"names":["defineRoute","useParams","WorkflowRunPage","staticData","layout","component","wid","pid","workflowRunId","strict","workspaceId","projectId"],"mappings":";AAAA,SAAQA,WAAW,QAAO,gCAAgC;AAC1D,SAAQC,SAAS,QAAO,yBAAyB;AACjD,SAAQC,eAAe,QAAO,8BAA8B;AAE5D,eAAeF,YAAY;IACzBG,YAAY;QAACC,QAAQ;IAAY;IACjCC,WAAW;QACT,MAAM,EAACC,GAAG,EAAEC,GAAG,EAAEC,aAAa,EAAC,GAAGP,UAAU;YAACQ,QAAQ;QAAK;QAK1D,qBAAO,KAACP;YAAgBQ,aAAaJ;YAAKK,WAAWJ;YAAKC,eAAeA;;IAC3E;AACF,GAAG"}
1
+ {"version":3,"sources":["../../src/routes/run-detail.tsx"],"sourcesContent":["import {defineRoute, useRouteParams, useRouteSearch} from '@shipfox/client-shell/runtime';\nimport {WorkflowRunPage} from '#pages/workflow-run-page.js';\nimport {validateWorkflowRunsSearch, workflowRouteParams} from './inputs.js';\n\nexport default defineRoute({\n staticData: {layout: 'full-bleed'},\n validateSearch: validateWorkflowRunsSearch,\n component: () => {\n const {wid, pid, workflowRunId} = useRouteParams(workflowRouteParams);\n return (\n <WorkflowRunPage\n workspaceId={wid}\n projectId={pid}\n workflowRunId={workflowRunId}\n search={useRouteSearch(validateWorkflowRunsSearch)}\n />\n );\n },\n});\n"],"names":["defineRoute","useRouteParams","useRouteSearch","WorkflowRunPage","validateWorkflowRunsSearch","workflowRouteParams","staticData","layout","validateSearch","component","wid","pid","workflowRunId","workspaceId","projectId","search"],"mappings":";AAAA,SAAQA,WAAW,EAAEC,cAAc,EAAEC,cAAc,QAAO,gCAAgC;AAC1F,SAAQC,eAAe,QAAO,8BAA8B;AAC5D,SAAQC,0BAA0B,EAAEC,mBAAmB,QAAO,cAAc;AAE5E,eAAeL,YAAY;IACzBM,YAAY;QAACC,QAAQ;IAAY;IACjCC,gBAAgBJ;IAChBK,WAAW;QACT,MAAM,EAACC,GAAG,EAAEC,GAAG,EAAEC,aAAa,EAAC,GAAGX,eAAeI;QACjD,qBACE,KAACF;YACCU,aAAaH;YACbI,WAAWH;YACXC,eAAeA;YACfG,QAAQb,eAAeE;;IAG7B;AACF,GAAG"}
@@ -1,7 +1,9 @@
1
+ import { validateWorkflowRunsSearch } from './inputs.js';
1
2
  declare const _default: import("@shipfox/client-shell/runtime").RouteImpl<{
2
3
  readonly staticData: {
3
4
  readonly layout: "full-bleed";
4
5
  };
6
+ readonly validateSearch: typeof validateWorkflowRunsSearch;
5
7
  readonly component: () => import("react").JSX.Element;
6
8
  }>;
7
9
  export default _default;
@@ -1 +1 @@
1
- {"version":3,"file":"runs.d.ts","sourceRoot":"","sources":["../../src/routes/runs.tsx"],"names":[],"mappings":";;;;;;AAIA,wBAMG"}
1
+ {"version":3,"file":"runs.d.ts","sourceRoot":"","sources":["../../src/routes/runs.tsx"],"names":[],"mappings":"AAEA,OAAO,EAAC,0BAA0B,EAAsB,MAAM,aAAa,CAAC;;;;;;;;AAE5E,wBAaG"}