@strapi/review-workflows 0.0.0-experimental.d23c1d5b0e45dd06ef09977f526c85468be05403 → 0.0.0-experimental.d325780feab1caf1b9e4423588eb1cc73b74c376

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 (96) hide show
  1. package/LICENSE +12 -17
  2. package/dist/_chunks/{Layout-dGg4FA1R.js → Layout-C3IORH2n.js} +14 -24
  3. package/dist/_chunks/Layout-C3IORH2n.js.map +1 -0
  4. package/dist/_chunks/{Layout-facLKucY.mjs → Layout-DNKR5bym.mjs} +16 -23
  5. package/dist/_chunks/Layout-DNKR5bym.mjs.map +1 -0
  6. package/dist/_chunks/{en-xcewH2pC.js → en-CYgjfSep.js} +5 -2
  7. package/dist/_chunks/en-CYgjfSep.js.map +1 -0
  8. package/dist/_chunks/{en-D9ZrQAV6.mjs → en-D9dxziEb.mjs} +5 -2
  9. package/dist/_chunks/en-D9dxziEb.mjs.map +1 -0
  10. package/dist/_chunks/{_id-D4CXKOqG.mjs → id-C9Ku9Br9.mjs} +390 -427
  11. package/dist/_chunks/id-C9Ku9Br9.mjs.map +1 -0
  12. package/dist/_chunks/{_id-B6DgrtpA.js → id-oOE1bYls.js} +395 -435
  13. package/dist/_chunks/id-oOE1bYls.js.map +1 -0
  14. package/dist/_chunks/{index-D7Y0ofdg.mjs → index-ByXbOW-R.mjs} +196 -232
  15. package/dist/_chunks/index-ByXbOW-R.mjs.map +1 -0
  16. package/dist/_chunks/{index-BuKZWpJw.js → index-CmHHjN95.js} +24 -61
  17. package/dist/_chunks/index-CmHHjN95.js.map +1 -0
  18. package/dist/_chunks/{index-QbWLXdZR.mjs → index-CyhaJuJG.mjs} +24 -58
  19. package/dist/_chunks/index-CyhaJuJG.mjs.map +1 -0
  20. package/dist/_chunks/{index-DX8AGcIP.js → index-DMT27jNE.js} +196 -235
  21. package/dist/_chunks/index-DMT27jNE.js.map +1 -0
  22. package/dist/_chunks/{purchase-review-workflows-Ds61D_tk.js → purchase-review-workflows-BxoDFxQ5.js} +8 -7
  23. package/dist/_chunks/purchase-review-workflows-BxoDFxQ5.js.map +1 -0
  24. package/dist/_chunks/{purchase-review-workflows-B-V0sA2I.mjs → purchase-review-workflows-DyFV_H0I.mjs} +9 -8
  25. package/dist/_chunks/purchase-review-workflows-DyFV_H0I.mjs.map +1 -0
  26. package/dist/_chunks/{router-ylD0eA48.mjs → router-BPl2HZMq.mjs} +3 -3
  27. package/dist/_chunks/router-BPl2HZMq.mjs.map +1 -0
  28. package/dist/_chunks/{router-CL62NScV.js → router-vDfGt9bq.js} +3 -3
  29. package/dist/_chunks/router-vDfGt9bq.js.map +1 -0
  30. package/dist/admin/index.js +1 -1
  31. package/dist/admin/index.mjs +1 -1
  32. package/dist/admin/src/components/LimitsModal.d.ts +2 -4
  33. package/dist/admin/src/routes/content-manager/[model]/[id]/components/Panel.d.ts +1 -1
  34. package/dist/admin/src/routes/settings/hooks/useDragAndDrop.d.ts +4 -4
  35. package/dist/admin/src/routes/settings/hooks/useKeyboardDragAndDrop.d.ts +1 -1
  36. package/dist/admin/src/routes/settings/hooks/useReviewWorkflows.d.ts +3 -3
  37. package/dist/admin/src/services/admin.d.ts +2 -2
  38. package/dist/admin/src/services/api.d.ts +2 -3
  39. package/dist/admin/src/services/content-manager.d.ts +7 -7
  40. package/dist/admin/src/services/settings.d.ts +1740 -10
  41. package/dist/admin/src/utils/api.d.ts +4 -19
  42. package/dist/admin/src/utils/cm-hooks.d.ts +1 -1
  43. package/dist/server/index.js +455 -628
  44. package/dist/server/index.js.map +1 -1
  45. package/dist/server/index.mjs +455 -628
  46. package/dist/server/index.mjs.map +1 -1
  47. package/dist/server/src/bootstrap.d.ts.map +1 -1
  48. package/dist/server/src/constants/workflows.d.ts +1 -0
  49. package/dist/server/src/constants/workflows.d.ts.map +1 -1
  50. package/dist/server/src/content-types/index.d.ts +6 -0
  51. package/dist/server/src/content-types/index.d.ts.map +1 -1
  52. package/dist/server/src/content-types/workflow/index.d.ts +6 -0
  53. package/dist/server/src/content-types/workflow/index.d.ts.map +1 -1
  54. package/dist/server/src/controllers/assignees.d.ts.map +1 -1
  55. package/dist/server/src/controllers/index.d.ts +0 -1
  56. package/dist/server/src/controllers/index.d.ts.map +1 -1
  57. package/dist/server/src/controllers/stages.d.ts.map +1 -1
  58. package/dist/server/src/controllers/workflows.d.ts +0 -7
  59. package/dist/server/src/controllers/workflows.d.ts.map +1 -1
  60. package/dist/server/src/index.d.ts +28 -7
  61. package/dist/server/src/index.d.ts.map +1 -1
  62. package/dist/server/src/register.d.ts.map +1 -1
  63. package/dist/server/src/routes/review-workflows.d.ts.map +1 -1
  64. package/dist/server/src/services/assignees.d.ts +8 -4
  65. package/dist/server/src/services/assignees.d.ts.map +1 -1
  66. package/dist/server/src/services/document-service-middleware.d.ts +1 -0
  67. package/dist/server/src/services/document-service-middleware.d.ts.map +1 -1
  68. package/dist/server/src/services/index.d.ts +16 -6
  69. package/dist/server/src/services/index.d.ts.map +1 -1
  70. package/dist/server/src/services/metrics/index.d.ts +4 -4
  71. package/dist/server/src/services/metrics/index.d.ts.map +1 -1
  72. package/dist/server/src/services/metrics/weekly-metrics.d.ts.map +1 -1
  73. package/dist/server/src/services/stages.d.ts +7 -7
  74. package/dist/server/src/services/stages.d.ts.map +1 -1
  75. package/dist/server/src/services/workflows.d.ts.map +1 -1
  76. package/dist/server/src/validation/review-workflows.d.ts +4 -0
  77. package/dist/server/src/validation/review-workflows.d.ts.map +1 -1
  78. package/dist/shared/contracts/review-workflows.d.ts +9 -17
  79. package/dist/shared/contracts/review-workflows.d.ts.map +1 -1
  80. package/package.json +17 -20
  81. package/dist/_chunks/Layout-dGg4FA1R.js.map +0 -1
  82. package/dist/_chunks/Layout-facLKucY.mjs.map +0 -1
  83. package/dist/_chunks/_id-B6DgrtpA.js.map +0 -1
  84. package/dist/_chunks/_id-D4CXKOqG.mjs.map +0 -1
  85. package/dist/_chunks/en-D9ZrQAV6.mjs.map +0 -1
  86. package/dist/_chunks/en-xcewH2pC.js.map +0 -1
  87. package/dist/_chunks/index-BuKZWpJw.js.map +0 -1
  88. package/dist/_chunks/index-D7Y0ofdg.mjs.map +0 -1
  89. package/dist/_chunks/index-DX8AGcIP.js.map +0 -1
  90. package/dist/_chunks/index-QbWLXdZR.mjs.map +0 -1
  91. package/dist/_chunks/purchase-review-workflows-B-V0sA2I.mjs.map +0 -1
  92. package/dist/_chunks/purchase-review-workflows-Ds61D_tk.js.map +0 -1
  93. package/dist/_chunks/router-CL62NScV.js.map +0 -1
  94. package/dist/_chunks/router-ylD0eA48.mjs.map +0 -1
  95. package/strapi-server.js +0 -3
  96. /package/dist/admin/src/routes/settings/{:id.d.ts → id.d.ts} +0 -0
