@dyrected/core 2.7.1 → 2.8.1

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 (53) hide show
  1. package/dist/app-config-7G-3tF_I.d.cts +2259 -0
  2. package/dist/app-config-7G-3tF_I.d.ts +2259 -0
  3. package/dist/app-config-B3ByBjCN.d.cts +2222 -0
  4. package/dist/app-config-B3ByBjCN.d.ts +2222 -0
  5. package/dist/app-config-B5tYsZaH.d.cts +2404 -0
  6. package/dist/app-config-B5tYsZaH.d.ts +2404 -0
  7. package/dist/app-config-BEuyPktb.d.cts +2556 -0
  8. package/dist/app-config-BEuyPktb.d.ts +2556 -0
  9. package/dist/app-config-BIkjQWzU.d.cts +2218 -0
  10. package/dist/app-config-BIkjQWzU.d.ts +2218 -0
  11. package/dist/app-config-BfpeE3bF.d.cts +2100 -0
  12. package/dist/app-config-BfpeE3bF.d.ts +2100 -0
  13. package/dist/app-config-CCe-yq9q.d.cts +2222 -0
  14. package/dist/app-config-CCe-yq9q.d.ts +2222 -0
  15. package/dist/app-config-CPOs7THF.d.cts +2217 -0
  16. package/dist/app-config-CPOs7THF.d.ts +2217 -0
  17. package/dist/app-config-Ctp454zB.d.cts +2214 -0
  18. package/dist/app-config-Ctp454zB.d.ts +2214 -0
  19. package/dist/app-config-DJmNYgYh.d.cts +2305 -0
  20. package/dist/app-config-DJmNYgYh.d.ts +2305 -0
  21. package/dist/app-config-DO3laV58.d.cts +2397 -0
  22. package/dist/app-config-DO3laV58.d.ts +2397 -0
  23. package/dist/app-config-DZf_mmi9.d.cts +2211 -0
  24. package/dist/app-config-DZf_mmi9.d.ts +2211 -0
  25. package/dist/app-config-SkUoN5JU.d.cts +2192 -0
  26. package/dist/app-config-SkUoN5JU.d.ts +2192 -0
  27. package/dist/app-config-WzqpuZMr.d.cts +2566 -0
  28. package/dist/app-config-WzqpuZMr.d.ts +2566 -0
  29. package/dist/app-config-fEjRm1o9.d.cts +2402 -0
  30. package/dist/app-config-fEjRm1o9.d.ts +2402 -0
  31. package/dist/app-config-oz8H_MOX.d.cts +2224 -0
  32. package/dist/app-config-oz8H_MOX.d.ts +2224 -0
  33. package/dist/chunk-3TRRTN6U.js +3441 -0
  34. package/dist/chunk-5ZIA5COH.js +3414 -0
  35. package/dist/chunk-6TWQ6GTD.js +3480 -0
  36. package/dist/chunk-AQO4HI2Y.js +3204 -0
  37. package/dist/chunk-DFBLNYUH.js +3402 -0
  38. package/dist/chunk-GFFGDHST.js +3543 -0
  39. package/dist/chunk-KEKOEAX6.js +3139 -0
  40. package/dist/chunk-PRQ2RF5C.js +3485 -0
  41. package/dist/chunk-PZMDK3MH.js +3203 -0
  42. package/dist/chunk-SM32ND5M.js +3472 -0
  43. package/dist/chunk-XX7N64NL.js +3550 -0
  44. package/dist/chunk-ZISFMAEL.js +3550 -0
  45. package/dist/index.cjs +439 -9
  46. package/dist/index.d.cts +166 -3
  47. package/dist/index.d.ts +166 -3
  48. package/dist/index.js +53 -1
  49. package/dist/server.cjs +623 -367
  50. package/dist/server.d.cts +26 -7
  51. package/dist/server.d.ts +26 -7
  52. package/dist/server.js +420 -359
  53. package/package.json +1 -1
