@dyrected/core 2.6.3 → 2.7.0

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 (354) hide show
  1. package/dist/__tests__/access-features.test.d.ts +2 -0
  2. package/dist/__tests__/access-features.test.d.ts.map +1 -0
  3. package/dist/__tests__/access-features.test.js +159 -0
  4. package/dist/__tests__/access-features.test.js.map +1 -0
  5. package/dist/__tests__/access-parity.test.d.ts +2 -0
  6. package/dist/__tests__/access-parity.test.d.ts.map +1 -0
  7. package/dist/__tests__/access-parity.test.js +338 -0
  8. package/dist/__tests__/access-parity.test.js.map +1 -0
  9. package/dist/__tests__/access.test.d.ts +2 -0
  10. package/dist/__tests__/access.test.d.ts.map +1 -0
  11. package/dist/__tests__/access.test.js +137 -0
  12. package/dist/__tests__/access.test.js.map +1 -0
  13. package/dist/__tests__/admin-auth.test.d.ts +2 -0
  14. package/dist/__tests__/admin-auth.test.d.ts.map +1 -0
  15. package/dist/__tests__/admin-auth.test.js +440 -0
  16. package/dist/__tests__/admin-auth.test.js.map +1 -0
  17. package/dist/__tests__/app.test.d.ts +2 -0
  18. package/dist/__tests__/app.test.d.ts.map +1 -0
  19. package/dist/__tests__/app.test.js +112 -0
  20. package/dist/__tests__/app.test.js.map +1 -0
  21. package/dist/__tests__/audit.test.d.ts +2 -0
  22. package/dist/__tests__/audit.test.d.ts.map +1 -0
  23. package/dist/__tests__/audit.test.js +125 -0
  24. package/dist/__tests__/audit.test.js.map +1 -0
  25. package/dist/__tests__/auth-hydration.test.d.ts +2 -0
  26. package/dist/__tests__/auth-hydration.test.d.ts.map +1 -0
  27. package/dist/__tests__/auth-hydration.test.js +90 -0
  28. package/dist/__tests__/auth-hydration.test.js.map +1 -0
  29. package/dist/__tests__/auth-invite.test.d.ts +2 -0
  30. package/dist/__tests__/auth-invite.test.d.ts.map +1 -0
  31. package/dist/__tests__/auth-invite.test.js +152 -0
  32. package/dist/__tests__/auth-invite.test.js.map +1 -0
  33. package/dist/__tests__/auth-lockout.test.d.ts +2 -0
  34. package/dist/__tests__/auth-lockout.test.d.ts.map +1 -0
  35. package/dist/__tests__/auth-lockout.test.js +154 -0
  36. package/dist/__tests__/auth-lockout.test.js.map +1 -0
  37. package/dist/__tests__/auth-sessions.test.d.ts +2 -0
  38. package/dist/__tests__/auth-sessions.test.d.ts.map +1 -0
  39. package/dist/__tests__/auth-sessions.test.js +118 -0
  40. package/dist/__tests__/auth-sessions.test.js.map +1 -0
  41. package/dist/__tests__/config.test.d.ts +2 -0
  42. package/dist/__tests__/config.test.d.ts.map +1 -0
  43. package/dist/__tests__/config.test.js +402 -0
  44. package/dist/__tests__/config.test.js.map +1 -0
  45. package/dist/__tests__/define-field.test.d.ts +2 -0
  46. package/dist/__tests__/define-field.test.d.ts.map +1 -0
  47. package/dist/__tests__/define-field.test.js +121 -0
  48. package/dist/__tests__/define-field.test.js.map +1 -0
  49. package/dist/__tests__/deleteMany.test.d.ts +2 -0
  50. package/dist/__tests__/deleteMany.test.d.ts.map +1 -0
  51. package/dist/__tests__/deleteMany.test.js +75 -0
  52. package/dist/__tests__/deleteMany.test.js.map +1 -0
  53. package/dist/__tests__/depth.test.d.ts +2 -0
  54. package/dist/__tests__/depth.test.d.ts.map +1 -0
  55. package/dist/__tests__/depth.test.js +115 -0
  56. package/dist/__tests__/depth.test.js.map +1 -0
  57. package/dist/__tests__/dynamic-options.test.d.ts +2 -0
  58. package/dist/__tests__/dynamic-options.test.d.ts.map +1 -0
  59. package/dist/__tests__/dynamic-options.test.js +168 -0
  60. package/dist/__tests__/dynamic-options.test.js.map +1 -0
  61. package/dist/__tests__/email.service.test.d.ts +2 -0
  62. package/dist/__tests__/email.service.test.d.ts.map +1 -0
  63. package/dist/__tests__/email.service.test.js +52 -0
  64. package/dist/__tests__/email.service.test.js.map +1 -0
  65. package/dist/__tests__/field-inference.test-types.d.ts +161 -0
  66. package/dist/__tests__/field-inference.test-types.d.ts.map +1 -0
  67. package/dist/__tests__/field-inference.test-types.js +87 -0
  68. package/dist/__tests__/field-inference.test-types.js.map +1 -0
  69. package/dist/__tests__/fixtures/editorial-workflow.d.ts +14 -0
  70. package/dist/__tests__/fixtures/editorial-workflow.d.ts.map +1 -0
  71. package/dist/__tests__/fixtures/editorial-workflow.js +12 -0
  72. package/dist/__tests__/fixtures/editorial-workflow.js.map +1 -0
  73. package/dist/__tests__/hooks.test.d.ts +2 -0
  74. package/dist/__tests__/hooks.test.d.ts.map +1 -0
  75. package/dist/__tests__/hooks.test.js +320 -0
  76. package/dist/__tests__/hooks.test.js.map +1 -0
  77. package/dist/__tests__/mocks.d.ts +75 -0
  78. package/dist/__tests__/mocks.d.ts.map +1 -0
  79. package/dist/__tests__/mocks.js +170 -0
  80. package/dist/__tests__/mocks.js.map +1 -0
  81. package/dist/__tests__/observability.test.d.ts +2 -0
  82. package/dist/__tests__/observability.test.d.ts.map +1 -0
  83. package/dist/__tests__/observability.test.js +233 -0
  84. package/dist/__tests__/observability.test.js.map +1 -0
  85. package/dist/__tests__/openapi.test.d.ts +2 -0
  86. package/dist/__tests__/openapi.test.d.ts.map +1 -0
  87. package/dist/__tests__/openapi.test.js +105 -0
  88. package/dist/__tests__/openapi.test.js.map +1 -0
  89. package/dist/__tests__/parse-sort.test.d.ts +2 -0
  90. package/dist/__tests__/parse-sort.test.d.ts.map +1 -0
  91. package/dist/__tests__/parse-sort.test.js +24 -0
  92. package/dist/__tests__/parse-sort.test.js.map +1 -0
  93. package/dist/__tests__/preferences.test.d.ts +2 -0
  94. package/dist/__tests__/preferences.test.d.ts.map +1 -0
  95. package/dist/__tests__/preferences.test.js +168 -0
  96. package/dist/__tests__/preferences.test.js.map +1 -0
  97. package/dist/__tests__/router.test.d.ts +2 -0
  98. package/dist/__tests__/router.test.d.ts.map +1 -0
  99. package/dist/__tests__/router.test.js +70 -0
  100. package/dist/__tests__/router.test.js.map +1 -0
  101. package/dist/__tests__/search.test.d.ts +2 -0
  102. package/dist/__tests__/search.test.d.ts.map +1 -0
  103. package/dist/__tests__/search.test.js +174 -0
  104. package/dist/__tests__/search.test.js.map +1 -0
  105. package/dist/__tests__/upload-validation.test.d.ts +2 -0
  106. package/dist/__tests__/upload-validation.test.d.ts.map +1 -0
  107. package/dist/__tests__/upload-validation.test.js +41 -0
  108. package/dist/__tests__/upload-validation.test.js.map +1 -0
  109. package/dist/__tests__/where.test.d.ts +2 -0
  110. package/dist/__tests__/where.test.d.ts.map +1 -0
  111. package/dist/__tests__/where.test.js +105 -0
  112. package/dist/__tests__/where.test.js.map +1 -0
  113. package/dist/__tests__/workflow.test.d.ts +2 -0
  114. package/dist/__tests__/workflow.test.d.ts.map +1 -0
  115. package/dist/__tests__/workflow.test.js +684 -0
  116. package/dist/__tests__/workflow.test.js.map +1 -0
  117. package/dist/app-config-C9VJ6rTv.d.cts +2092 -0
  118. package/dist/app-config-C9VJ6rTv.d.ts +2092 -0
  119. package/dist/app-config-CYV70eoF.d.cts +2100 -0
  120. package/dist/app-config-CYV70eoF.d.ts +2100 -0
  121. package/dist/app-config-ChsrBB7p.d.cts +2100 -0
  122. package/dist/app-config-ChsrBB7p.d.ts +2100 -0
  123. package/dist/app.d.ts +35 -0
  124. package/dist/app.d.ts.map +1 -0
  125. package/dist/app.js +164 -0
  126. package/dist/app.js.map +1 -0
  127. package/dist/auth/access.d.ts +5 -0
  128. package/dist/auth/access.d.ts.map +1 -0
  129. package/dist/auth/access.js +59 -0
  130. package/dist/auth/access.js.map +1 -0
  131. package/dist/auth/jexl.d.ts +13 -0
  132. package/dist/auth/jexl.d.ts.map +1 -0
  133. package/dist/auth/jexl.js +30 -0
  134. package/dist/auth/jexl.js.map +1 -0
  135. package/dist/auth/lockout.d.ts +11 -0
  136. package/dist/auth/lockout.d.ts.map +1 -0
  137. package/dist/auth/lockout.js +37 -0
  138. package/dist/auth/lockout.js.map +1 -0
  139. package/dist/auth/password.d.ts +10 -0
  140. package/dist/auth/password.d.ts.map +1 -0
  141. package/dist/auth/password.js +28 -0
  142. package/dist/auth/password.js.map +1 -0
  143. package/dist/auth/sessions.d.ts +39 -0
  144. package/dist/auth/sessions.d.ts.map +1 -0
  145. package/dist/auth/sessions.js +126 -0
  146. package/dist/auth/sessions.js.map +1 -0
  147. package/dist/auth/token.d.ts +23 -0
  148. package/dist/auth/token.d.ts.map +1 -0
  149. package/dist/auth/token.js +40 -0
  150. package/dist/auth/token.js.map +1 -0
  151. package/dist/chunk-23NM4LDU.js +2883 -0
  152. package/dist/chunk-2TKDCCIR.js +2622 -0
  153. package/dist/chunk-3SFITPX4.js +2628 -0
  154. package/dist/chunk-CQVTQ67D.js +2632 -0
  155. package/dist/chunk-ELHRRPKX.js +2863 -0
  156. package/dist/chunk-HRLSFTLR.js +3061 -0
  157. package/dist/chunk-QTIAQBNH.js +3097 -0
  158. package/dist/chunk-T2DGC4MD.js +3008 -0
  159. package/dist/chunk-TLU77TLE.js +3203 -0
  160. package/dist/chunk-YEBCT77K.js +3269 -0
  161. package/dist/chunk-YXEKNN5X.js +3085 -0
  162. package/dist/controllers/admin-auth.controller.d.ts +71 -0
  163. package/dist/controllers/admin-auth.controller.d.ts.map +1 -0
  164. package/dist/controllers/admin-auth.controller.js +450 -0
  165. package/dist/controllers/admin-auth.controller.js.map +1 -0
  166. package/dist/controllers/audit.controller.d.ts +42 -0
  167. package/dist/controllers/audit.controller.d.ts.map +1 -0
  168. package/dist/controllers/audit.controller.js +149 -0
  169. package/dist/controllers/audit.controller.js.map +1 -0
  170. package/dist/controllers/auth.controller.d.ts +143 -0
  171. package/dist/controllers/auth.controller.d.ts.map +1 -0
  172. package/dist/controllers/auth.controller.js +572 -0
  173. package/dist/controllers/auth.controller.js.map +1 -0
  174. package/dist/controllers/collection.controller.d.ts +170 -0
  175. package/dist/controllers/collection.controller.d.ts.map +1 -0
  176. package/dist/controllers/collection.controller.js +1033 -0
  177. package/dist/controllers/collection.controller.js.map +1 -0
  178. package/dist/controllers/global.controller.d.ts +20 -0
  179. package/dist/controllers/global.controller.d.ts.map +1 -0
  180. package/dist/controllers/global.controller.js +182 -0
  181. package/dist/controllers/global.controller.js.map +1 -0
  182. package/dist/controllers/media.controller.d.ts +39 -0
  183. package/dist/controllers/media.controller.d.ts.map +1 -0
  184. package/dist/controllers/media.controller.js +178 -0
  185. package/dist/controllers/media.controller.js.map +1 -0
  186. package/dist/controllers/preview.controller.d.ts +37 -0
  187. package/dist/controllers/preview.controller.d.ts.map +1 -0
  188. package/dist/controllers/preview.controller.js +48 -0
  189. package/dist/controllers/preview.controller.js.map +1 -0
  190. package/dist/index.cjs +707 -27
  191. package/dist/index.d.cts +77 -5
  192. package/dist/index.d.ts +77 -5
  193. package/dist/index.d.ts.map +1 -0
  194. package/dist/index.js +37 -1
  195. package/dist/index.js.map +1 -0
  196. package/dist/middleware/auth.d.ts +19 -0
  197. package/dist/middleware/auth.d.ts.map +1 -0
  198. package/dist/middleware/auth.js +157 -0
  199. package/dist/middleware/auth.js.map +1 -0
  200. package/dist/middleware/rate-limit.d.ts +9 -0
  201. package/dist/middleware/rate-limit.d.ts.map +1 -0
  202. package/dist/middleware/rate-limit.js +75 -0
  203. package/dist/middleware/rate-limit.js.map +1 -0
  204. package/dist/network.d.ts +6 -0
  205. package/dist/network.d.ts.map +1 -0
  206. package/dist/network.js +70 -0
  207. package/dist/network.js.map +1 -0
  208. package/dist/observability.d.ts +113 -0
  209. package/dist/observability.d.ts.map +1 -0
  210. package/dist/observability.js +497 -0
  211. package/dist/observability.js.map +1 -0
  212. package/dist/router.d.ts +8 -0
  213. package/dist/router.d.ts.map +1 -0
  214. package/dist/router.js +704 -0
  215. package/dist/router.js.map +1 -0
  216. package/dist/server.cjs +861 -54
  217. package/dist/server.d.cts +9 -1
  218. package/dist/server.d.ts +9 -1
  219. package/dist/server.d.ts.map +1 -0
  220. package/dist/server.js +189 -26
  221. package/dist/server.js.map +1 -0
  222. package/dist/services/audit.service.d.ts +23 -0
  223. package/dist/services/audit.service.d.ts.map +1 -0
  224. package/dist/services/audit.service.js +39 -0
  225. package/dist/services/audit.service.js.map +1 -0
  226. package/dist/services/defaults.service.d.ts +8 -0
  227. package/dist/services/defaults.service.d.ts.map +1 -0
  228. package/dist/services/defaults.service.js +55 -0
  229. package/dist/services/defaults.service.js.map +1 -0
  230. package/dist/services/email-template.d.ts +46 -0
  231. package/dist/services/email-template.d.ts.map +1 -0
  232. package/dist/services/email-template.js +88 -0
  233. package/dist/services/email-template.js.map +1 -0
  234. package/dist/services/email.service.d.ts +34 -0
  235. package/dist/services/email.service.d.ts.map +1 -0
  236. package/dist/services/email.service.js +129 -0
  237. package/dist/services/email.service.js.map +1 -0
  238. package/dist/services/media.service.d.ts +20 -0
  239. package/dist/services/media.service.d.ts.map +1 -0
  240. package/dist/services/media.service.js +49 -0
  241. package/dist/services/media.service.js.map +1 -0
  242. package/dist/services/population.service.d.ts +20 -0
  243. package/dist/services/population.service.d.ts.map +1 -0
  244. package/dist/services/population.service.js +224 -0
  245. package/dist/services/population.service.js.map +1 -0
  246. package/dist/types/access.d.ts +48 -0
  247. package/dist/types/access.d.ts.map +1 -0
  248. package/dist/types/access.js +2 -0
  249. package/dist/types/access.js.map +1 -0
  250. package/dist/types/adapters.d.ts +152 -0
  251. package/dist/types/adapters.d.ts.map +1 -0
  252. package/dist/types/adapters.js +2 -0
  253. package/dist/types/adapters.js.map +1 -0
  254. package/dist/types/admin-auth.d.ts +132 -0
  255. package/dist/types/admin-auth.d.ts.map +1 -0
  256. package/dist/types/admin-auth.js +2 -0
  257. package/dist/types/admin-auth.js.map +1 -0
  258. package/dist/types/admin.d.ts +86 -0
  259. package/dist/types/admin.d.ts.map +1 -0
  260. package/dist/types/admin.js +2 -0
  261. package/dist/types/admin.js.map +1 -0
  262. package/dist/types/app-config.d.ts +279 -0
  263. package/dist/types/app-config.d.ts.map +1 -0
  264. package/dist/types/app-config.js +2 -0
  265. package/dist/types/app-config.js.map +1 -0
  266. package/dist/types/documents.d.ts +65 -0
  267. package/dist/types/documents.d.ts.map +1 -0
  268. package/dist/types/documents.js +2 -0
  269. package/dist/types/documents.js.map +1 -0
  270. package/dist/types/hooks.d.ts +122 -0
  271. package/dist/types/hooks.d.ts.map +1 -0
  272. package/dist/types/hooks.js +2 -0
  273. package/dist/types/hooks.js.map +1 -0
  274. package/dist/types/index.d.ts +13 -0
  275. package/dist/types/index.d.ts.map +1 -0
  276. package/dist/types/index.js +13 -0
  277. package/dist/types/index.js.map +1 -0
  278. package/dist/types/request.d.ts +42 -0
  279. package/dist/types/request.d.ts.map +1 -0
  280. package/dist/types/request.js +2 -0
  281. package/dist/types/request.js.map +1 -0
  282. package/dist/types/schema-config.d.ts +443 -0
  283. package/dist/types/schema-config.d.ts.map +1 -0
  284. package/dist/types/schema-config.js +2 -0
  285. package/dist/types/schema-config.js.map +1 -0
  286. package/dist/types/schema-core.d.ts +628 -0
  287. package/dist/types/schema-core.d.ts.map +1 -0
  288. package/dist/types/schema-core.js +2 -0
  289. package/dist/types/schema-core.js.map +1 -0
  290. package/dist/types/schema-inference.d.ts +73 -0
  291. package/dist/types/schema-inference.d.ts.map +1 -0
  292. package/dist/types/schema-inference.js +2 -0
  293. package/dist/types/schema-inference.js.map +1 -0
  294. package/dist/types/workflows.d.ts +121 -0
  295. package/dist/types/workflows.d.ts.map +1 -0
  296. package/dist/types/workflows.js +7 -0
  297. package/dist/types/workflows.js.map +1 -0
  298. package/dist/utils/access-control.d.ts +35 -0
  299. package/dist/utils/access-control.d.ts.map +1 -0
  300. package/dist/utils/access-control.js +161 -0
  301. package/dist/utils/access-control.js.map +1 -0
  302. package/dist/utils/admin-auth.d.ts +5 -0
  303. package/dist/utils/admin-auth.d.ts.map +1 -0
  304. package/dist/utils/admin-auth.js +39 -0
  305. package/dist/utils/admin-auth.js.map +1 -0
  306. package/dist/utils/block-references.d.ts +10 -0
  307. package/dist/utils/block-references.d.ts.map +1 -0
  308. package/dist/utils/block-references.js +100 -0
  309. package/dist/utils/block-references.js.map +1 -0
  310. package/dist/utils/collection-search.d.ts +11 -0
  311. package/dist/utils/collection-search.d.ts.map +1 -0
  312. package/dist/utils/collection-search.js +204 -0
  313. package/dist/utils/collection-search.js.map +1 -0
  314. package/dist/utils/config.d.ts +8 -0
  315. package/dist/utils/config.d.ts.map +1 -0
  316. package/dist/utils/config.js +336 -0
  317. package/dist/utils/config.js.map +1 -0
  318. package/dist/utils/hooks.d.ts +41 -0
  319. package/dist/utils/hooks.d.ts.map +1 -0
  320. package/dist/utils/hooks.js +177 -0
  321. package/dist/utils/hooks.js.map +1 -0
  322. package/dist/utils/openapi.d.ts +6 -0
  323. package/dist/utils/openapi.d.ts.map +1 -0
  324. package/dist/utils/openapi.js +981 -0
  325. package/dist/utils/openapi.js.map +1 -0
  326. package/dist/utils/parse-sort.d.ts +43 -0
  327. package/dist/utils/parse-sort.d.ts.map +1 -0
  328. package/dist/utils/parse-sort.js +70 -0
  329. package/dist/utils/parse-sort.js.map +1 -0
  330. package/dist/utils/parse-where.d.ts +69 -0
  331. package/dist/utils/parse-where.d.ts.map +1 -0
  332. package/dist/utils/parse-where.js +202 -0
  333. package/dist/utils/parse-where.js.map +1 -0
  334. package/dist/utils/readonly-db.d.ts +9 -0
  335. package/dist/utils/readonly-db.d.ts.map +1 -0
  336. package/dist/utils/readonly-db.js +21 -0
  337. package/dist/utils/readonly-db.js.map +1 -0
  338. package/dist/utils/swagger.d.ts +11 -0
  339. package/dist/utils/swagger.d.ts.map +1 -0
  340. package/dist/utils/swagger.js +62 -0
  341. package/dist/utils/swagger.js.map +1 -0
  342. package/dist/utils/upload-validation.d.ts +23 -0
  343. package/dist/utils/upload-validation.d.ts.map +1 -0
  344. package/dist/utils/upload-validation.js +46 -0
  345. package/dist/utils/upload-validation.js.map +1 -0
  346. package/dist/utils/where-sanitizer.d.ts +10 -0
  347. package/dist/utils/where-sanitizer.d.ts.map +1 -0
  348. package/dist/utils/where-sanitizer.js +67 -0
  349. package/dist/utils/where-sanitizer.js.map +1 -0
  350. package/dist/workflows.d.ts +86 -0
  351. package/dist/workflows.d.ts.map +1 -0
  352. package/dist/workflows.js +405 -0
  353. package/dist/workflows.js.map +1 -0
  354. package/package.json +1 -1