@@ -8,19 +8,15 @@ const designSystem = require("@strapi/design-system");
8
8
  const icons = require("@strapi/icons");
9
9
  const fractionalIndexing = require("fractional-indexing");
10
10
  const reactIntl = require("react-intl");
11
- const reactRedux = require("react-redux");
12
11
  const reactRouterDom = require("react-router-dom");
13
12
  const yup = require("yup");
14
- const index = require("./index-DX8AGcIP.js");
15
- const Layout = require("./Layout-dGg4FA1R.js");
16
- const v2 = require("@strapi/design-system/v2");
13
+ const index = require("./index-DMT27jNE.js");
14
+ const Layout = require("./Layout-C3IORH2n.js");
17
15
  const reactDndHtml5Backend = require("react-dnd-html5-backend");
18
- const styled = require("styled-components");
16
+ const styledComponents = require("styled-components");
19
17
  const reactDnd = require("react-dnd");
20
- const _interopDefault = (e) => e && e.__esModule ? e : { default: e };
21
18
  function _interopNamespace(e) {
22
- if (e && e.__esModule)
23
- return e;
19
+ if (e && e.__esModule) return e;
24
20
  const n = Object.create(null, { [Symbol.toStringTag]: { value: "Module" } });
25
21
  if (e) {
26
22
  for (const k in e) {
@@ -38,11 +34,10 @@ function _interopNamespace(e) {
38
34
  }
39
35
  const React__namespace = /* @__PURE__ */ _interopNamespace(React);
40
36
  const yup__namespace = /* @__PURE__ */ _interopNamespace(yup);
41
- const styled__default = /* @__PURE__ */ _interopDefault(styled);
42
37
  const adminApi = index.reviewWorkflowsApi.injectEndpoints({
43
38
  endpoints(builder) {
44
39
  return {
45
- getRoles: builder.query({
40
+ getAdminRoles: builder.query({
46
41
  query: () => ({
47
42
  url: `/admin/roles`,
48
43
  method: "GET"
@@ -54,7 +49,7 @@ const adminApi = index.reviewWorkflowsApi.injectEndpoints({
54
49
  };
55
50
  }
56
51
  });
57
- const { useGetRolesQuery } = adminApi;
52
+ const { useGetAdminRolesQuery } = adminApi;
58
53
  const useKeyboardDragAndDrop = (active, index2, { onCancel, onDropItem, onGrabItem, onMoveItem }) => {
59
54
  const [isSelected, setIsSelected] = React__namespace.useState(false);
60
55
  const handleMove = (movement) => {
@@ -163,8 +158,7 @@ const useDragAndDrop = (active, {
163
158
  const hoverBoundingRect = objectRef.current?.getBoundingClientRect();
164
159
  const hoverMiddleY = (hoverBoundingRect.bottom - hoverBoundingRect.top) / 2;
165
160
  const clientOffset = monitor.getClientOffset();
166
- if (!clientOffset)
167
- return;
161
+ if (!clientOffset) return;
168
162
  const hoverClientY = clientOffset && clientOffset.y - hoverBoundingRect.top;
169
163
  if (typeof dragIndex === "number" && typeof newIndex === "number") {
170
164
  if (dragIndex === newIndex) {
@@ -217,10 +211,8 @@ const useDragAndDrop = (active, {
217
211
  const getDragDirection = (monitor) => {
218
212
  if (monitor && monitor.isDragging() && !monitor.didDrop() && monitor.getInitialClientOffset() && monitor.getClientOffset()) {
219
213
  const deltaY = monitor.getInitialClientOffset().y - monitor.getClientOffset().y;
220
- if (deltaY > 0)
221
- return DIRECTIONS.UPWARD;
222
- if (deltaY < 0)
223
- return DIRECTIONS.DOWNWARD;
214
+ if (deltaY > 0) return DIRECTIONS.UPWARD;
215
+ if (deltaY < 0) return DIRECTIONS.DOWNWARD;
224
216
  return null;
225
217
  }
226
218
  return null;
@@ -273,74 +265,35 @@ const AddStage = ({ children, ...props }) => {
273
265
  return /* @__PURE__ */ jsxRuntime.jsx(
274
266
  StyledButton,
275
267
  {
276
- as: "button",
268
+ tag: "button",
277
269
  background: "neutral0",
278
- border: "neutral150",
270
+ borderColor: "neutral150",
279
271
  paddingBottom: 3,
280
272
  paddingLeft: 4,
281
273
  paddingRight: 4,
282
274
  paddingTop: 3,
283
275
  shadow: "filterShadow",
284
276
  ...props,
285
- children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { gap: 2, children: [
286
- /* @__PURE__ */ jsxRuntime.jsx(StyledAddIcon, { "aria-hidden": true }),
287
- /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, { variant: "pi", fontWeight: "bold", textColor: "neutral500", children })
288
- ] })
277
+ children: /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, { variant: "pi", fontWeight: "bold", children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { tag: "span", gap: 2, children: [
278
+ /* @__PURE__ */ jsxRuntime.jsx(icons.PlusCircle, { width: "2.4rem", height: "2.4rem", "aria-hidden": true }),
279
+ children
280
+ ] }) })
289
281
  }
290
282
  );
291
283
  };
292
- const StyledAddIcon = styled__default.default(icons.PlusCircle)`
293
- > circle {
294
- fill: ${({ theme }) => theme.colors.neutral150};
295
- }
296
- > path {
297
- fill: ${({ theme }) => theme.colors.neutral600};
298
- }
299
- `;
300
- const StyledButton = styled__default.default(designSystem.Box)`
284
+ const StyledButton = styledComponents.styled(designSystem.Box)`
301
285
  border-radius: 26px;
302
-
303
- svg {
304
- height: ${({ theme }) => theme.spaces[6]};
305
- width: ${({ theme }) => theme.spaces[6]};
306
-
307
- > path {
308
- fill: ${({ theme }) => theme.colors.neutral600};
309
- }
310
- }
286
+ color: ${({ theme }) => theme.colors.neutral500};
311
287
 
312
288
  &:hover {
313
- color: ${({ theme }) => theme.colors.primary600} !important;
314
- ${designSystem.Typography} {
315
- color: ${({ theme }) => theme.colors.primary600} !important;
316
- }
317
-
318
- ${StyledAddIcon} {
319
- > circle {
320
- fill: ${({ theme }) => theme.colors.primary600};
321
- }
322
- > path {
323
- fill: ${({ theme }) => theme.colors.neutral100};
324
- }
325
- }
289
+ color: ${({ theme }) => theme.colors.primary600};
326
290
  }
327
291
 
328
292
  &:active {
329
- ${designSystem.Typography} {
330
- color: ${({ theme }) => theme.colors.primary600};
331
- }
332
-
333
- ${StyledAddIcon} {
334
- > circle {
335
- fill: ${({ theme }) => theme.colors.primary600};
336
- }
337
- > path {
338
- fill: ${({ theme }) => theme.colors.neutral100};
339
- }
340
- }
293
+ color: ${({ theme }) => theme.colors.primary600};
341
294
  }
342
295
  `;
343
- const Stages = ({ canDelete = true, canUpdate = true, isCreating = false }) => {
296
+ const Stages = ({ canDelete = true, canUpdate = true, isCreating }) => {
344
297
  const { formatMessage } = reactIntl.useIntl();
345
298
  const { trackUsage } = strapiAdmin.useTracking();
346
299
  const addFieldRow = strapiAdmin.useForm("Stages", (state) => state.addFieldRow);
@@ -355,35 +308,23 @@ const Stages = ({ canDelete = true, canUpdate = true, isCreating = false }) => {
355
308
  left: "50%",
356
309
  position: "absolute",
357
310
  top: "0",
358
- width: 2,
359
- zIndex: 1
311
+ width: 2
360
312
  }
361
313
  ),
362
- /* @__PURE__ */ jsxRuntime.jsx(
363
- designSystem.Flex,
364
- {
365
- direction: "column",
366
- alignItems: "stretch",
367
- gap: 6,
368
- zIndex: 2,
369
- position: "relative",
370
- as: "ol",
371
- children: stages.map((stage, index2) => {
372
- return /* @__PURE__ */ jsxRuntime.jsx(designSystem.Box, { as: "li", children: /* @__PURE__ */ jsxRuntime.jsx(
373
- Stage,
374
- {
375
- index: index2,
376
- canDelete: stages.length > 1 && canDelete,
377
- canReorder: stages.length > 1,
378
- canUpdate,
379
- stagesCount: stages.length,
380
- isOpen: isCreating,
381
- ...stage
382
- }
383
- ) }, stage.__temp_key__);
384
- })
385
- }
386
- )
314
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Flex, { direction: "column", alignItems: "stretch", gap: 6, position: "relative", tag: "ol", children: stages.map((stage, index2) => {
315
+ return /* @__PURE__ */ jsxRuntime.jsx(designSystem.Box, { tag: "li", children: /* @__PURE__ */ jsxRuntime.jsx(
316
+ Stage,
317
+ {
318
+ index: index2,
319
+ canDelete: stages.length > 1 && canDelete,
320
+ canReorder: stages.length > 1,
321
+ canUpdate,
322
+ stagesCount: stages.length,
323
+ defaultOpen: !stage.id,
324
+ ...stage
325
+ }
326
+ ) }, stage.__temp_key__);
327
+ }) })
387
328
  ] }),
388
329
  canUpdate && /* @__PURE__ */ jsxRuntime.jsx(
389
330
  AddStage,
@@ -401,7 +342,7 @@ const Stages = ({ canDelete = true, canUpdate = true, isCreating = false }) => {
401
342
  )
402
343
  ] });
403
344
  };
404
- const Background = styled__default.default(designSystem.Box)`
345
+ const Background = styledComponents.styled(designSystem.Box)`
405
346
  transform: translateX(-50%);
406
347
  `;
407
348
  const Stage = ({
@@ -409,16 +350,15 @@ const Stage = ({
409
350
  canDelete = false,
410
351
  canReorder = false,
411
352
  canUpdate = false,
412
- isOpen: isOpenDefault = false,
413
353
  stagesCount,
414
354
  name,
415
355
  permissions,
416
- color
356
+ color,
357
+ defaultOpen
417
358
  }) => {
418
359
  const [liveText, setLiveText] = React__namespace.useState();
419
360
  const { formatMessage } = reactIntl.useIntl();
420
361
  const { trackUsage } = strapiAdmin.useTracking();
421
- const [isOpen, setIsOpen] = React__namespace.useState(isOpenDefault);
422
362
  const stageErrors = strapiAdmin.useForm("Stages", (state) => state.errors.stages);
423
363
  const error = stageErrors?.[index2];
424
364
  const addFieldRow = strapiAdmin.useForm("Stage", (state) => state.addFieldRow);
@@ -500,7 +440,8 @@ const Stage = ({
500
440
  const handleCloneClick = () => {
501
441
  addFieldRow("stages", { name, color, permissions });
502
442
  };
503
- return /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Box, { ref: (ref) => composedRef(ref), children: [
443
+ const id = React__namespace.useId();
444
+ return /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Box, { ref: composedRef, shadow: "tableShadow", children: [
504
445
  liveText && /* @__PURE__ */ jsxRuntime.jsx(designSystem.VisuallyHidden, { "aria-live": "assertive", children: liveText }),
505
446
  isDragging ? /* @__PURE__ */ jsxRuntime.jsx(
506
447
  designSystem.Box,
@@ -511,74 +452,61 @@ const Stage = ({
511
452
  borderWidth: "1px",
512
453
  display: "block",
513
454
  hasRadius: true,
514
- padding: 6,
515
- shadow: "tableShadow"
455
+ padding: 6
516
456
  }
517
- ) : /* @__PURE__ */ jsxRuntime.jsxs(
518
- designSystem.Accordion,
457
+ ) : /* @__PURE__ */ jsxRuntime.jsx(
458
+ AccordionRoot,
519
459
  {
520
- size: "S",
521
- variant: "primary",
522
- onToggle: () => {
523
- setIsOpen(!isOpen);
524
- if (!isOpen) {
460
+ onValueChange: (value) => {
461
+ if (value) {
525
462
  trackUsage("willEditStage");
526
463
  }
527
464
  },
528
- expanded: isOpen,
529
- shadow: "tableShadow",
530
- error: Object.values(error ?? {})[0],
531
- hasErrorMessage: false,
532
- children: [
533
- /* @__PURE__ */ jsxRuntime.jsx(
534
- designSystem.AccordionToggle,
535
- {
536
- title: name,
537
- togglePosition: "left",
538
- action: (canDelete || canUpdate) && /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { children: [
539
- /* @__PURE__ */ jsxRuntime.jsxs(v2.Menu.Root, { children: [
540
- /* @__PURE__ */ jsxRuntime.jsxs(ContextMenuTrigger, { size: "S", endIcon: null, paddingLeft: 2, paddingRight: 2, children: [
541
- /* @__PURE__ */ jsxRuntime.jsx(icons.More, { "aria-hidden": true, focusable: false }),
542
- /* @__PURE__ */ jsxRuntime.jsx(designSystem.VisuallyHidden, { as: "span", children: formatMessage({
543
- id: "[tbdb].components.DynamicZone.more-actions",
544
- defaultMessage: "More actions"
545
- }) })
546
- ] }),
547
- /* @__PURE__ */ jsxRuntime.jsx(v2.Menu.Content, { popoverPlacement: "bottom-end", zIndex: 2, children: /* @__PURE__ */ jsxRuntime.jsxs(v2.Menu.SubRoot, { children: [
548
- canUpdate && /* @__PURE__ */ jsxRuntime.jsx(v2.MenuItem, { onClick: handleCloneClick, children: formatMessage({
549
- id: "Settings.review-workflows.stage.delete",
550
- defaultMessage: "Duplicate stage"
551
- }) }),
552
- canDelete && /* @__PURE__ */ jsxRuntime.jsx(DeleteMenuItem, { onClick: () => removeFieldRow("stages", index2), children: formatMessage({
553
- id: "Settings.review-workflows.stage.delete",
554
- defaultMessage: "Delete"
555
- }) })
556
- ] }) })
465
+ defaultValue: defaultOpen ? id : void 0,
466
+ $error: Object.values(error ?? {}).length > 0,
467
+ children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Accordion.Item, { value: id, children: [
468
+ /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Accordion.Header, { children: [
469
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Accordion.Trigger, { children: name }),
470
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Accordion.Actions, { children: canDelete || canUpdate ? /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
471
+ /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Menu.Root, { children: [
472
+ /* @__PURE__ */ jsxRuntime.jsxs(ContextMenuTrigger, { size: "S", endIcon: null, paddingLeft: 2, paddingRight: 2, children: [
473
+ /* @__PURE__ */ jsxRuntime.jsx(icons.More, { "aria-hidden": true, focusable: false }),
474
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.VisuallyHidden, { tag: "span", children: formatMessage({
475
+ id: "[tbdb].components.DynamicZone.more-actions",
476
+ defaultMessage: "More actions"
477
+ }) })
557
478
  ] }),
558
- canUpdate && /* @__PURE__ */ jsxRuntime.jsx(
559
- DragIconButton,
560
- {
561
- background: "transparent",
562
- forwardedAs: "div",
563
- hasRadius: true,
564
- role: "button",
565
- noBorder: true,
566
- tabIndex: 0,
567
- "data-handler-id": handlerId,
568
- ref: dragRef,
569
- label: formatMessage({
570
- id: "Settings.review-workflows.stage.drag",
571
- defaultMessage: "Drag"
572
- }),
573
- onClick: (e) => e.stopPropagation(),
574
- onKeyDown: handleKeyDown,
575
- children: /* @__PURE__ */ jsxRuntime.jsx(icons.Drag, {})
576
- }
577
- )
578
- ] })
579
- }
580
- ),
581
- /* @__PURE__ */ jsxRuntime.jsx(designSystem.AccordionContent, { padding: 6, background: "neutral0", hasRadius: true, children: /* @__PURE__ */ jsxRuntime.jsx(designSystem.Grid, { gap: 4, children: [
479
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Menu.Content, { popoverPlacement: "bottom-end", zIndex: 2, children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Menu.SubRoot, { children: [
480
+ canUpdate && /* @__PURE__ */ jsxRuntime.jsx(designSystem.MenuItem, { onClick: handleCloneClick, children: formatMessage({
481
+ id: "Settings.review-workflows.stage.delete",
482
+ defaultMessage: "Duplicate stage"
483
+ }) }),
484
+ canDelete && /* @__PURE__ */ jsxRuntime.jsx(DeleteMenuItem, { onClick: () => removeFieldRow("stages", index2), children: formatMessage({
485
+ id: "Settings.review-workflows.stage.delete",
486
+ defaultMessage: "Delete"
487
+ }) })
488
+ ] }) })
489
+ ] }),
490
+ canUpdate && /* @__PURE__ */ jsxRuntime.jsx(
491
+ designSystem.IconButton,
492
+ {
493
+ background: "transparent",
494
+ hasRadius: true,
495
+ variant: "ghost",
496
+ "data-handler-id": handlerId,
497
+ ref: dragRef,
498
+ label: formatMessage({
499
+ id: "Settings.review-workflows.stage.drag",
500
+ defaultMessage: "Drag"
501
+ }),
502
+ onClick: (e) => e.stopPropagation(),
503
+ onKeyDown: handleKeyDown,
504
+ children: /* @__PURE__ */ jsxRuntime.jsx(icons.Drag, {})
505
+ }
506
+ )
507
+ ] }) : null })
508
+ ] }),
509
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Accordion.Content, { children: /* @__PURE__ */ jsxRuntime.jsx(designSystem.Grid.Root, { gap: 4, padding: 6, children: [
582
510
  {
583
511
  disabled: !canUpdate,
584
512
  label: formatMessage({
@@ -616,16 +544,20 @@ const Stage = ({
616
544
  size: 6,
617
545
  type: "permissions"
618
546
  }
619
- ].map(({ size, ...field }) => /* @__PURE__ */ jsxRuntime.jsx(designSystem.GridItem, { col: size, children: /* @__PURE__ */ jsxRuntime.jsx(InputRenderer, { ...field }) }, field.name)) }) })
620
- ]
547
+ ].map(({ size, ...field }) => /* @__PURE__ */ jsxRuntime.jsx(designSystem.Grid.Item, { col: size, direction: "column", alignItems: "stretch", children: /* @__PURE__ */ jsxRuntime.jsx(InputRenderer, { ...field }) }, field.name)) }) })
548
+ ] })
621
549
  }
622
550
  )
623
551
  ] });
624
552
  };
625
- const DeleteMenuItem = styled__default.default(v2.MenuItem)`
553
+ const AccordionRoot = styledComponents.styled(designSystem.Accordion.Root)`
554
+ border: 1px solid
555
+ ${({ theme, $error }) => $error ? theme.colors.danger600 : theme.colors.neutral200};
556
+ `;
557
+ const DeleteMenuItem = styledComponents.styled(designSystem.MenuItem)`
626
558
  color: ${({ theme }) => theme.colors.danger600};
627
559
  `;
628
- const ContextMenuTrigger = styled__default.default(v2.Menu.Trigger)`
560
+ const ContextMenuTrigger = styledComponents.styled(designSystem.Menu.Trigger)`
629
561
  :hover,
630
562
  :focus {
631
563
  background-color: ${({ theme }) => theme.colors.neutral100};
@@ -635,22 +567,6 @@ const ContextMenuTrigger = styled__default.default(v2.Menu.Trigger)`
635
567
  font-size: 0;
636
568
  }
637
569
  `;
638
- const DragIconButton = styled__default.default(designSystem.IconButton)`
639
- align-items: center;
640
- border-radius: ${({ theme }) => theme.borderRadius};
641
- display: flex;
642
- justify-content: center;
643
-
644
- &:hover,
645
- &:focus {
646
- background-color: ${({ theme }) => theme.colors.neutral100};
647
- }
648
-
649
- svg {
650
- height: auto;
651
- width: ${({ theme }) => theme.spaces[3]};
652
- }
653
- `;
654
570
  const InputRenderer = (props) => {
655
571
  switch (props.type) {
656
572
  case "color":
@@ -676,54 +592,55 @@ const ColorSelector = ({ disabled, label, name, required }) => {
676
592
  color: hex
677
593
  }));
678
594
  const { themeColorName } = index.getStageColorByHex(value) ?? {};
679
- return /* @__PURE__ */ jsxRuntime.jsx(
680
- designSystem.SingleSelect,
681
- {
682
- disabled,
683
- error,
684
- required,
685
- label,
686
- onChange: (v) => {
687
- onChange(name, v.toString());
688
- },
689
- value: value?.toUpperCase(),
690
- startIcon: /* @__PURE__ */ jsxRuntime.jsx(
691
- designSystem.Flex,
692
- {
693
- as: "span",
694
- height: 2,
695
- background: value,
696
- borderColor: themeColorName === "neutral0" ? "neutral150" : "transparent",
697
- hasRadius: true,
698
- shrink: 0,
699
- width: 2
700
- }
701
- ),
702
- children: colorOptions.map(({ value: value2, label: label2, color }) => {
703
- const { themeColorName: themeColorName2 } = index.getStageColorByHex(color) || {};
704
- return /* @__PURE__ */ jsxRuntime.jsx(
705
- designSystem.SingleSelectOption,
595
+ return /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Field.Root, { error, name, required, children: [
596
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Field.Label, { children: label }),
597
+ /* @__PURE__ */ jsxRuntime.jsx(
598
+ designSystem.SingleSelect,
599
+ {
600
+ disabled,
601
+ onChange: (v) => {
602
+ onChange(name, v.toString());
603
+ },
604
+ value: value?.toUpperCase(),
605
+ startIcon: /* @__PURE__ */ jsxRuntime.jsx(
606
+ designSystem.Flex,
706
607
  {
707
- value: value2,
708
- startIcon: /* @__PURE__ */ jsxRuntime.jsx(
709
- designSystem.Flex,
710
- {
711
- as: "span",
712
- height: 2,
713
- background: color,
714
- borderColor: themeColorName2 === "neutral0" ? "neutral150" : "transparent",
715
- hasRadius: true,
716
- shrink: 0,
717
- width: 2
718
- }
719
- ),
720
- children: label2
721
- },
722
- value2
723
- );
724
- })
725
- }
726
- );
608
+ tag: "span",
609
+ height: 2,
610
+ background: value,
611
+ borderColor: themeColorName === "neutral0" ? "neutral150" : "transparent",
612
+ hasRadius: true,
613
+ shrink: 0,
614
+ width: 2
615
+ }
616
+ ),
617
+ children: colorOptions.map(({ value: value2, label: label2, color }) => {
618
+ const { themeColorName: themeColorName2 } = index.getStageColorByHex(color) || {};
619
+ return /* @__PURE__ */ jsxRuntime.jsx(
620
+ designSystem.SingleSelectOption,
621
+ {
622
+ value: value2,
623
+ startIcon: /* @__PURE__ */ jsxRuntime.jsx(
624
+ designSystem.Flex,
625
+ {
626
+ tag: "span",
627
+ height: 2,
628
+ background: color,
629
+ borderColor: themeColorName2 === "neutral0" ? "neutral150" : "transparent",
630
+ hasRadius: true,
631
+ shrink: 0,
632
+ width: 2
633
+ }
634
+ ),
635
+ children: label2
636
+ },
637
+ value2
638
+ );
639
+ })
640
+ }
641
+ ),
642
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Field.Error, {})
643
+ ] });
727
644
  };
728
645
  const PermissionsField = ({ disabled, name, placeholder, required }) => {
729
646
  const { formatMessage } = reactIntl.useIntl();
@@ -732,57 +649,65 @@ const PermissionsField = ({ disabled, name, placeholder, required }) => {
732
649
  const { value = [], error, onChange } = strapiAdmin.useField(name);
733
650
  const allStages = strapiAdmin.useForm("PermissionsField", (state) => state.values.stages);
734
651
  const onFormValueChange = strapiAdmin.useForm("PermissionsField", (state) => state.onChange);
735
- const { data: roles = [], isLoading } = useGetRolesQuery();
652
+ const rolesErrorCount = React__namespace.useRef(0);
653
+ const { data: roles = [], isLoading, error: getRolesError } = useGetAdminRolesQuery();
736
654
  const filteredRoles = roles?.filter((role) => role.code !== "strapi-super-admin") ?? [];
737
655
  React__namespace.useEffect(() => {
738
- if (!isLoading && roles.length === 0) {
656
+ if (!isLoading && getRolesError && "status" in getRolesError && getRolesError.status == 403 && rolesErrorCount.current === 0) {
657
+ rolesErrorCount.current = 1;
739
658
  toggleNotification({
740
659
  blockTransition: true,
741
660
  type: "danger",
742
661
  message: formatMessage({
743
662
  id: "review-workflows.stage.permissions.noPermissions.description",
744
- defaultMessage: "You don’t have the permission to see roles"
663
+ defaultMessage: "You don’t have the permission to see roles. Contact your administrator."
745
664
  })
746
665
  });
747
666
  }
748
- }, [formatMessage, isLoading, roles, toggleNotification]);
667
+ }, [formatMessage, isLoading, roles, toggleNotification, getRolesError]);
749
668
  if (!isLoading && filteredRoles.length === 0) {
750
- return /* @__PURE__ */ jsxRuntime.jsx(
751
- designSystem.TextInput,
669
+ return /* @__PURE__ */ jsxRuntime.jsxs(
670
+ designSystem.Field.Root,
752
671
  {
753
- disabled: true,
754
672
  name,
755
673
  hint: formatMessage({
756
674
  id: "Settings.review-workflows.stage.permissions.noPermissions.description",
757
675
  defaultMessage: "You don’t have the permission to see roles"
758
676
  }),
759
- label: formatMessage({
760
- id: "Settings.review-workflows.stage.permissions.label",
761
- defaultMessage: "Roles that can change this stage"
762
- }),
763
- placeholder: formatMessage({
764
- id: "components.NotAllowedInput.text",
765
- defaultMessage: "No permissions to see this field"
766
- }),
767
677
  required,
768
- startAction: /* @__PURE__ */ jsxRuntime.jsx(StyledIcon, {}),
769
- type: "text",
770
- value: ""
678
+ children: [
679
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Field.Label, { children: formatMessage({
680
+ id: "Settings.review-workflows.stage.permissions.label",
681
+ defaultMessage: "Roles that can change this stage"
682
+ }) }),
683
+ /* @__PURE__ */ jsxRuntime.jsx(
684
+ designSystem.TextInput,
685
+ {
686
+ disabled: true,
687
+ placeholder: formatMessage({
688
+ id: "components.NotAllowedInput.text",
689
+ defaultMessage: "No permissions to see this field"
690
+ }),
691
+ startAction: /* @__PURE__ */ jsxRuntime.jsx(icons.EyeStriked, { fill: "neutral600" }),
692
+ type: "text",
693
+ value: ""
694
+ }
695
+ ),
696
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Field.Hint, {})
697
+ ]
771
698
  }
772
699
  );
773
700
  }
774
- return /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
775
- /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { alignItems: "flex-end", gap: 3, children: [
776
- /* @__PURE__ */ jsxRuntime.jsx(PermissionWrapper, { grow: 1, children: /* @__PURE__ */ jsxRuntime.jsx(
701
+ return /* @__PURE__ */ jsxRuntime.jsx(jsxRuntime.Fragment, { children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { alignItems: "flex-end", gap: 3, children: [
702
+ /* @__PURE__ */ jsxRuntime.jsx(PermissionWrapper, { grow: 1, children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Field.Root, { error, name, required: true, children: [
703
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Field.Label, { children: formatMessage({
704
+ id: "Settings.review-workflows.stage.permissions.label",
705
+ defaultMessage: "Roles that can change this stage"
706
+ }) }),
707
+ /* @__PURE__ */ jsxRuntime.jsx(
777
708
  designSystem.MultiSelect,
778
709
  {
779
710
  disabled,
780
- error,
781
- id: name,
782
- label: formatMessage({
783
- id: "Settings.review-workflows.stage.permissions.label",
784
- defaultMessage: "Roles that can change this stage"
785
- }),
786
711
  onChange: (values) => {
787
712
  const permissions = values.map((value2) => ({
788
713
  role: parseInt(value2, 10),
@@ -791,7 +716,6 @@ const PermissionsField = ({ disabled, name, placeholder, required }) => {
791
716
  onChange(name, permissions);
792
717
  },
793
718
  placeholder,
794
- required: true,
795
719
  value: value.map((permission) => `${permission.role}`),
796
720
  withTags: true,
797
721
  children: /* @__PURE__ */ jsxRuntime.jsx(
@@ -808,70 +732,64 @@ const PermissionsField = ({ disabled, name, placeholder, required }) => {
808
732
  }
809
733
  )
810
734
  }
811
- ) }),
812
- /* @__PURE__ */ jsxRuntime.jsx(
735
+ ),
736
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Field.Error, {})
737
+ ] }) }),
738
+ /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Dialog.Root, { open: isApplyAllConfirmationOpen, onOpenChange: setIsApplyAllConfirmationOpen, children: [
739
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Dialog.Trigger, { children: /* @__PURE__ */ jsxRuntime.jsx(
813
740
  designSystem.IconButton,
814
741
  {
815
742
  disabled,
816
- icon: /* @__PURE__ */ jsxRuntime.jsx(icons.Duplicate, {}),
817
743
  label: formatMessage({
818
744
  id: "Settings.review-workflows.stage.permissions.apply.label",
819
745
  defaultMessage: "Apply to all stages"
820
746
  }),
821
747
  size: "L",
822
- variant: "secondary",
823
- onClick: () => setIsApplyAllConfirmationOpen(true)
748
+ children: /* @__PURE__ */ jsxRuntime.jsx(icons.Duplicate, {})
749
+ }
750
+ ) }),
751
+ /* @__PURE__ */ jsxRuntime.jsx(
752
+ strapiAdmin.ConfirmDialog,
753
+ {
754
+ onConfirm: () => {
755
+ onFormValueChange(
756
+ "stages",
757
+ allStages.map((stage) => ({
758
+ ...stage,
759
+ permissions: value
760
+ }))
761
+ );
762
+ setIsApplyAllConfirmationOpen(false);
763
+ toggleNotification({
764
+ type: "success",
765
+ message: formatMessage({
766
+ id: "Settings.review-workflows.page.edit.confirm.stages.permissions.copy.success",
767
+ defaultMessage: "Applied roles to all other stages of the workflow"
768
+ })
769
+ });
770
+ },
771
+ variant: "default",
772
+ children: formatMessage({
773
+ id: "Settings.review-workflows.page.edit.confirm.stages.permissions.copy",
774
+ defaultMessage: "Roles that can change that stage will be applied to all the other stages."
775
+ })
824
776
  }
825
777
  )
826
- ] }),
827
- /* @__PURE__ */ jsxRuntime.jsx(
828
- strapiAdmin.ConfirmDialog,
829
- {
830
- isOpen: isApplyAllConfirmationOpen,
831
- onClose: () => setIsApplyAllConfirmationOpen(false),
832
- onConfirm: () => {
833
- onFormValueChange(
834
- "stages",
835
- allStages.map((stage) => ({
836
- ...stage,
837
- permissions: value
838
- }))
839
- );
840
- setIsApplyAllConfirmationOpen(false);
841
- toggleNotification({
842
- type: "success",
843
- message: formatMessage({
844
- id: "Settings.review-workflows.page.edit.confirm.stages.permissions.copy.success",
845
- defaultMessage: "Applied roles to all other stages of the workflow"
846
- })
847
- });
848
- },
849
- variant: "default",
850
- children: formatMessage({
851
- id: "Settings.review-workflows.page.edit.confirm.stages.permissions.copy",
852
- defaultMessage: "Roles that can change that stage will be applied to all the other stages."
853
- })
854
- }
855
- )
856
- ] });
778
+ ] })
779
+ ] }) });
857
780
  };
858
- const StyledIcon = styled__default.default(icons.EyeStriked)`
859
- & > path {
860
- fill: ${({ theme }) => theme.colors.neutral600};
861
- }
862
- `;
863
- const NestedOption$1 = styled__default.default(designSystem.MultiSelectOption)`
781
+ const NestedOption$1 = styledComponents.styled(designSystem.MultiSelectOption)`
864
782
  padding-left: ${({ theme }) => theme.spaces[7]};
865
783
  `;
866
- const PermissionWrapper = styled__default.default(designSystem.Flex)`
784
+ const PermissionWrapper = styledComponents.styled(designSystem.Flex)`
867
785
  > * {
868
786
  flex-grow: 1;
869
787
  }
870
788
  `;
871
789
  const WorkflowAttributes = ({ canUpdate = true }) => {
872
790
  const { formatMessage } = reactIntl.useIntl();
873
- return /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Grid, { background: "neutral0", hasRadius: true, gap: 4, padding: 6, shadow: "tableShadow", children: [
874
- /* @__PURE__ */ jsxRuntime.jsx(designSystem.GridItem, { col: 6, children: /* @__PURE__ */ jsxRuntime.jsx(
791
+ return /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Grid.Root, { background: "neutral0", hasRadius: true, gap: 4, padding: 6, shadow: "tableShadow", children: [
792
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Grid.Item, { col: 6, direction: "column", alignItems: "stretch", children: /* @__PURE__ */ jsxRuntime.jsx(
875
793
  strapiAdmin.InputRenderer,
876
794
  {
877
795
  disabled: !canUpdate,
@@ -884,7 +802,8 @@ const WorkflowAttributes = ({ canUpdate = true }) => {
884
802
  type: "string"
885
803
  }
886
804
  ) }),
887
- /* @__PURE__ */ jsxRuntime.jsx(designSystem.GridItem, { col: 6, children: /* @__PURE__ */ jsxRuntime.jsx(ContentTypesSelector, { disabled: !canUpdate }) })
805
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Grid.Item, { col: 6, direction: "column", alignItems: "stretch", children: /* @__PURE__ */ jsxRuntime.jsx(ContentTypesSelector, { disabled: !canUpdate }) }),
806
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Grid.Item, { col: 6, direction: "column", alignItems: "stretch", children: /* @__PURE__ */ jsxRuntime.jsx(StageSelector, { disabled: !canUpdate }) })
888
807
  ] });
889
808
  };
890
809
  const ContentTypesSelector = ({ disabled }) => {
@@ -905,97 +824,146 @@ const ContentTypesSelector = ({ disabled }) => {
905
824
  label: contentType.info.displayName,
906
825
  value: contentType.uid
907
826
  }));
908
- return /* @__PURE__ */ jsxRuntime.jsx(
909
- designSystem.MultiSelect,
910
- {
911
- customizeContent: (value2) => formatMessage(
912
- {
913
- id: "Settings.review-workflows.workflow.contentTypes.displayValue",
914
- defaultMessage: "{count} {count, plural, one {content type} other {content types}} selected"
827
+ return /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Field.Root, { error, name: "contentTypes", children: [
828
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Field.Label, { children: formatMessage({
829
+ id: "Settings.review-workflows.workflow.contentTypes.label",
830
+ defaultMessage: "Associated to"
831
+ }) }),
832
+ /* @__PURE__ */ jsxRuntime.jsx(
833
+ designSystem.MultiSelect,
834
+ {
835
+ customizeContent: (value2) => formatMessage(
836
+ {
837
+ id: "Settings.review-workflows.workflow.contentTypes.displayValue",
838
+ defaultMessage: "{count} {count, plural, one {content type} other {content types}} selected"
839
+ },
840
+ { count: value2?.length }
841
+ ),
842
+ disabled: isDisabled,
843
+ onChange: (values) => {
844
+ onChange("contentTypes", values);
915
845
  },
916
- { count: value2?.length }
917
- ),
918
- disabled: isDisabled,
846
+ value,
847
+ placeholder: formatMessage({
848
+ id: "Settings.review-workflows.workflow.contentTypes.placeholder",
849
+ defaultMessage: "Select"
850
+ }),
851
+ children: [
852
+ ...collectionTypes.length > 0 ? [
853
+ {
854
+ label: formatMessage({
855
+ id: "Settings.review-workflows.workflow.contentTypes.collectionTypes.label",
856
+ defaultMessage: "Collection Types"
857
+ }),
858
+ children: collectionTypes
859
+ }
860
+ ] : [],
861
+ ...singleTypes.length > 0 ? [
862
+ {
863
+ label: formatMessage({
864
+ id: "Settings.review-workflows.workflow.contentTypes.singleTypes.label",
865
+ defaultMessage: "Single Types"
866
+ }),
867
+ children: singleTypes
868
+ }
869
+ ] : []
870
+ ].map((opt) => {
871
+ return /* @__PURE__ */ jsxRuntime.jsx(
872
+ designSystem.MultiSelectGroup,
873
+ {
874
+ label: opt.label,
875
+ values: opt.children.map((child) => child.value.toString()),
876
+ children: opt.children.map((child) => {
877
+ const { name: assignedWorkflowName } = workflows?.find(
878
+ (workflow) => (currentWorkflow && workflow.id !== currentWorkflow.id || !currentWorkflow) && workflow.contentTypes.includes(child.value)
879
+ ) ?? {};
880
+ return /* @__PURE__ */ jsxRuntime.jsx(NestedOption, { value: child.value, children: /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, {
881
+ // @ts-expect-error - formatMessage options doesn't expect to be a React component but that's what we need actually for the <i> and <em> components
882
+ children: formatMessage(
883
+ {
884
+ id: "Settings.review-workflows.workflow.contentTypes.assigned.notice",
885
+ defaultMessage: "{label} {name, select, undefined {} other {<i>(assigned to <em>{name}</em> workflow)</i>}}"
886
+ },
887
+ {
888
+ label: child.label,
889
+ name: assignedWorkflowName,
890
+ em: (...children) => /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, { tag: "em", fontWeight: "bold", children }),
891
+ i: (...children) => /* @__PURE__ */ jsxRuntime.jsx(ContentTypeTakeNotice, { children })
892
+ }
893
+ )
894
+ }) }, child.value);
895
+ })
896
+ },
897
+ opt.label
898
+ );
899
+ })
900
+ }
901
+ )
902
+ ] });
903
+ };
904
+ const NestedOption = styledComponents.styled(designSystem.MultiSelectOption)`
905
+ padding-left: ${({ theme }) => theme.spaces[7]};
906
+ `;
907
+ const ContentTypeTakeNotice = styledComponents.styled(designSystem.Typography)`
908
+ font-style: italic;
909
+ `;
910
+ const StageSelector = ({ disabled }) => {
911
+ const { value: stages = [] } = strapiAdmin.useField("stages");
912
+ const { formatMessage } = reactIntl.useIntl();
913
+ const { error, value, onChange } = strapiAdmin.useField("stageRequiredToPublish");
914
+ const validStages = stages.filter((stage) => stage.name);
915
+ return /* @__PURE__ */ jsxRuntime.jsxs(
916
+ designSystem.Field.Root,
917
+ {
919
918
  error,
920
- label: formatMessage({
921
- id: "Settings.review-workflows.workflow.contentTypes.label",
922
- defaultMessage: "Associated to"
923
- }),
924
- onChange: (values) => {
925
- onChange("contentTypes", values);
926
- },
927
- value,
928
- placeholder: formatMessage({
929
- id: "Settings.review-workflows.workflow.contentTypes.placeholder",
930
- defaultMessage: "Select"
919
+ name: "stageRequiredToPublish",
920
+ hint: formatMessage({
921
+ id: "settings.review-workflows.workflow.stageRequiredToPublish.hint",
922
+ defaultMessage: "Prevents entries from being published if they are not at the required stage."
931
923
  }),
932
924
  children: [
933
- ...collectionTypes.length > 0 ? [
934
- {
935
- label: formatMessage({
936
- id: "Settings.review-workflows.workflow.contentTypes.collectionTypes.label",
937
- defaultMessage: "Collection Types"
938
- }),
939
- children: collectionTypes
940
- }
941
- ] : [],
942
- ...singleTypes.length > 0 ? [
925
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Field.Label, { children: formatMessage({
926
+ id: "settings.review-workflows.workflow.stageRequiredToPublish.label",
927
+ defaultMessage: "Required stage for publishing"
928
+ }) }),
929
+ /* @__PURE__ */ jsxRuntime.jsxs(
930
+ designSystem.SingleSelect,
943
931
  {
944
- label: formatMessage({
945
- id: "Settings.review-workflows.workflow.contentTypes.singleTypes.label",
946
- defaultMessage: "Single Types"
947
- }),
948
- children: singleTypes
932
+ disabled,
933
+ onChange: (value2) => {
934
+ onChange("stageRequiredToPublish", value2);
935
+ },
936
+ value,
937
+ children: [
938
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.SingleSelectOption, { value: "", children: formatMessage({
939
+ id: "settings.review-workflows.workflow.stageRequiredToPublish.any",
940
+ defaultMessage: "Any stage"
941
+ }) }),
942
+ validStages.map((stage, i) => /* @__PURE__ */ jsxRuntime.jsx(
943
+ designSystem.SingleSelectOption,
944
+ {
945
+ value: stage.id?.toString() || stage.__temp_key__,
946
+ children: stage.name
947
+ },
948
+ `requiredToPublishStage-${stage.id || stage.__temp_key__}`
949
+ ))
950
+ ]
949
951
  }
950
- ] : []
951
- ].map((opt) => {
952
- return /* @__PURE__ */ jsxRuntime.jsx(
953
- designSystem.MultiSelectGroup,
954
- {
955
- label: opt.label,
956
- values: opt.children.map((child) => child.value.toString()),
957
- children: opt.children.map((child) => {
958
- const { name: assignedWorkflowName } = workflows?.find(
959
- (workflow) => (currentWorkflow && workflow.id !== currentWorkflow.id || !currentWorkflow) && workflow.contentTypes.includes(child.value)
960
- ) ?? {};
961
- return /* @__PURE__ */ jsxRuntime.jsx(NestedOption, { value: child.value, children: /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, {
962
- // @ts-expect-error - formatMessage options doesn't expect to be a React component but that's what we need actually for the <i> and <em> components
963
- children: formatMessage(
964
- {
965
- id: "Settings.review-workflows.workflow.contentTypes.assigned.notice",
966
- defaultMessage: "{label} {name, select, undefined {} other {<i>(assigned to <em>{name}</em> workflow)</i>}}"
967
- },
968
- {
969
- label: child.label,
970
- name: assignedWorkflowName,
971
- em: (...children) => /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, { as: "em", fontWeight: "bold", children }),
972
- i: (...children) => /* @__PURE__ */ jsxRuntime.jsx(ContentTypeTakeNotice, { children })
973
- }
974
- )
975
- }) }, child.value);
976
- })
977
- },
978
- opt.label
979
- );
980
- })
952
+ ),
953
+ /* @__PURE__ */ jsxRuntime.jsx(designSystem.Field.Hint, {})
954
+ ]
981
955
  }
982
956
  );
983
957
  };
984
- const NestedOption = styled__default.default(designSystem.MultiSelectOption)`
985
- padding-left: ${({ theme }) => theme.spaces[7]};
986
- `;
987
- const ContentTypeTakeNotice = styled__default.default(designSystem.Typography)`
988
- font-style: italic;
989
- `;
990
958
  const WORKFLOW_SCHEMA = yup__namespace.object({
991
959
  contentTypes: yup__namespace.array().of(yup__namespace.string()),
992
960
  name: yup__namespace.string().max(255, {
993
961
  id: "review-workflows.validation.name.max-length",
994
962
  defaultMessage: "Name can not be longer than 255 characters"
995
- }).required(),
963
+ }).required().nullable(),
996
964
  stages: yup__namespace.array().of(
997
965
  yup__namespace.object().shape({
998
- name: yup__namespace.string().required({
966
+ name: yup__namespace.string().nullable().required({
999
967
  id: "review-workflows.validation.stage.name",
1000
968
  defaultMessage: "Name is required"
1001
969
  }).max(255, {
@@ -1012,7 +980,7 @@ const WORKFLOW_SCHEMA = yup__namespace.object({
1012
980
  return stages.filter((stage) => stage.name === stageName).length === 1;
1013
981
  }
1014
982
  ),
1015
- color: yup__namespace.string().required({
983
+ color: yup__namespace.string().nullable().required({
1016
984
  id: "review-workflows.validation.stage.color",
1017
985
  defaultMessage: "Color is required"
1018
986
  }).matches(/^#(?:[0-9a-fA-F]{3}){1,2}$/i),
@@ -1029,7 +997,8 @@ const WORKFLOW_SCHEMA = yup__namespace.object({
1029
997
  })
1030
998
  ).strict()
1031
999
  })
1032
- ).min(1)
1000
+ ).min(1),
1001
+ stageRequiredToPublish: yup__namespace.string().nullable()
1033
1002
  });
1034
1003
  const EditPage = () => {
1035
1004
  const { id = "" } = reactRouterDom.useParams();
@@ -1038,7 +1007,6 @@ const EditPage = () => {
1038
1007
  const { _unstableFormatValidationErrors: formatValidationErrors } = strapiAdmin.useAPIErrorHandler();
1039
1008
  const navigate = reactRouterDom.useNavigate();
1040
1009
  const { toggleNotification } = strapiAdmin.useNotification();
1041
- const dispatch = reactRedux.useDispatch();
1042
1010
  const {
1043
1011
  isLoading: isLoadingWorkflow,
1044
1012
  meta,
@@ -1046,7 +1014,7 @@ const EditPage = () => {
1046
1014
  error,
1047
1015
  update,
1048
1016
  create
1049
- } = Layout.useReviewWorkflows({ id: isCreatingWorkflow ? void 0 : id });
1017
+ } = Layout.useReviewWorkflows();
1050
1018
  const permissions = index.useTypedSelector(
1051
1019
  (state) => state.admin_app.permissions["settings"]?.["review-workflows"]
1052
1020
  );
@@ -1063,13 +1031,17 @@ const EditPage = () => {
1063
1031
  const stagesPerWorkflow = limits?.[index.CHARGEBEE_STAGES_PER_WORKFLOW_ENTITLEMENT_NAME];
1064
1032
  const submitForm = async (data, helpers) => {
1065
1033
  try {
1034
+ const { stageRequiredToPublish, ...rest } = data;
1035
+ const stageRequiredToPublishName = stageRequiredToPublish === "" ? null : rest.stages.find(
1036
+ (stage) => stage.id === Number(stageRequiredToPublish) || stage.__temp_key__ === stageRequiredToPublish
1037
+ )?.name;
1066
1038
  if (!isCreatingWorkflow) {
1067
1039
  const res = await update(id, {
1068
- ...data,
1040
+ ...rest,
1069
1041
  // compare permissions of stages and only submit them if at least one has
1070
1042
  // changed; this enables partial updates e.g. for users who don't have
1071
1043
  // permissions to see roles
1072
- stages: data.stages.map((stage) => {
1044
+ stages: rest.stages.map((stage) => {
1073
1045
  let hasUpdatedPermissions = true;
1074
1046
  const serverStage = currentWorkflow?.stages?.find(
1075
1047
  (serverStage2) => serverStage2.id === stage?.id
@@ -1085,40 +1057,21 @@ const EditPage = () => {
1085
1057
  ...stage,
1086
1058
  permissions: hasUpdatedPermissions ? stage.permissions : void 0
1087
1059
  };
1088
- })
1060
+ }),
1061
+ stageRequiredToPublishName
1089
1062
  });
1090
1063
  if ("error" in res && index.isBaseQueryError(res.error) && res.error.name === "ValidationError") {
1091
1064
  helpers.setErrors(formatValidationErrors(res.error));
1092
- } else if ("data" in res) {
1093
- for (const uid of res.data.contentTypes) {
1094
- dispatch({
1095
- type: "contentManagerApi/invalidateTags",
1096
- payload: [
1097
- {
1098
- type: "ContentTypesConfiguration",
1099
- id: uid
1100
- }
1101
- ]
1102
- });
1103
- }
1104
1065
  }
1105
1066
  } else {
1106
- const res = await create(data);
1067
+ const res = await create({
1068
+ ...rest,
1069
+ stageRequiredToPublishName
1070
+ });
1107
1071
  if ("error" in res && index.isBaseQueryError(res.error) && res.error.name === "ValidationError") {
1108
1072
  helpers.setErrors(formatValidationErrors(res.error));
1109
1073
  } else if ("data" in res) {
1110
- for (const uid of res.data.contentTypes) {
1111
- dispatch({
1112
- type: "contentManagerApi/invalidateTags",
1113
- payload: [
1114
- {
1115
- type: "ContentTypesConfiguration",
1116
- id: uid
1117
- }
1118
- ]
1119
- });
1120
- }
1121
- navigate(`../${res.data.id}`);
1074
+ navigate(`../${res.data.id}`, { replace: true });
1122
1075
  }
1123
1076
  }
1124
1077
  } catch (error2) {
@@ -1182,13 +1135,15 @@ const EditPage = () => {
1182
1135
  return {
1183
1136
  name: "",
1184
1137
  stages: [],
1185
- contentTypes: []
1138
+ contentTypes: [],
1139
+ stageRequiredToPublish: ""
1186
1140
  };
1187
1141
  } else {
1188
1142
  return {
1189
1143
  name: currentWorkflow.name,
1190
1144
  stages: addTmpKeysToStages(currentWorkflow.stages),
1191
- contentTypes: currentWorkflow.contentTypes
1145
+ contentTypes: currentWorkflow.contentTypes,
1146
+ stageRequiredToPublish: currentWorkflow.stageRequiredToPublish?.id.toString() ?? ""
1192
1147
  };
1193
1148
  }
1194
1149
  }, [currentWorkflow, isCreatingWorkflow]);
@@ -1211,13 +1166,12 @@ const EditPage = () => {
1211
1166
  /* @__PURE__ */ jsxRuntime.jsx(
1212
1167
  Layout.Header,
1213
1168
  {
1214
- navigationAction: /* @__PURE__ */ jsxRuntime.jsx(strapiAdmin.BackButton, {}),
1169
+ navigationAction: /* @__PURE__ */ jsxRuntime.jsx(strapiAdmin.BackButton, { fallback: ".." }),
1215
1170
  primaryAction: canUpdate || canCreate ? /* @__PURE__ */ jsxRuntime.jsx(
1216
1171
  designSystem.Button,
1217
1172
  {
1218
1173
  startIcon: /* @__PURE__ */ jsxRuntime.jsx(icons.Check, {}),
1219
1174
  type: "submit",
1220
- size: "M",
1221
1175
  disabled: !modified || isSubmitting || values.stages.length === 0,
1222
1176
  loading: !Boolean(Object.keys(savePrompts).length > 0) && isSubmitting,
1223
1177
  children: formatMessage({
@@ -1240,23 +1194,22 @@ const EditPage = () => {
1240
1194
  }
1241
1195
  ),
1242
1196
  /* @__PURE__ */ jsxRuntime.jsx(Layout.Root, { children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { alignItems: "stretch", direction: "column", gap: 7, children: [
1243
- /* @__PURE__ */ jsxRuntime.jsx(WorkflowAttributes, { canUpdate }),
1197
+ /* @__PURE__ */ jsxRuntime.jsx(WorkflowAttributes, { canUpdate: canUpdate || canCreate }),
1244
1198
  /* @__PURE__ */ jsxRuntime.jsx(
1245
1199
  Stages,
1246
1200
  {
1247
1201
  canDelete,
1248
- canUpdate,
1202
+ canUpdate: canUpdate || canCreate,
1249
1203
  isCreating: isCreatingWorkflow
1250
1204
  }
1251
1205
  )
1252
1206
  ] }) }),
1253
1207
  /* @__PURE__ */ jsxRuntime.jsx(
1254
- strapiAdmin.ConfirmDialog,
1208
+ designSystem.Dialog.Root,
1255
1209
  {
1256
- isOpen: Object.keys(savePrompts).length > 0,
1257
- onClose: handleConfirmClose,
1258
- onConfirm: handleConfirmDeleteDialog(values, { setErrors }),
1259
- children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { direction: "column", gap: 5, children: [
1210
+ open: Object.keys(savePrompts).length > 0,
1211
+ onOpenChange: handleConfirmClose,
1212
+ children: /* @__PURE__ */ jsxRuntime.jsx(strapiAdmin.ConfirmDialog, { onConfirm: handleConfirmDeleteDialog(values, { setErrors }), children: /* @__PURE__ */ jsxRuntime.jsxs(designSystem.Flex, { direction: "column", gap: 5, children: [
1260
1213
  savePrompts.hasDeletedServerStages && /* @__PURE__ */ jsxRuntime.jsx(designSystem.Typography, { textAlign: "center", variant: "omega", children: formatMessage({
1261
1214
  id: "review-workflows.page.delete.confirm.stages.body",
1262
1215
  defaultMessage: "All entries assigned to deleted stages will be moved to the previous stage."
@@ -1268,7 +1221,7 @@ const EditPage = () => {
1268
1221
  },
1269
1222
  {
1270
1223
  count: contentTypesFromOtherWorkflows?.filter(
1271
- (contentType) => currentWorkflow?.contentTypes?.includes(contentType)
1224
+ (contentType) => values.contentTypes.includes(contentType)
1272
1225
  ).length ?? 0
1273
1226
  }
1274
1227
  ) }),
@@ -1276,7 +1229,7 @@ const EditPage = () => {
1276
1229
  id: "review-workflows.page.delete.confirm.confirm",
1277
1230
  defaultMessage: "Are you sure you want to save?"
1278
1231
  }) })
1279
- ] })
1232
+ ] }) })
1280
1233
  }
1281
1234
  )
1282
1235
  ] })
@@ -1285,8 +1238,8 @@ const EditPage = () => {
1285
1238
  /* @__PURE__ */ jsxRuntime.jsxs(
1286
1239
  index.LimitsModal.Root,
1287
1240
  {
1288
- isOpen: showLimitModal === "workflow",
1289
- onClose: () => setShowLimitModal(null),
1241
+ open: showLimitModal === "workflow",
1242
+ onOpenChange: () => setShowLimitModal(null),
1290
1243
  children: [
1291
1244
  /* @__PURE__ */ jsxRuntime.jsx(index.LimitsModal.Title, { children: formatMessage({
1292
1245
  id: "review-workflows.edit.page.workflows.limit.title",
@@ -1299,16 +1252,23 @@ const EditPage = () => {
1299
1252
  ]
1300
1253
  }
1301
1254
  ),
1302
- /* @__PURE__ */ jsxRuntime.jsxs(index.LimitsModal.Root, { isOpen: showLimitModal === "stage", onClose: () => setShowLimitModal(null), children: [
1303
- /* @__PURE__ */ jsxRuntime.jsx(index.LimitsModal.Title, { children: formatMessage({
1304
- id: "review-workflows.edit.page.stages.limit.title",
1305
- defaultMessage: "You have reached the limit of stages for this workflow in your plan"
1306
- }) }),
1307
- /* @__PURE__ */ jsxRuntime.jsx(index.LimitsModal.Body, { children: formatMessage({
1308
- id: "review-workflows.edit.page.stages.limit.body",
1309
- defaultMessage: "Try deleting some stages or contact Sales to enable more stages."
1310
- }) })
1311
- ] })
1255
+ /* @__PURE__ */ jsxRuntime.jsxs(
1256
+ index.LimitsModal.Root,
1257
+ {
1258
+ open: showLimitModal === "stage",
1259
+ onOpenChange: () => setShowLimitModal(null),
1260
+ children: [
1261
+ /* @__PURE__ */ jsxRuntime.jsx(index.LimitsModal.Title, { children: formatMessage({
1262
+ id: "review-workflows.edit.page.stages.limit.title",
1263
+ defaultMessage: "You have reached the limit of stages for this workflow in your plan"
1264
+ }) }),
1265
+ /* @__PURE__ */ jsxRuntime.jsx(index.LimitsModal.Body, { children: formatMessage({
1266
+ id: "review-workflows.edit.page.stages.limit.body",
1267
+ defaultMessage: "Try deleting some stages or contact Sales to enable more stages."
1268
+ }) })
1269
+ ]
1270
+ }
1271
+ )
1312
1272
  ] });
1313
1273
  };
1314
1274
  const addTmpKeysToStages = (data) => {
@@ -1330,4 +1290,4 @@ const ProtectedEditPage = () => {
1330
1290
  return /* @__PURE__ */ jsxRuntime.jsx(strapiAdmin.Page.Protect, { permissions, children: /* @__PURE__ */ jsxRuntime.jsx(EditPage, {}) });
1331
1291
  };
1332
1292
  exports.ProtectedEditPage = ProtectedEditPage;
1333
- //# sourceMappingURL=_id-B6DgrtpA.js.map
1293
+ //# sourceMappingURL=id-oOE1bYls.js.map