package/dist/index.cjs CHANGED
@@ -549,6 +549,7 @@ __export(index_exports, {
549
549
  LIFECYCLE_EVENTS_COLLECTION: () => LIFECYCLE_EVENTS_COLLECTION,
550
550
  LIFECYCLE_EVENT_NAMES: () => LIFECYCLE_EVENT_NAMES,
551
551
  WORKFLOW_HISTORY_COLLECTION: () => WORKFLOW_HISTORY_COLLECTION,
552
+ abs: () => abs,
552
553
  addDays: () => addDays,
553
554
  assertValidAdminConditionsInConfig: () => assertValidAdminConditionsInConfig,
554
555
  assertValidDeclarativeAccessInConfig: () => assertValidDeclarativeAccessInConfig,
@@ -560,6 +561,7 @@ __export(index_exports, {
560
561
  buildSqlOrderBy: () => buildSqlOrderBy,
561
562
  canViewWorkflowDraft: () => canViewWorkflowDraft,
562
563
  capitalize: () => capitalize,
564
+ ceil: () => ceil,
563
565
  clamp: () => clamp,
564
566
  coalesce: () => coalesce,
565
567
  collectAdminConditionValidationIssues: () => collectAdminConditionValidationIssues,
@@ -568,6 +570,7 @@ __export(index_exports, {
568
570
  collectDeclarativeHookValidationIssues: () => collectDeclarativeHookValidationIssues,
569
571
  collectPreviewUrlValidationIssues: () => collectPreviewUrlValidationIssues,
570
572
  compact: () => compact,
573
+ count: () => count,
571
574
  createLifecycleEvent: () => createLifecycleEvent,
572
575
  createWorkflowDocument: () => createWorkflowDocument,
573
576
  defaultValue: () => defaultValue,
@@ -603,12 +606,28 @@ __export(index_exports, {
603
606
  diffDays: () => diffDays,
604
607
  dispatchLifecycleEvent: () => dispatchLifecycleEvent,
605
608
  dispatchPendingLifecycleEvents: () => dispatchPendingLifecycleEvents,
609
+ displayComputed: () => displayComputed,
610
+ displayCustom: () => displayCustom,
611
+ displayCustomComponent: () => displayCustomComponent,
612
+ displayDivider: () => displayDivider,
613
+ displayField: () => displayField,
614
+ displayGrid: () => displayGrid,
615
+ displayRepeat: () => displayRepeat,
616
+ displaySection: () => displaySection,
617
+ displayTab: () => displayTab,
618
+ displayTabs: () => displayTabs,
619
+ displayText: () => displayText,
606
620
  endsWith: () => endsWith,
621
+ evaluateDetailComputed: () => evaluateDetailComputed,
622
+ evaluateJexl: () => evaluateJexl,
623
+ evaluateJexlSync: () => evaluateJexlSync,
607
624
  executeFieldAfterRead: () => executeFieldAfterRead,
608
625
  executeFieldBeforeChange: () => executeFieldBeforeChange,
609
626
  first: () => first,
627
+ floor: () => floor,
610
628
  formatConfigDiagnostics: () => formatConfigDiagnostics,
611
629
  formatDate: () => formatDate,
630
+ generateDefaultDetailSchema: () => generateDefaultDetailSchema,
612
631
  generateOpenApi: () => generateOpenApi,
613
632
  get: () => get,
614
633
  getAdminAuthCollection: () => getAdminAuthCollection,
@@ -616,6 +635,7 @@ __export(index_exports, {
616
635
  includes: () => includes,
617
636
  initializeWorkflowDocument: () => initializeWorkflowDocument,
618
637
  isConfigValidationError: () => isConfigValidationError,
638
+ isDetailItemVisible: () => isDetailItemVisible,
619
639
  isEmpty: () => isEmpty,
620
640
  isFuture: () => isFuture,
621
641
  isPast: () => isPast,
@@ -624,12 +644,16 @@ __export(index_exports, {
624
644
  length: () => length,
625
645
  lower: () => lower,
626
646
  materializeWorkflowDocument: () => materializeWorkflowDocument,
647
+ max: () => max,
648
+ min: () => min,
627
649
  normalizeConfig: () => normalizeConfig,
650
+ normalizeDetailItem: () => normalizeDetailItem,
628
651
  now: () => now,
629
652
  numericFieldNames: () => numericFieldNames,
630
653
  parseMongoWhere: () => parseMongoWhere,
631
654
  parseSort: () => parseSort,
632
655
  parseSqlWhere: () => parseSqlWhere,
656
+ pow: () => pow,
633
657
  publishedStateName: () => publishedStateName,
634
658
  publishingWorkflow: () => publishingWorkflow,
635
659
  readingTime: () => readingTime,
@@ -641,7 +665,9 @@ __export(index_exports, {
641
665
  saveWorkflowDraft: () => saveWorkflowDraft,
642
666
  simplePublishingWorkflow: () => simplePublishingWorkflow,
643
667
  slugify: () => slugify,
668
+ sqrt: () => sqrt,
644
669
  startsWith: () => startsWith,
670
+ sum: () => sum,
645
671
  today: () => today,
646
672
  transitionWorkflow: () => transitionWorkflow,
647
673
  trim: () => trim,
@@ -1361,9 +1387,42 @@ function round(val, decimals = 0) {
1361
1387
  }
1362
1388
  function clamp(val, minVal, maxVal) {
1363
1389
  const num = Number(val) || 0;
1364
- const min = Number(minVal) || 0;
1365
- const max = Number(maxVal) || 0;
1366
- return Math.min(Math.max(num, min), max);
1390
+ const min2 = Number(minVal) || 0;
1391
+ const max2 = Number(maxVal) || 0;
1392
+ return Math.min(Math.max(num, min2), max2);
1393
+ }
1394
+ function ceil(val) {
1395
+ return Math.ceil(Number(val) || 0);
1396
+ }
1397
+ function floor(val) {
1398
+ return Math.floor(Number(val) || 0);
1399
+ }
1400
+ function abs(val) {
1401
+ return Math.abs(Number(val) || 0);
1402
+ }
1403
+ function min(...args) {
1404
+ const nums = args.flat().map((n) => Number(n) || 0);
1405
+ return nums.length ? Math.min(...nums) : 0;
1406
+ }
1407
+ function max(...args) {
1408
+ const nums = args.flat().map((n) => Number(n) || 0);
1409
+ return nums.length ? Math.max(...nums) : 0;
1410
+ }
1411
+ function pow(base, exp) {
1412
+ return Math.pow(Number(base) || 0, Number(exp) || 0);
1413
+ }
1414
+ function sqrt(val) {
1415
+ return Math.sqrt(Number(val) || 0);
1416
+ }
1417
+ function sum(arr) {
1418
+ if (!Array.isArray(arr)) return Number(arr) || 0;
1419
+ return arr.reduce((acc, val) => acc + (Number(val) || 0), 0);
1420
+ }
1421
+ function count(val) {
1422
+ if (Array.isArray(val)) return val.length;
1423
+ if (typeof val === "string") return val.length;
1424
+ if (val !== void 0 && val !== null && val !== false) return 1;
1425
+ return 0;
1367
1426
  }
1368
1427
  function defaultValue(val, fallback) {
1369
1428
  if (val === void 0 || val === null || val === "") return fallback;
@@ -1382,13 +1441,12 @@ function isEmpty(val) {
1382
1441
  return false;
1383
1442
  }
1384
1443
  function get(obj, path, fallback = null) {
1385
- if (!obj || typeof obj !== "object") return fallback;
1386
- const pathStr = String(path || "").trim();
1387
- if (!pathStr) return fallback;
1388
- const parts = pathStr.split(".");
1444
+ if (obj === void 0 || obj === null || typeof obj !== "object") return fallback;
1445
+ if (typeof path !== "string") return fallback;
1446
+ const parts = path.split(".").filter(Boolean);
1389
1447
  let curr = obj;
1390
1448
  for (const part of parts) {
1391
- if (curr === void 0 || curr === null) return fallback;
1449
+ if (curr === void 0 || curr === null || typeof curr !== "object") return fallback;
1392
1450
  curr = curr[part];
1393
1451
  }
1394
1452
  return curr === void 0 || curr === null ? fallback : curr;
@@ -1426,6 +1484,15 @@ function registerJexlHelpers(jexlInstance = import_jexl.default) {
1426
1484
  // Math
1427
1485
  round,
1428
1486
  clamp,
1487
+ ceil,
1488
+ floor,
1489
+ abs,
1490
+ min,
1491
+ max,
1492
+ pow,
1493
+ sqrt,
1494
+ sum,
1495
+ count,
1429
1496
  // Objects & Logical
1430
1497
  default: defaultValue,
1431
1498
  coalesce,
@@ -1437,9 +1504,48 @@ function registerJexlHelpers(jexlInstance = import_jexl.default) {
1437
1504
  jexlInstance.addFunction(name, fn);
1438
1505
  } catch {
1439
1506
  }
1507
+ try {
1508
+ jexlInstance.addTransform(name, fn);
1509
+ } catch {
1510
+ }
1511
+ }
1512
+ try {
1513
+ jexlInstance.addBinaryOp("and", 20, (left, right) => Boolean(left && right));
1514
+ jexlInstance.addBinaryOp("or", 10, (left, right) => Boolean(left || right));
1515
+ } catch {
1440
1516
  }
1441
1517
  }
1442
1518
  registerJexlHelpers(import_jexl.default);
1519
+ async function evaluateJexl(expression, context = {}) {
1520
+ if (!expression || typeof expression !== "string") return void 0;
1521
+ try {
1522
+ const evalContext = {
1523
+ null: null,
1524
+ undefined: void 0,
1525
+ ...context,
1526
+ math: Math,
1527
+ Math
1528
+ };
1529
+ return await import_jexl.default.eval(expression, evalContext);
1530
+ } catch (_err) {
1531
+ return void 0;
1532
+ }
1533
+ }
1534
+ function evaluateJexlSync(expression, context = {}) {
1535
+ if (!expression || typeof expression !== "string") return void 0;
1536
+ try {
1537
+ const evalContext = {
1538
+ null: null,
1539
+ undefined: void 0,
1540
+ ...context,
1541
+ math: Math,
1542
+ Math
1543
+ };
1544
+ return import_jexl.default.evalSync(expression, evalContext);
1545
+ } catch (_err) {
1546
+ return void 0;
1547
+ }
1548
+ }
1443
1549
  var BUILTIN_JEXL_HELPERS = [
1444
1550
  // Strings
1445
1551
  "slugify",
@@ -2021,7 +2127,7 @@ function collectConfigDiagnostics(config) {
2021
2127
  function formatConfigDiagnostics(source, diagnostics, options = {}) {
2022
2128
  const color = options.color ?? false;
2023
2129
  const header = `${colorize("Config validation failed", 31, color)} in ${colorize(source, 36, color)}`;
2024
- const docLink = `${colorize(" Learn how to write declarative rules:", 90, color)} ${colorize("https://docs.dyrected.com/docs/features/admin/form-and-field-hooks", 34, color)}`;
2130
+ const docLink = `${colorize(" Learn how to write declarative rules:", 90, color)} ${colorize("https://docs.dyrected.com/docs/editor-experience/form-and-field-hooks", 34, color)}`;
2025
2131
  const lines = diagnostics.flatMap((issue, index) => [
2026
2132
  `${colorize(`${index + 1}.`, 31, color)} ${colorize(issue.path, 1, color)}`,
2027
2133
  ` ${issue.message}`,
@@ -3236,6 +3342,71 @@ function generateOpenApi(config) {
3236
3342
  responses: { 200: { description: "Deleted and failed document IDs" } }
3237
3343
  }
3238
3344
  };
3345
+ spec.paths[`${path}/aggregate`] = {
3346
+ post: {
3347
+ tags: [collectionTag],
3348
+ summary: `Aggregate ${labels.plural}`,
3349
+ description: `Compute statistical aggregations (count, sum, avg, min, max) across ${labels.plural}.`,
3350
+ requestBody: {
3351
+ required: true,
3352
+ content: {
3353
+ "application/json": {
3354
+ schema: {
3355
+ type: "object",
3356
+ additionalProperties: {
3357
+ type: "object",
3358
+ properties: {
3359
+ count: { type: "string", example: "*" },
3360
+ sum: { type: "string", description: "Field to sum" },
3361
+ avg: { type: "string", description: "Field to average" },
3362
+ min: { type: "string", description: "Field for minimum" },
3363
+ max: { type: "string", description: "Field for maximum" },
3364
+ cast: {
3365
+ type: "string",
3366
+ enum: [
3367
+ "number",
3368
+ "integer",
3369
+ "float",
3370
+ "boolean",
3371
+ "date",
3372
+ "string"
3373
+ ]
3374
+ },
3375
+ where: {
3376
+ type: "object",
3377
+ description: "Per-aggregate filter condition",
3378
+ additionalProperties: true
3379
+ }
3380
+ }
3381
+ }
3382
+ }
3383
+ }
3384
+ }
3385
+ },
3386
+ responses: {
3387
+ 200: {
3388
+ description: "Success",
3389
+ content: {
3390
+ "application/json": {
3391
+ schema: {
3392
+ type: "object",
3393
+ additionalProperties: {
3394
+ type: "number",
3395
+ nullable: true
3396
+ }
3397
+ }
3398
+ }
3399
+ }
3400
+ },
3401
+ 400: {
3402
+ description: "Bad Request - Invalid aggregate input"
3403
+ },
3404
+ 403: {
3405
+ description: "Forbidden - Access denied by read rule"
3406
+ }
3407
+ }
3408
+ }
3409
+ };
3239
3410
  if (collection.audit) {
3240
3411
  spec.paths[`${path}/__audit`] = {
3241
3412
  get: {
@@ -3763,6 +3934,239 @@ function fieldToSchema(field) {
3763
3934
  return schema;
3764
3935
  }
3765
3936
 
3937
+ // src/detail.ts
3938
+ function normalizeDetailItem(item) {
3939
+ if (typeof item === "string") {
3940
+ return {
3941
+ type: "field",
3942
+ field: item
3943
+ };
3944
+ }
3945
+ return item;
3946
+ }
3947
+ function displaySection(title, items, options) {
3948
+ return {
3949
+ type: "section",
3950
+ title,
3951
+ items,
3952
+ options
3953
+ };
3954
+ }
3955
+ function displayTab(label, items, options) {
3956
+ return {
3957
+ type: "tab",
3958
+ label,
3959
+ items,
3960
+ options
3961
+ };
3962
+ }
3963
+ function displayTabs(tabs, options) {
3964
+ return {
3965
+ type: "tabs",
3966
+ tabs,
3967
+ options
3968
+ };
3969
+ }
3970
+ function displayGrid(columns, items, options) {
3971
+ return {
3972
+ type: "grid",
3973
+ columns,
3974
+ items,
3975
+ options
3976
+ };
3977
+ }
3978
+ function displayField(fieldName, options) {
3979
+ return {
3980
+ type: "field",
3981
+ field: fieldName,
3982
+ options
3983
+ };
3984
+ }
3985
+ function displayRepeat(fieldName, items, options) {
3986
+ return {
3987
+ type: "repeat",
3988
+ field: fieldName,
3989
+ items,
3990
+ options
3991
+ };
3992
+ }
3993
+ function displayComputed(label, expressionOrOptionsOrHandler, options) {
3994
+ let expression;
3995
+ let handler;
3996
+ let finalOptions = options;
3997
+ if (typeof expressionOrOptionsOrHandler === "string") {
3998
+ expression = expressionOrOptionsOrHandler;
3999
+ } else if (typeof expressionOrOptionsOrHandler === "function") {
4000
+ handler = expressionOrOptionsOrHandler;
4001
+ } else if (expressionOrOptionsOrHandler && typeof expressionOrOptionsOrHandler === "object") {
4002
+ expression = expressionOrOptionsOrHandler.expression;
4003
+ handler = expressionOrOptionsOrHandler.handler;
4004
+ finalOptions = {
4005
+ ...expressionOrOptionsOrHandler,
4006
+ ...options
4007
+ };
4008
+ }
4009
+ const id = finalOptions?.id || label.toLowerCase().trim().replace(/[^a-z0-9]+/g, "_");
4010
+ return {
4011
+ type: "computed",
4012
+ id,
4013
+ label,
4014
+ expression,
4015
+ handler,
4016
+ options: finalOptions
4017
+ };
4018
+ }
4019
+ function displayDivider(options) {
4020
+ return {
4021
+ type: "divider",
4022
+ options
4023
+ };
4024
+ }
4025
+ function displayText(content, options) {
4026
+ return {
4027
+ type: "text",
4028
+ content,
4029
+ options
4030
+ };
4031
+ }
4032
+ function displayCustom(name, options) {
4033
+ return {
4034
+ type: "custom",
4035
+ name,
4036
+ options
4037
+ };
4038
+ }
4039
+ function displayCustomComponent(name, options) {
4040
+ return displayCustom(name, options);
4041
+ }
4042
+ async function evaluateDetailComputed(detail, doc, user, db) {
4043
+ if (!doc || !detail || !Array.isArray(detail)) {
4044
+ return doc;
4045
+ }
4046
+ const computedItems = [];
4047
+ const extractComputed = (items) => {
4048
+ for (const rawItem of items) {
4049
+ if (!rawItem) continue;
4050
+ const item = normalizeDetailItem(rawItem);
4051
+ if (item.type === "computed") {
4052
+ const id = item.id || item.label?.toLowerCase().replace(/[^a-z0-9]+/g, "_");
4053
+ if (id) {
4054
+ computedItems.push({
4055
+ id,
4056
+ label: item.label,
4057
+ expression: item.expression,
4058
+ handler: item.handler
4059
+ });
4060
+ }
4061
+ } else if (item.type === "section" || item.type === "grid" || item.type === "repeat") {
4062
+ if (item.items && Array.isArray(item.items)) {
4063
+ extractComputed(item.items);
4064
+ }
4065
+ } else if (item.type === "tabs" && item.tabs && Array.isArray(item.tabs)) {
4066
+ for (const tab of item.tabs) {
4067
+ if (tab.items) extractComputed(tab.items);
4068
+ }
4069
+ }
4070
+ }
4071
+ };
4072
+ extractComputed(detail);
4073
+ if (computedItems.length === 0) return doc;
4074
+ const evaluated = {};
4075
+ for (const item of computedItems) {
4076
+ try {
4077
+ if (typeof item.handler === "function") {
4078
+ evaluated[item.id] = await item.handler({ doc, user, db });
4079
+ } else if (item.expression) {
4080
+ evaluated[item.id] = await evaluateJexl(item.expression, { doc, user });
4081
+ }
4082
+ } catch (_err) {
4083
+ evaluated[item.id] = null;
4084
+ }
4085
+ }
4086
+ return {
4087
+ ...doc,
4088
+ _meta: {
4089
+ ...doc._meta || {},
4090
+ computed: evaluated
4091
+ }
4092
+ };
4093
+ }
4094
+ var SENSITIVE_DETAIL_FIELDS = /* @__PURE__ */ new Set([
4095
+ "password",
4096
+ "salt",
4097
+ "resetPasswordToken",
4098
+ "resetPasswordExpires",
4099
+ "loginAttempts",
4100
+ "lockUntil",
4101
+ "apiKey",
4102
+ "secret"
4103
+ ]);
4104
+ function generateDefaultDetailSchema(schema) {
4105
+ const fields = schema.fields || [];
4106
+ const sidebarFieldTypes = /* @__PURE__ */ new Set(["select", "radio", "boolean", "date", "datetime", "relationship"]);
4107
+ const mainFields = [];
4108
+ const sidebarFields = [];
4109
+ for (const field of fields) {
4110
+ if (!field.name) continue;
4111
+ if (SENSITIVE_DETAIL_FIELDS.has(field.name)) continue;
4112
+ if (field.hidden) continue;
4113
+ if (field.admin?.hidden) continue;
4114
+ const isSidebar = sidebarFieldTypes.has(field.type) && field.type !== "relationship" && !field.hasMany;
4115
+ if (isSidebar && sidebarFields.length < 5) {
4116
+ sidebarFields.push(
4117
+ displayField(field.name, {
4118
+ span: 12,
4119
+ display: field.type === "select" || field.type === "radio" ? "badge" : void 0
4120
+ })
4121
+ );
4122
+ } else {
4123
+ const span = field.type === "richText" || field.type === "blocks" || field.type === "textarea" || field.type === "array" || field.type === "json" || field.type === "object" ? 12 : 6;
4124
+ mainFields.push(
4125
+ displayField(field.name, {
4126
+ span
4127
+ })
4128
+ );
4129
+ }
4130
+ }
4131
+ const sections = [];
4132
+ const mainTitle = schema.labels?.singular || schema.label || "Details";
4133
+ if (sidebarFields.length > 0) {
4134
+ sections.push(
4135
+ displaySection(mainTitle, mainFields, {
4136
+ span: 8
4137
+ })
4138
+ );
4139
+ sections.push(
4140
+ displaySection("Overview", sidebarFields, {
4141
+ span: 4
4142
+ })
4143
+ );
4144
+ } else {
4145
+ sections.push(
4146
+ displaySection(mainTitle, mainFields, {
4147
+ span: 12
4148
+ })
4149
+ );
4150
+ }
4151
+ return sections;
4152
+ }
4153
+ function isDetailItemVisible(item, doc, user) {
4154
+ if (!item) return true;
4155
+ const it = normalizeDetailItem(item);
4156
+ const visible = it.options?.visible;
4157
+ if (visible === void 0 || visible === null) return true;
4158
+ if (typeof visible === "boolean") return visible;
4159
+ if (typeof visible === "string") {
4160
+ if (visible.trim().length === 0) return true;
4161
+ try {
4162
+ return Boolean(evaluateJexlSync(visible, { doc, user }));
4163
+ } catch {
4164
+ return true;
4165
+ }
4166
+ }
4167
+ return true;
4168
+ }
4169
+
3766
4170
  // src/index.ts
3767
4171
  function defineCollection(config) {
3768
4172
  return config;
@@ -3817,6 +4221,7 @@ function defineTab(args) {
3817
4221
  LIFECYCLE_EVENTS_COLLECTION,
3818
4222
  LIFECYCLE_EVENT_NAMES,
3819
4223
  WORKFLOW_HISTORY_COLLECTION,
4224
+ abs,
3820
4225
  addDays,
3821
4226
  assertValidAdminConditionsInConfig,
3822
4227
  assertValidDeclarativeAccessInConfig,
@@ -3828,6 +4233,7 @@ function defineTab(args) {
3828
4233
  buildSqlOrderBy,
3829
4234
  canViewWorkflowDraft,
3830
4235
  capitalize,
4236
+ ceil,
3831
4237
  clamp,
3832
4238
  coalesce,
3833
4239
  collectAdminConditionValidationIssues,
@@ -3836,6 +4242,7 @@ function defineTab(args) {
3836
4242
  collectDeclarativeHookValidationIssues,
3837
4243
  collectPreviewUrlValidationIssues,
3838
4244
  compact,
4245
+ count,
3839
4246
  createLifecycleEvent,
3840
4247
  createWorkflowDocument,
3841
4248
  defaultValue,
@@ -3871,12 +4278,28 @@ function defineTab(args) {
3871
4278
  diffDays,
3872
4279
  dispatchLifecycleEvent,
3873
4280
  dispatchPendingLifecycleEvents,
4281
+ displayComputed,
4282
+ displayCustom,
4283
+ displayCustomComponent,
4284
+ displayDivider,
4285
+ displayField,
4286
+ displayGrid,
4287
+ displayRepeat,
4288
+ displaySection,
4289
+ displayTab,
4290
+ displayTabs,
4291
+ displayText,
3874
4292
  endsWith,
4293
+ evaluateDetailComputed,
4294
+ evaluateJexl,
4295
+ evaluateJexlSync,
3875
4296
  executeFieldAfterRead,
3876
4297
  executeFieldBeforeChange,
3877
4298
  first,
4299
+ floor,
3878
4300
  formatConfigDiagnostics,
3879
4301
  formatDate,
4302
+ generateDefaultDetailSchema,
3880
4303
  generateOpenApi,
3881
4304
  get,
3882
4305
  getAdminAuthCollection,
@@ -3884,6 +4307,7 @@ function defineTab(args) {
3884
4307
  includes,
3885
4308
  initializeWorkflowDocument,
3886
4309
  isConfigValidationError,
4310
+ isDetailItemVisible,
3887
4311
  isEmpty,
3888
4312
  isFuture,
3889
4313
  isPast,
@@ -3892,12 +4316,16 @@ function defineTab(args) {
3892
4316
  length,
3893
4317
  lower,
3894
4318
  materializeWorkflowDocument,
4319
+ max,
4320
+ min,
3895
4321
  normalizeConfig,
4322
+ normalizeDetailItem,
3896
4323
  now,
3897
4324
  numericFieldNames,
3898
4325
  parseMongoWhere,
3899
4326
  parseSort,
3900
4327
  parseSqlWhere,
4328
+ pow,
3901
4329
  publishedStateName,
3902
4330
  publishingWorkflow,
3903
4331
  readingTime,
@@ -3909,7 +4337,9 @@ function defineTab(args) {
3909
4337
  saveWorkflowDraft,
3910
4338
  simplePublishingWorkflow,
3911
4339
  slugify,
4340
+ sqrt,
3912
4341
  startsWith,
4342
+ sum,
3913
4343
  today,
3914
4344
  transitionWorkflow,
3915
4345
  trim,