package/dist/index.cjs CHANGED
@@ -30,12 +30,24 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
30
30
  // src/index.ts
31
31
  var index_exports = {};
32
32
  __export(index_exports, {
33
+ ConfigValidationError: () => ConfigValidationError,
33
34
  LIFECYCLE_EVENTS_COLLECTION: () => LIFECYCLE_EVENTS_COLLECTION,
34
35
  LIFECYCLE_EVENT_NAMES: () => LIFECYCLE_EVENT_NAMES,
35
36
  WORKFLOW_HISTORY_COLLECTION: () => WORKFLOW_HISTORY_COLLECTION,
37
+ assertValidAdminConditionsInConfig: () => assertValidAdminConditionsInConfig,
38
+ assertValidDeclarativeAccessInConfig: () => assertValidDeclarativeAccessInConfig,
39
+ assertValidDeclarativeHookExpression: () => assertValidDeclarativeHookExpression,
40
+ assertValidDeclarativeHookResult: () => assertValidDeclarativeHookResult,
41
+ assertValidDeclarativeHooksInConfig: () => assertValidDeclarativeHooksInConfig,
42
+ assertValidPreviewUrlsInConfig: () => assertValidPreviewUrlsInConfig,
36
43
  availableWorkflowTransitions: () => availableWorkflowTransitions,
37
44
  buildSqlOrderBy: () => buildSqlOrderBy,
38
45
  canViewWorkflowDraft: () => canViewWorkflowDraft,
46
+ collectAdminConditionValidationIssues: () => collectAdminConditionValidationIssues,
47
+ collectConfigDiagnostics: () => collectConfigDiagnostics,
48
+ collectDeclarativeAccessValidationIssues: () => collectDeclarativeAccessValidationIssues,
49
+ collectDeclarativeHookValidationIssues: () => collectDeclarativeHookValidationIssues,
50
+ collectPreviewUrlValidationIssues: () => collectPreviewUrlValidationIssues,
39
51
  createLifecycleEvent: () => createLifecycleEvent,
40
52
  createWorkflowDocument: () => createWorkflowDocument,
41
53
  defineArrayField: () => defineArrayField,
@@ -71,10 +83,12 @@ __export(index_exports, {
71
83
  dispatchPendingLifecycleEvents: () => dispatchPendingLifecycleEvents,
72
84
  executeFieldAfterRead: () => executeFieldAfterRead,
73
85
  executeFieldBeforeChange: () => executeFieldBeforeChange,
86
+ formatConfigDiagnostics: () => formatConfigDiagnostics,
74
87
  generateOpenApi: () => generateOpenApi,
75
88
  getAdminAuthCollection: () => getAdminAuthCollection,
76
89
  getPublicAdminAuthConfig: () => getPublicAdminAuthConfig,
77
90
  initializeWorkflowDocument: () => initializeWorkflowDocument,
91
+ isConfigValidationError: () => isConfigValidationError,
78
92
  materializeWorkflowDocument: () => materializeWorkflowDocument,
79
93
  normalizeConfig: () => normalizeConfig,
80
94
  numericFieldNames: () => numericFieldNames,
@@ -88,6 +102,10 @@ __export(index_exports, {
88
102
  saveWorkflowDraft: () => saveWorkflowDraft,
89
103
  simplePublishingWorkflow: () => simplePublishingWorkflow,
90
104
  transitionWorkflow: () => transitionWorkflow,
105
+ validateAdminConditionExpression: () => validateAdminConditionExpression,
106
+ validateDeclarativeAccessExpression: () => validateDeclarativeAccessExpression,
107
+ validateDeclarativeHookExpression: () => validateDeclarativeHookExpression,
108
+ validatePreviewUrlExpression: () => validatePreviewUrlExpression,
91
109
  workflowCapabilities: () => workflowCapabilities
92
110
  });
93
111
  module.exports = __toCommonJS(index_exports);
@@ -592,6 +610,594 @@ function normalizeSchemaFragment(fragment) {
592
610
  };
593
611
  }
594
612
 
613
+ // src/utils/declarative-hooks.ts
614
+ var import_jexl = __toESM(require("jexl"), 1);
615
+ var SURFACE_ROOTS = {
616
+ "collection.beforeRead": ["req", "user", "query"],
617
+ "collection.afterRead": ["req", "user", "doc"],
618
+ "collection.beforeChange": ["req", "user", "data", "doc", "operation"],
619
+ "global.beforeRead": ["req", "user", "query"],
620
+ "global.afterRead": ["req", "user", "doc"],
621
+ "global.beforeChange": ["req", "user", "data", "doc", "operation"],
622
+ "field.beforeChange": ["value", "data", "originalDoc", "user"],
623
+ "field.admin.onChange": ["value", "siblingData", "data"]
624
+ };
625
+ var ACCESS_ROOTS = ["user", "req", "doc", "data", "id", "config"];
626
+ var ADMIN_CONDITION_RESERVED_ROOTS = ["data", "siblingData", "user", "id"];
627
+ var PREVIEW_URL_RESERVED_ROOTS = ["siteUrl", "id"];
628
+ var COMPILE_CACHE = /* @__PURE__ */ new Map();
629
+ function compileExpression(expression) {
630
+ const cached = COMPILE_CACHE.get(expression);
631
+ if (cached) return cached;
632
+ const compiled = import_jexl.default.compile(expression);
633
+ const next = { ast: compiled._ast };
634
+ COMPILE_CACHE.set(expression, next);
635
+ return next;
636
+ }
637
+ function isPlainObject(value) {
638
+ return !!value && typeof value === "object" && !Array.isArray(value);
639
+ }
640
+ function quoteSegment(value) {
641
+ return `["${value.replace(/"/g, '\\"')}"]`;
642
+ }
643
+ function fieldSegment(field, index) {
644
+ return typeof field.name === "string" && field.name.length > 0 ? `fields${quoteSegment(field.name)}` : `fields[${index}]`;
645
+ }
646
+ function blockSegment(block, index) {
647
+ return typeof block.slug === "string" && block.slug.length > 0 ? `blocks${quoteSegment(block.slug)}` : `blocks[${index}]`;
648
+ }
649
+ function collectionSegment(collection, index) {
650
+ return typeof collection.slug === "string" && collection.slug.length > 0 ? `collections${quoteSegment(collection.slug)}` : `collections[${index}]`;
651
+ }
652
+ function globalSegment(global, index) {
653
+ return typeof global.slug === "string" && global.slug.length > 0 ? `globals${quoteSegment(global.slug)}` : `globals[${index}]`;
654
+ }
655
+ function colorize(value, code, enabled) {
656
+ return enabled ? `\x1B[${code}m${value}\x1B[0m` : value;
657
+ }
658
+ function collectRootIdentifiers(node, roots, seen) {
659
+ if (!node || typeof node !== "object" || seen.has(node)) return;
660
+ seen.add(node);
661
+ const candidate = node;
662
+ if (candidate.type === "Identifier") {
663
+ if (candidate.from) {
664
+ collectRootIdentifiers(candidate.from, roots, seen);
665
+ return;
666
+ }
667
+ if (typeof candidate.value === "string" && candidate.value !== "null") {
668
+ roots.add(candidate.value);
669
+ }
670
+ return;
671
+ }
672
+ if (Array.isArray(node)) {
673
+ for (const entry of node) collectRootIdentifiers(entry, roots, seen);
674
+ return;
675
+ }
676
+ for (const value of Object.values(node)) {
677
+ if (Array.isArray(value)) {
678
+ for (const entry of value) collectRootIdentifiers(entry, roots, seen);
679
+ continue;
680
+ }
681
+ if (value && typeof value === "object") {
682
+ collectRootIdentifiers(value, roots, seen);
683
+ }
684
+ }
685
+ }
686
+ function getInvalidRoots(expression, allowedRoots) {
687
+ const { ast } = compileExpression(expression);
688
+ const roots = /* @__PURE__ */ new Set();
689
+ collectRootIdentifiers(ast, roots, /* @__PURE__ */ new Set());
690
+ const allowed = new Set(allowedRoots);
691
+ return [...roots].filter((root) => !allowed.has(root));
692
+ }
693
+ function validateDeclarativeHookExpression(expression, surface, path) {
694
+ try {
695
+ const invalidRoots = getInvalidRoots(expression, SURFACE_ROOTS[surface]);
696
+ if (invalidRoots.length === 0) return [];
697
+ return [
698
+ {
699
+ path,
700
+ surface,
701
+ expression,
702
+ message: `uses unsupported context ${invalidRoots.map((root) => `"${root}"`).join(", ")}. Allowed context: ${SURFACE_ROOTS[surface].map((root) => `"${root}"`).join(", ")}`
703
+ }
704
+ ];
705
+ } catch (error) {
706
+ return [
707
+ {
708
+ path,
709
+ surface,
710
+ expression,
711
+ message: `has invalid syntax: ${error.message}`
712
+ }
713
+ ];
714
+ }
715
+ }
716
+ function validateDeclarativeAccessExpression(expression, surface, path) {
717
+ try {
718
+ const invalidRoots = getInvalidRoots(expression, ACCESS_ROOTS);
719
+ if (invalidRoots.length === 0) return [];
720
+ return [
721
+ {
722
+ path,
723
+ surface,
724
+ expression,
725
+ message: `uses unsupported context ${invalidRoots.map((root) => `"${root}"`).join(", ")}. Allowed context: ${ACCESS_ROOTS.map((root) => `"${root}"`).join(", ")}`
726
+ }
727
+ ];
728
+ } catch (error) {
729
+ return [
730
+ {
731
+ path,
732
+ surface,
733
+ expression,
734
+ message: `has invalid syntax: ${error.message}`
735
+ }
736
+ ];
737
+ }
738
+ }
739
+ function validateAdminConditionExpression(expression, path, allowedRoots) {
740
+ try {
741
+ const invalidRoots = getInvalidRoots(expression, allowedRoots);
742
+ if (invalidRoots.length === 0) return [];
743
+ return [
744
+ {
745
+ path,
746
+ surface: "field.admin.condition",
747
+ expression,
748
+ message: `uses unsupported context ${invalidRoots.map((root) => `"${root}"`).join(", ")}. Allowed context: ${allowedRoots.map((root) => `"${root}"`).join(", ")}`
749
+ }
750
+ ];
751
+ } catch (error) {
752
+ return [
753
+ {
754
+ path,
755
+ surface: "field.admin.condition",
756
+ expression,
757
+ message: `has invalid syntax: ${error.message}`
758
+ }
759
+ ];
760
+ }
761
+ }
762
+ function validatePreviewUrlExpression(expression, path, allowedRoots) {
763
+ try {
764
+ const invalidRoots = getInvalidRoots(expression, allowedRoots);
765
+ if (invalidRoots.length === 0) return [];
766
+ return [
767
+ {
768
+ path,
769
+ surface: "collection.admin.previewUrl",
770
+ expression,
771
+ message: `uses unsupported context ${invalidRoots.map((root) => `"${root}"`).join(", ")}. Allowed context: ${allowedRoots.map((root) => `"${root}"`).join(", ")}`
772
+ }
773
+ ];
774
+ } catch (error) {
775
+ return [
776
+ {
777
+ path,
778
+ surface: "collection.admin.previewUrl",
779
+ expression,
780
+ message: `has invalid syntax: ${error.message}`
781
+ }
782
+ ];
783
+ }
784
+ }
785
+ function assertValidDeclarativeHookExpression(expression, surface, path) {
786
+ const issues = validateDeclarativeHookExpression(expression, surface, path);
787
+ if (issues.length === 0) return;
788
+ throw new Error(`Invalid declarative hook at ${path}: ${issues[0].message}`);
789
+ }
790
+ function assertValidDeclarativeHookResult(result, surface, path) {
791
+ if (isPlainObject(result)) return;
792
+ throw new Error(`Invalid declarative hook result at ${path}: ${surface} expressions must return an object`);
793
+ }
794
+ function collectFieldIssues(fields, path, issues) {
795
+ fields.forEach((field, index) => {
796
+ const fieldPath = `${path}.${fieldSegment(field, index)}`;
797
+ field.hooks?.beforeChange?.forEach((hook, hookIndex) => {
798
+ if (typeof hook !== "string") return;
799
+ issues.push(
800
+ ...validateDeclarativeHookExpression(
801
+ hook,
802
+ "field.beforeChange",
803
+ `${fieldPath}.hooks.beforeChange[${hookIndex}]`
804
+ )
805
+ );
806
+ });
807
+ field.hooks?.afterRead?.forEach((hook, hookIndex) => {
808
+ if (typeof hook !== "string") return;
809
+ issues.push({
810
+ path: `${fieldPath}.hooks.afterRead[${hookIndex}]`,
811
+ surface: "unsupported",
812
+ expression: hook,
813
+ message: "declarative strings are not supported on field hooks.afterRead"
814
+ });
815
+ });
816
+ if (typeof field.admin?.hooks?.onChange === "string") {
817
+ issues.push(
818
+ ...validateDeclarativeHookExpression(
819
+ field.admin.hooks.onChange,
820
+ "field.admin.onChange",
821
+ `${fieldPath}.admin.hooks.onChange`
822
+ )
823
+ );
824
+ }
825
+ if (typeof field.admin?.hooks?.options === "string") {
826
+ issues.push({
827
+ path: `${fieldPath}.admin.hooks.options`,
828
+ surface: "unsupported",
829
+ expression: field.admin.hooks.options,
830
+ message: "declarative strings are not supported on field admin.hooks.options"
831
+ });
832
+ }
833
+ if (Array.isArray(field.fields)) {
834
+ collectFieldIssues(field.fields, fieldPath, issues);
835
+ }
836
+ if (Array.isArray(field.blocks)) {
837
+ field.blocks.forEach((block, blockIndex) => {
838
+ if (!Array.isArray(block.fields)) return;
839
+ collectFieldIssues(block.fields, `${fieldPath}.${blockSegment(block, blockIndex)}`, issues);
840
+ });
841
+ }
842
+ });
843
+ }
844
+ function collectFieldNames(fields) {
845
+ return fields.flatMap(
846
+ (field) => typeof field.name === "string" && field.name.length > 0 ? [field.name] : []
847
+ );
848
+ }
849
+ function collectAdminConditionIssues(fields, path, rootFieldNames, issues) {
850
+ const scopeFieldNames = collectFieldNames(fields);
851
+ const allowedRoots = [.../* @__PURE__ */ new Set([...ADMIN_CONDITION_RESERVED_ROOTS, ...rootFieldNames, ...scopeFieldNames])];
852
+ fields.forEach((field, index) => {
853
+ const fieldPath = `${path}.${fieldSegment(field, index)}`;
854
+ if (typeof field.admin?.condition === "string") {
855
+ issues.push(
856
+ ...validateAdminConditionExpression(
857
+ field.admin.condition,
858
+ `${fieldPath}.admin.condition`,
859
+ allowedRoots
860
+ )
861
+ );
862
+ }
863
+ if (Array.isArray(field.fields)) {
864
+ collectAdminConditionIssues(field.fields, fieldPath, rootFieldNames, issues);
865
+ }
866
+ if (Array.isArray(field.blocks)) {
867
+ field.blocks.forEach((block, blockIndex) => {
868
+ if (!Array.isArray(block.fields)) return;
869
+ collectAdminConditionIssues(
870
+ block.fields,
871
+ `${fieldPath}.${blockSegment(block, blockIndex)}`,
872
+ rootFieldNames,
873
+ issues
874
+ );
875
+ });
876
+ }
877
+ });
878
+ }
879
+ function collectFieldAccessIssues(fields, path, issues) {
880
+ fields.forEach((field, index) => {
881
+ const fieldPath = `${path}.${fieldSegment(field, index)}`;
882
+ if (typeof field.access?.read === "string") {
883
+ issues.push(...validateDeclarativeAccessExpression(field.access.read, "field.access", `${fieldPath}.access.read`));
884
+ }
885
+ if (typeof field.access?.create === "string") {
886
+ issues.push(
887
+ ...validateDeclarativeAccessExpression(field.access.create, "field.access", `${fieldPath}.access.create`)
888
+ );
889
+ }
890
+ if (typeof field.access?.update === "string") {
891
+ issues.push(
892
+ ...validateDeclarativeAccessExpression(field.access.update, "field.access", `${fieldPath}.access.update`)
893
+ );
894
+ }
895
+ if (Array.isArray(field.fields)) {
896
+ collectFieldAccessIssues(field.fields, fieldPath, issues);
897
+ }
898
+ if (Array.isArray(field.blocks)) {
899
+ field.blocks.forEach((block, blockIndex) => {
900
+ if (!Array.isArray(block.fields)) return;
901
+ collectFieldAccessIssues(
902
+ block.fields,
903
+ `${fieldPath}.${blockSegment(block, blockIndex)}`,
904
+ issues
905
+ );
906
+ });
907
+ }
908
+ });
909
+ }
910
+ function collectHookIssues(hooks, scope, path, issues) {
911
+ if (!hooks) return;
912
+ const supported = {
913
+ beforeRead: `${scope}.beforeRead`,
914
+ afterRead: `${scope}.afterRead`,
915
+ beforeChange: `${scope}.beforeChange`
916
+ };
917
+ for (const [key, value] of Object.entries(hooks)) {
918
+ if (!Array.isArray(value)) continue;
919
+ value.forEach((hook, index) => {
920
+ if (typeof hook !== "string") return;
921
+ const surface = supported[key];
922
+ if (!surface) {
923
+ issues.push({
924
+ path: `${path}.${key}[${index}]`,
925
+ surface: "unsupported",
926
+ expression: hook,
927
+ message: `declarative strings are not supported on ${scope} hooks.${key}`
928
+ });
929
+ return;
930
+ }
931
+ issues.push(...validateDeclarativeHookExpression(hook, surface, `${path}.${key}[${index}]`));
932
+ });
933
+ }
934
+ }
935
+ function collectDeclarativeHookValidationIssues(config) {
936
+ const issues = [];
937
+ config.blocks?.forEach((block, blockIndex) => {
938
+ if (!Array.isArray(block.fields)) return;
939
+ collectFieldIssues(
940
+ block.fields,
941
+ blockSegment(block, blockIndex),
942
+ issues
943
+ );
944
+ });
945
+ config.collections.forEach((collection, collectionIndex) => {
946
+ const collectionPath = collectionSegment(collection, collectionIndex);
947
+ collectHookIssues(
948
+ collection.hooks,
949
+ "collection",
950
+ `${collectionPath}.hooks`,
951
+ issues
952
+ );
953
+ collectFieldIssues(collection.fields, collectionPath, issues);
954
+ });
955
+ config.globals?.forEach((global, globalIndex) => {
956
+ const globalPath = globalSegment(global, globalIndex);
957
+ collectHookIssues(
958
+ global.hooks,
959
+ "global",
960
+ `${globalPath}.hooks`,
961
+ issues
962
+ );
963
+ collectFieldIssues(global.fields, globalPath, issues);
964
+ });
965
+ return issues;
966
+ }
967
+ function collectDeclarativeAccessValidationIssues(config) {
968
+ const issues = [];
969
+ Object.entries(config.accessPolicies ?? {}).forEach(([name, value]) => {
970
+ if (typeof value !== "string") return;
971
+ issues.push(
972
+ ...validateDeclarativeAccessExpression(value, "config.accessPolicy", `accessPolicies.${name}`)
973
+ );
974
+ });
975
+ config.blocks?.forEach((block, blockIndex) => {
976
+ if (!Array.isArray(block.fields)) return;
977
+ collectFieldAccessIssues(
978
+ block.fields,
979
+ blockSegment(block, blockIndex),
980
+ issues
981
+ );
982
+ });
983
+ config.collections.forEach((collection, collectionIndex) => {
984
+ const collectionPath = collectionSegment(collection, collectionIndex);
985
+ if (typeof collection.access?.read === "string") {
986
+ issues.push(
987
+ ...validateDeclarativeAccessExpression(
988
+ collection.access.read,
989
+ "collection.access",
990
+ `${collectionPath}.access.read`
991
+ )
992
+ );
993
+ }
994
+ if (typeof collection.access?.create === "string") {
995
+ issues.push(
996
+ ...validateDeclarativeAccessExpression(
997
+ collection.access.create,
998
+ "collection.access",
999
+ `${collectionPath}.access.create`
1000
+ )
1001
+ );
1002
+ }
1003
+ if (typeof collection.access?.update === "string") {
1004
+ issues.push(
1005
+ ...validateDeclarativeAccessExpression(
1006
+ collection.access.update,
1007
+ "collection.access",
1008
+ `${collectionPath}.access.update`
1009
+ )
1010
+ );
1011
+ }
1012
+ if (typeof collection.access?.delete === "string") {
1013
+ issues.push(
1014
+ ...validateDeclarativeAccessExpression(
1015
+ collection.access.delete,
1016
+ "collection.access",
1017
+ `${collectionPath}.access.delete`
1018
+ )
1019
+ );
1020
+ }
1021
+ if (typeof collection.access?.readAudit === "string") {
1022
+ issues.push(
1023
+ ...validateDeclarativeAccessExpression(
1024
+ collection.access.readAudit,
1025
+ "collection.access",
1026
+ `${collectionPath}.access.readAudit`
1027
+ )
1028
+ );
1029
+ }
1030
+ collectFieldAccessIssues(collection.fields, collectionPath, issues);
1031
+ });
1032
+ config.globals?.forEach((global, globalIndex) => {
1033
+ const globalPath = globalSegment(global, globalIndex);
1034
+ if (typeof global.access?.read === "string") {
1035
+ issues.push(
1036
+ ...validateDeclarativeAccessExpression(global.access.read, "global.access", `${globalPath}.access.read`)
1037
+ );
1038
+ }
1039
+ if (typeof global.access?.update === "string") {
1040
+ issues.push(
1041
+ ...validateDeclarativeAccessExpression(
1042
+ global.access.update,
1043
+ "global.access",
1044
+ `${globalPath}.access.update`
1045
+ )
1046
+ );
1047
+ }
1048
+ collectFieldAccessIssues(global.fields, globalPath, issues);
1049
+ });
1050
+ return issues;
1051
+ }
1052
+ function collectAdminConditionValidationIssues(config) {
1053
+ const issues = [];
1054
+ config.blocks?.forEach((block, blockIndex) => {
1055
+ if (!Array.isArray(block.fields)) return;
1056
+ collectAdminConditionIssues(
1057
+ block.fields,
1058
+ blockSegment(block, blockIndex),
1059
+ collectFieldNames(block.fields),
1060
+ issues
1061
+ );
1062
+ });
1063
+ config.collections.forEach((collection, collectionIndex) => {
1064
+ const collectionPath = collectionSegment(collection, collectionIndex);
1065
+ const rootFieldNames = collectFieldNames(collection.fields);
1066
+ collectAdminConditionIssues(collection.fields, collectionPath, rootFieldNames, issues);
1067
+ });
1068
+ config.globals?.forEach((global, globalIndex) => {
1069
+ const globalPath = globalSegment(global, globalIndex);
1070
+ const rootFieldNames = collectFieldNames(global.fields);
1071
+ collectAdminConditionIssues(global.fields, globalPath, rootFieldNames, issues);
1072
+ });
1073
+ return issues;
1074
+ }
1075
+ function collectPreviewUrlValidationIssues(config) {
1076
+ const issues = [];
1077
+ config.collections.forEach((collection, collectionIndex) => {
1078
+ if (typeof collection.admin?.previewUrl !== "string") return;
1079
+ const collectionPath = collectionSegment(collection, collectionIndex);
1080
+ const allowedRoots = [
1081
+ .../* @__PURE__ */ new Set([...PREVIEW_URL_RESERVED_ROOTS, ...collectFieldNames(collection.fields)])
1082
+ ];
1083
+ issues.push(
1084
+ ...validatePreviewUrlExpression(
1085
+ collection.admin.previewUrl,
1086
+ `${collectionPath}.admin.previewUrl`,
1087
+ allowedRoots
1088
+ )
1089
+ );
1090
+ });
1091
+ return issues;
1092
+ }
1093
+ function assertValidAdminConditionsInConfig(config, source = "config") {
1094
+ const diagnostics = collectAdminConditionValidationIssues(config).map((issue) => ({
1095
+ severity: "error",
1096
+ source: "adminCondition",
1097
+ path: issue.path,
1098
+ surface: issue.surface,
1099
+ message: issue.message,
1100
+ expression: issue.expression
1101
+ }));
1102
+ if (diagnostics.length === 0) return;
1103
+ throw new ConfigValidationError(source, diagnostics);
1104
+ }
1105
+ function assertValidPreviewUrlsInConfig(config, source = "config") {
1106
+ const diagnostics = collectPreviewUrlValidationIssues(config).map((issue) => ({
1107
+ severity: "error",
1108
+ source: "previewUrl",
1109
+ path: issue.path,
1110
+ surface: issue.surface,
1111
+ message: issue.message,
1112
+ expression: issue.expression
1113
+ }));
1114
+ if (diagnostics.length === 0) return;
1115
+ throw new ConfigValidationError(source, diagnostics);
1116
+ }
1117
+ function collectConfigDiagnostics(config) {
1118
+ const hookIssues = collectDeclarativeHookValidationIssues(config).map((issue) => ({
1119
+ severity: "error",
1120
+ source: "declarativeHook",
1121
+ path: issue.path,
1122
+ surface: issue.surface,
1123
+ message: issue.message,
1124
+ expression: issue.expression
1125
+ }));
1126
+ const accessIssues = collectDeclarativeAccessValidationIssues(config).map((issue) => ({
1127
+ severity: "error",
1128
+ source: "declarativeAccess",
1129
+ path: issue.path,
1130
+ surface: issue.surface,
1131
+ message: issue.message,
1132
+ expression: issue.expression
1133
+ }));
1134
+ const adminConditionIssues = collectAdminConditionValidationIssues(config).map((issue) => ({
1135
+ severity: "error",
1136
+ source: "adminCondition",
1137
+ path: issue.path,
1138
+ surface: issue.surface,
1139
+ message: issue.message,
1140
+ expression: issue.expression
1141
+ }));
1142
+ const previewUrlIssues = collectPreviewUrlValidationIssues(config).map((issue) => ({
1143
+ severity: "error",
1144
+ source: "previewUrl",
1145
+ path: issue.path,
1146
+ surface: issue.surface,
1147
+ message: issue.message,
1148
+ expression: issue.expression
1149
+ }));
1150
+ return [...hookIssues, ...accessIssues, ...adminConditionIssues, ...previewUrlIssues];
1151
+ }
1152
+ function formatConfigDiagnostics(source, diagnostics, options = {}) {
1153
+ const color = options.color ?? false;
1154
+ const header = `${colorize("Config validation failed", 31, color)} in ${colorize(source, 36, color)}`;
1155
+ const lines = diagnostics.flatMap((issue, index) => [
1156
+ `${colorize(`${index + 1}.`, 31, color)} ${colorize(issue.path, 1, color)}`,
1157
+ ` ${issue.message}`,
1158
+ ` ${colorize("surface:", 90, color)} ${issue.surface}`
1159
+ ]);
1160
+ return `${header}
1161
+ ${lines.join("\n")}`;
1162
+ }
1163
+ var ConfigValidationError = class extends Error {
1164
+ diagnostics;
1165
+ source;
1166
+ constructor(source, diagnostics) {
1167
+ super(formatConfigDiagnostics(source, diagnostics));
1168
+ this.name = "ConfigValidationError";
1169
+ this.source = source;
1170
+ this.diagnostics = diagnostics;
1171
+ }
1172
+ };
1173
+ function isConfigValidationError(error) {
1174
+ return error instanceof ConfigValidationError;
1175
+ }
1176
+ function assertValidDeclarativeHooksInConfig(config, source = "config") {
1177
+ const diagnostics = collectDeclarativeHookValidationIssues(config).map((issue) => ({
1178
+ severity: "error",
1179
+ source: "declarativeHook",
1180
+ path: issue.path,
1181
+ surface: issue.surface,
1182
+ message: issue.message,
1183
+ expression: issue.expression
1184
+ }));
1185
+ if (diagnostics.length === 0) return;
1186
+ throw new ConfigValidationError(source, diagnostics);
1187
+ }
1188
+ function assertValidDeclarativeAccessInConfig(config, source = "config") {
1189
+ const diagnostics = collectDeclarativeAccessValidationIssues(config).map((issue) => ({
1190
+ severity: "error",
1191
+ source: "declarativeAccess",
1192
+ path: issue.path,
1193
+ surface: issue.surface,
1194
+ message: issue.message,
1195
+ expression: issue.expression
1196
+ }));
1197
+ if (diagnostics.length === 0) return;
1198
+ throw new ConfigValidationError(source, diagnostics);
1199
+ }
1200
+
595
1201
  // src/utils/config.ts
596
1202
  var AUDIT_COLLECTION_SLUG = "__audit";
597
1203
  var SYSTEM_FIELDS = [
@@ -720,6 +1326,10 @@ var AUTH_SESSIONS_COLLECTION_CONFIG = {
720
1326
  };
721
1327
  function normalizeConfig(config) {
722
1328
  const schemaAwareConfig = normalizeSchemaFragment(config);
1329
+ assertValidDeclarativeHooksInConfig(schemaAwareConfig, "config");
1330
+ assertValidDeclarativeAccessInConfig(schemaAwareConfig, "config");
1331
+ assertValidAdminConditionsInConfig(schemaAwareConfig, "config");
1332
+ assertValidPreviewUrlsInConfig(schemaAwareConfig, "config");
723
1333
  const collections = schemaAwareConfig?.collections || [];
724
1334
  const globals = schemaAwareConfig?.globals || [];
725
1335
  const needsAudit = collections.some((col) => col.audit);
@@ -782,6 +1392,27 @@ function normalizeConfig(config) {
782
1392
  }
783
1393
  ];
784
1394
  }
1395
+ if (!existingFieldNames.has("status")) {
1396
+ fields = [
1397
+ ...fields,
1398
+ {
1399
+ name: "status",
1400
+ type: "select",
1401
+ label: "Status",
1402
+ defaultValue: "active",
1403
+ options: [
1404
+ { value: "active", label: "Active" },
1405
+ { value: "pending", label: "Pending" }
1406
+ ],
1407
+ access: {
1408
+ update: "user.roles && 'admin' in user.roles && user.id != id"
1409
+ },
1410
+ admin: {
1411
+ condition: `!(data.roles && "admin" in data.roles)`
1412
+ }
1413
+ }
1414
+ ];
1415
+ }
785
1416
  fields = fields.map((field) => {
786
1417
  if (field.name === "email") {
787
1418
  return {
@@ -821,6 +1452,15 @@ function normalizeConfig(config) {
821
1452
  }
822
1453
  };
823
1454
  }
1455
+ if (field.name === "status") {
1456
+ return {
1457
+ ...field,
1458
+ access: {
1459
+ ...field.access || {},
1460
+ update: "user.roles && 'admin' in user.roles && user.id != id"
1461
+ }
1462
+ };
1463
+ }
824
1464
  return field;
825
1465
  });
826
1466
  }
@@ -858,9 +1498,7 @@ function normalizeConfig(config) {
858
1498
  }
859
1499
  }
860
1500
  const updatedFieldNames = new Set(fields.map((f) => f.name));
861
- const fieldsToInject = SYSTEM_FIELDS.filter(
862
- (f) => !updatedFieldNames.has(f.name)
863
- );
1501
+ const fieldsToInject = SYSTEM_FIELDS.filter((f) => !updatedFieldNames.has(f.name));
864
1502
  const workflow = col.workflow || (col.drafts ? simplePublishingWorkflow() : void 0);
865
1503
  return {
866
1504
  ...col,
@@ -868,20 +1506,13 @@ function normalizeConfig(config) {
868
1506
  fields: [...fields, ...fieldsToInject]
869
1507
  };
870
1508
  });
871
- const hasAuditCollection = normalizedCollections.some(
872
- (col) => col.slug === AUDIT_COLLECTION_SLUG
873
- );
1509
+ const hasAuditCollection = normalizedCollections.some((col) => col.slug === AUDIT_COLLECTION_SLUG);
874
1510
  const systemCollections = [];
875
- if (needsAudit && !hasAuditCollection)
876
- systemCollections.push(AUDIT_COLLECTION);
877
- if (needsWorkflow && !normalizedCollections.some(
878
- (col) => col.slug === WORKFLOW_HISTORY_COLLECTION
879
- )) {
1511
+ if (needsAudit && !hasAuditCollection) systemCollections.push(AUDIT_COLLECTION);
1512
+ if (needsWorkflow && !normalizedCollections.some((col) => col.slug === WORKFLOW_HISTORY_COLLECTION)) {
880
1513
  systemCollections.push(WORKFLOW_HISTORY_COLLECTION_CONFIG);
881
1514
  }
882
- if (needsWorkflow && !normalizedCollections.some(
883
- (col) => col.slug === LIFECYCLE_EVENTS_COLLECTION
884
- )) {
1515
+ if (needsWorkflow && !normalizedCollections.some((col) => col.slug === LIFECYCLE_EVENTS_COLLECTION)) {
885
1516
  systemCollections.push(LIFECYCLE_EVENTS_COLLECTION_CONFIG);
886
1517
  }
887
1518
  if (needsAuthSessions && !normalizedCollections.some((col) => col.slug === AUTH_SESSIONS_COLLECTION)) {
@@ -1097,20 +1728,41 @@ function buildSqlOrderBy(sort, existingColumns, numericFields, dialect) {
1097
1728
  }
1098
1729
 
1099
1730
  // src/utils/hooks.ts
1731
+ var import_jexl2 = __toESM(require("jexl"), 1);
1100
1732
  async function runCollectionHooks(hooks, args, options = {}) {
1101
1733
  if (!hooks || hooks.length === 0) {
1102
- return args.data ?? args.doc ?? void 0;
1734
+ return args.data ?? args.doc ?? args.query ?? void 0;
1103
1735
  }
1104
- let currentPayload = args.data ?? args.doc ?? void 0;
1736
+ const payloadKey = args.data !== void 0 ? "data" : args.doc !== void 0 ? "doc" : "query" in args ? "query" : void 0;
1737
+ let currentPayload = payloadKey === void 0 ? void 0 : args[payloadKey];
1105
1738
  for (const hook of hooks) {
1106
1739
  try {
1107
- const result = await hook({
1740
+ const hookArgs = {
1108
1741
  ...args,
1109
- data: args.data !== void 0 ? currentPayload : void 0,
1110
- doc: args.doc !== void 0 ? currentPayload : void 0
1111
- });
1742
+ ...payloadKey !== void 0 ? { [payloadKey]: currentPayload } : {}
1743
+ };
1744
+ const result = typeof hook === "string" ? await (() => {
1745
+ if (options.surface) {
1746
+ assertValidDeclarativeHookExpression(
1747
+ hook,
1748
+ options.surface,
1749
+ options.path ?? options.surface
1750
+ );
1751
+ }
1752
+ return import_jexl2.default.eval(hook, hookArgs);
1753
+ })() : await hook(hookArgs);
1112
1754
  if (result !== void 0) {
1113
- currentPayload = result;
1755
+ if (typeof hook === "string" && options.surface) {
1756
+ assertValidDeclarativeHookResult(
1757
+ result,
1758
+ options.surface,
1759
+ options.path ?? options.surface
1760
+ );
1761
+ }
1762
+ currentPayload = typeof hook === "string" && currentPayload && typeof currentPayload === "object" && !Array.isArray(currentPayload) && result && typeof result === "object" && !Array.isArray(result) ? {
1763
+ ...currentPayload,
1764
+ ...result
1765
+ } : result;
1114
1766
  }
1115
1767
  } catch (err) {
1116
1768
  if (options.isolated) {
@@ -1125,17 +1777,17 @@ async function runCollectionHooks(hooks, args, options = {}) {
1125
1777
  }
1126
1778
  return currentPayload;
1127
1779
  }
1128
- async function executeFieldBeforeChange(fields, data, originalDoc, user, db) {
1780
+ async function executeFieldBeforeChange(fields, data, originalDoc, user, db, pathPrefix = "") {
1129
1781
  if (!data || typeof data !== "object") return data;
1130
1782
  const result = { ...data };
1131
1783
  for (const field of fields) {
1132
1784
  if (!field.name) continue;
1785
+ const fieldPath = pathPrefix ? `${pathPrefix}.${field.name}` : field.name;
1133
1786
  const value = result[field.name];
1134
1787
  const origValue = originalDoc?.[field.name];
1135
1788
  let updatedValue = value;
1136
1789
  if (field.hooks?.beforeChange) {
1137
1790
  for (const hook of field.hooks.beforeChange) {
1138
- const typedHook = hook;
1139
1791
  const hookArgs = {
1140
1792
  value: updatedValue,
1141
1793
  originalDoc: originalDoc ?? void 0,
@@ -1143,7 +1795,14 @@ async function executeFieldBeforeChange(fields, data, originalDoc, user, db) {
1143
1795
  user,
1144
1796
  db
1145
1797
  };
1146
- updatedValue = await typedHook(hookArgs);
1798
+ updatedValue = typeof hook === "string" ? await (() => {
1799
+ assertValidDeclarativeHookExpression(
1800
+ hook,
1801
+ "field.beforeChange",
1802
+ fieldPath
1803
+ );
1804
+ return import_jexl2.default.eval(hook, hookArgs);
1805
+ })() : await hook(hookArgs);
1147
1806
  }
1148
1807
  result[field.name] = updatedValue;
1149
1808
  }
@@ -1154,7 +1813,8 @@ async function executeFieldBeforeChange(fields, data, originalDoc, user, db) {
1154
1813
  updatedValue,
1155
1814
  origValue,
1156
1815
  user,
1157
- db
1816
+ db,
1817
+ fieldPath
1158
1818
  );
1159
1819
  } else if (field.type === "array" && field.fields && Array.isArray(updatedValue)) {
1160
1820
  const arrayResult = [];
@@ -1167,7 +1827,8 @@ async function executeFieldBeforeChange(fields, data, originalDoc, user, db) {
1167
1827
  item,
1168
1828
  origItem,
1169
1829
  user,
1170
- db
1830
+ db,
1831
+ fieldPath
1171
1832
  )
1172
1833
  );
1173
1834
  }
@@ -1187,7 +1848,8 @@ async function executeFieldBeforeChange(fields, data, originalDoc, user, db) {
1187
1848
  blockData,
1188
1849
  origBlock,
1189
1850
  user,
1190
- db
1851
+ db,
1852
+ fieldPath
1191
1853
  )
1192
1854
  );
1193
1855
  } else {
@@ -2281,12 +2943,24 @@ function defineTab(args) {
2281
2943
  }
2282
2944
  // Annotate the CommonJS export names for ESM import in node:
2283
2945
  0 && (module.exports = {
2946
+ ConfigValidationError,
2284
2947
  LIFECYCLE_EVENTS_COLLECTION,
2285
2948
  LIFECYCLE_EVENT_NAMES,
2286
2949
  WORKFLOW_HISTORY_COLLECTION,
2950
+ assertValidAdminConditionsInConfig,
2951
+ assertValidDeclarativeAccessInConfig,
2952
+ assertValidDeclarativeHookExpression,
2953
+ assertValidDeclarativeHookResult,
2954
+ assertValidDeclarativeHooksInConfig,
2955
+ assertValidPreviewUrlsInConfig,
2287
2956
  availableWorkflowTransitions,
2288
2957
  buildSqlOrderBy,
2289
2958
  canViewWorkflowDraft,
2959
+ collectAdminConditionValidationIssues,
2960
+ collectConfigDiagnostics,
2961
+ collectDeclarativeAccessValidationIssues,
2962
+ collectDeclarativeHookValidationIssues,
2963
+ collectPreviewUrlValidationIssues,
2290
2964
  createLifecycleEvent,
2291
2965
  createWorkflowDocument,
2292
2966
  defineArrayField,
@@ -2322,10 +2996,12 @@ function defineTab(args) {
2322
2996
  dispatchPendingLifecycleEvents,
2323
2997
  executeFieldAfterRead,
2324
2998
  executeFieldBeforeChange,
2999
+ formatConfigDiagnostics,
2325
3000
  generateOpenApi,
2326
3001
  getAdminAuthCollection,
2327
3002
  getPublicAdminAuthConfig,
2328
3003
  initializeWorkflowDocument,
3004
+ isConfigValidationError,
2329
3005
  materializeWorkflowDocument,
2330
3006
  normalizeConfig,
2331
3007
  numericFieldNames,
@@ -2339,5 +3015,9 @@ function defineTab(args) {
2339
3015
  saveWorkflowDraft,
2340
3016
  simplePublishingWorkflow,
2341
3017
  transitionWorkflow,
3018
+ validateAdminConditionExpression,
3019
+ validateDeclarativeAccessExpression,
3020
+ validateDeclarativeHookExpression,
3021
+ validatePreviewUrlExpression,
2342
3022
  workflowCapabilities
2343
3023
  });