emdash 0.32.0 → 0.34.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 (946) hide show
  1. package/dist/{adapters-C0ONzkUP.d.mts → adapters-34EN2eXO.d.mts} +34 -2
  2. package/dist/adapters-34EN2eXO.d.mts.map +1 -0
  3. package/dist/after-CBU2vkoO.mjs +96 -0
  4. package/dist/after-CBU2vkoO.mjs.map +1 -0
  5. package/dist/{allowed-origins-CCEi9bPI.mjs → allowed-origins-DW7sYyqg.mjs} +2 -2
  6. package/dist/{allowed-origins-CCEi9bPI.mjs.map → allowed-origins-DW7sYyqg.mjs.map} +1 -1
  7. package/dist/api/route-utils.d.mts +3 -4
  8. package/dist/api/route-utils.d.mts.map +1 -1
  9. package/dist/api/route-utils.mjs +26 -25
  10. package/dist/api/route-utils.mjs.map +1 -1
  11. package/dist/api/schemas/index.d.mts +2 -2
  12. package/dist/api/schemas/index.mjs +6 -5
  13. package/dist/{api-DgPbMlng.mjs → api-DdAsirBe.mjs} +321 -428
  14. package/dist/api-DdAsirBe.mjs.map +1 -0
  15. package/dist/{api-tokens-p-iMzvXR.mjs → api-tokens-CFXu8F_2.mjs} +2 -2
  16. package/dist/{api-tokens-p-iMzvXR.mjs.map → api-tokens-CFXu8F_2.mjs.map} +1 -1
  17. package/dist/{apply-1_6ra7NP.mjs → apply-D5zfeD09.mjs} +139 -102
  18. package/dist/apply-D5zfeD09.mjs.map +1 -0
  19. package/dist/astro/index.d.mts +12 -12
  20. package/dist/astro/index.d.mts.map +1 -1
  21. package/dist/astro/index.mjs +103 -35
  22. package/dist/astro/index.mjs.map +1 -1
  23. package/dist/astro/middleware/auth.d.mts +10 -10
  24. package/dist/astro/middleware/auth.mjs +9 -9
  25. package/dist/astro/middleware/media-usage-write-fence.d.mts +7 -0
  26. package/dist/astro/middleware/media-usage-write-fence.d.mts.map +1 -0
  27. package/dist/astro/middleware/media-usage-write-fence.mjs +35 -0
  28. package/dist/astro/middleware/media-usage-write-fence.mjs.map +1 -0
  29. package/dist/astro/middleware/redirect.d.mts.map +1 -1
  30. package/dist/astro/middleware/redirect.mjs +13 -10
  31. package/dist/astro/middleware/redirect.mjs.map +1 -1
  32. package/dist/astro/middleware/request-context.mjs +5 -5
  33. package/dist/astro/middleware/setup.mjs +1 -1
  34. package/dist/astro/middleware.d.mts +12 -11
  35. package/dist/astro/middleware.d.mts.map +1 -1
  36. package/dist/astro/middleware.mjs +1915 -223
  37. package/dist/astro/middleware.mjs.map +1 -1
  38. package/dist/astro/routes/api/admin/allowed-domains/_domain_.mjs +9 -8
  39. package/dist/astro/routes/api/admin/allowed-domains/_domain_.mjs.map +1 -1
  40. package/dist/astro/routes/api/admin/allowed-domains/index.mjs +9 -8
  41. package/dist/astro/routes/api/admin/allowed-domains/index.mjs.map +1 -1
  42. package/dist/astro/routes/api/admin/api-tokens/_id_.mjs +5 -5
  43. package/dist/astro/routes/api/admin/api-tokens/index.mjs +6 -6
  44. package/dist/astro/routes/api/admin/byline-fields/_slug_/usage.mjs +6 -6
  45. package/dist/astro/routes/api/admin/byline-fields/_slug_.mjs +12 -11
  46. package/dist/astro/routes/api/admin/byline-fields/_slug_.mjs.map +1 -1
  47. package/dist/astro/routes/api/admin/byline-fields/index.mjs +12 -11
  48. package/dist/astro/routes/api/admin/byline-fields/index.mjs.map +1 -1
  49. package/dist/astro/routes/api/admin/byline-fields/reorder.mjs +12 -11
  50. package/dist/astro/routes/api/admin/byline-fields/reorder.mjs.map +1 -1
  51. package/dist/astro/routes/api/admin/bylines/_id_/index.mjs +20 -20
  52. package/dist/astro/routes/api/admin/bylines/_id_/translations.mjs +20 -20
  53. package/dist/astro/routes/api/admin/bylines/index.mjs +20 -20
  54. package/dist/astro/routes/api/admin/comments/_id_/status.mjs +18 -17
  55. package/dist/astro/routes/api/admin/comments/_id_/status.mjs.map +1 -1
  56. package/dist/astro/routes/api/admin/comments/_id_.mjs +8 -8
  57. package/dist/astro/routes/api/admin/comments/bulk.mjs +14 -13
  58. package/dist/astro/routes/api/admin/comments/bulk.mjs.map +1 -1
  59. package/dist/astro/routes/api/admin/comments/counts.mjs +8 -8
  60. package/dist/astro/routes/api/admin/comments/index.mjs +14 -13
  61. package/dist/astro/routes/api/admin/comments/index.mjs.map +1 -1
  62. package/dist/astro/routes/api/admin/hooks/exclusive/_hookName_.mjs +6 -6
  63. package/dist/astro/routes/api/admin/hooks/exclusive/index.mjs +5 -5
  64. package/dist/astro/routes/api/admin/media-usage/collection-deletions/index.d.mts +8 -0
  65. package/dist/astro/routes/api/admin/media-usage/collection-deletions/index.d.mts.map +1 -0
  66. package/dist/astro/routes/api/admin/media-usage/collection-deletions/index.mjs +36 -0
  67. package/dist/astro/routes/api/admin/media-usage/collection-deletions/index.mjs.map +1 -0
  68. package/dist/astro/routes/api/admin/media-usage/collection-deletions/retry.d.mts +8 -0
  69. package/dist/astro/routes/api/admin/media-usage/collection-deletions/retry.d.mts.map +1 -0
  70. package/dist/astro/routes/api/admin/media-usage/collection-deletions/retry.mjs +36 -0
  71. package/dist/astro/routes/api/admin/media-usage/collection-deletions/retry.mjs.map +1 -0
  72. package/dist/astro/routes/api/admin/media-usage/repair.mjs +15 -14
  73. package/dist/astro/routes/api/admin/media-usage/repair.mjs.map +1 -1
  74. package/dist/astro/routes/api/admin/media-usage/work/index.d.mts +8 -0
  75. package/dist/astro/routes/api/admin/media-usage/work/index.d.mts.map +1 -0
  76. package/dist/astro/routes/api/admin/media-usage/work/index.mjs +37 -0
  77. package/dist/astro/routes/api/admin/media-usage/work/index.mjs.map +1 -0
  78. package/dist/astro/routes/api/admin/media-usage/work/retry.d.mts +8 -0
  79. package/dist/astro/routes/api/admin/media-usage/work/retry.d.mts.map +1 -0
  80. package/dist/astro/routes/api/admin/media-usage/work/retry.mjs +37 -0
  81. package/dist/astro/routes/api/admin/media-usage/work/retry.mjs.map +1 -0
  82. package/dist/astro/routes/api/admin/oauth-clients/_id_.mjs +5 -5
  83. package/dist/astro/routes/api/admin/oauth-clients/index.mjs +5 -5
  84. package/dist/astro/routes/api/admin/plugins/_id_/disable.d.mts.map +1 -1
  85. package/dist/astro/routes/api/admin/plugins/_id_/disable.mjs +56 -47
  86. package/dist/astro/routes/api/admin/plugins/_id_/disable.mjs.map +1 -1
  87. package/dist/astro/routes/api/admin/plugins/_id_/enable.d.mts.map +1 -1
  88. package/dist/astro/routes/api/admin/plugins/_id_/enable.mjs +56 -47
  89. package/dist/astro/routes/api/admin/plugins/_id_/enable.mjs.map +1 -1
  90. package/dist/astro/routes/api/admin/plugins/_id_/index.mjs +52 -46
  91. package/dist/astro/routes/api/admin/plugins/_id_/index.mjs.map +1 -1
  92. package/dist/astro/routes/api/admin/plugins/_id_/mcp.mjs +6 -6
  93. package/dist/astro/routes/api/admin/plugins/_id_/settings.mjs +52 -46
  94. package/dist/astro/routes/api/admin/plugins/_id_/settings.mjs.map +1 -1
  95. package/dist/astro/routes/api/admin/plugins/_id_/uninstall.d.mts.map +1 -1
  96. package/dist/astro/routes/api/admin/plugins/_id_/uninstall.mjs +55 -46
  97. package/dist/astro/routes/api/admin/plugins/_id_/uninstall.mjs.map +1 -1
  98. package/dist/astro/routes/api/admin/plugins/_id_/update.d.mts.map +1 -1
  99. package/dist/astro/routes/api/admin/plugins/_id_/update.mjs +55 -46
  100. package/dist/astro/routes/api/admin/plugins/_id_/update.mjs.map +1 -1
  101. package/dist/astro/routes/api/admin/plugins/index.mjs +52 -46
  102. package/dist/astro/routes/api/admin/plugins/index.mjs.map +1 -1
  103. package/dist/astro/routes/api/admin/plugins/marketplace/_id_/icon.mjs +4 -4
  104. package/dist/astro/routes/api/admin/plugins/marketplace/_id_/index.mjs +52 -46
  105. package/dist/astro/routes/api/admin/plugins/marketplace/_id_/index.mjs.map +1 -1
  106. package/dist/astro/routes/api/admin/plugins/marketplace/_id_/install.d.mts.map +1 -1
  107. package/dist/astro/routes/api/admin/plugins/marketplace/_id_/install.mjs +55 -46
  108. package/dist/astro/routes/api/admin/plugins/marketplace/_id_/install.mjs.map +1 -1
  109. package/dist/astro/routes/api/admin/plugins/marketplace/index.mjs +52 -46
  110. package/dist/astro/routes/api/admin/plugins/marketplace/index.mjs.map +1 -1
  111. package/dist/astro/routes/api/admin/plugins/registry/_id_/uninstall.d.mts.map +1 -1
  112. package/dist/astro/routes/api/admin/plugins/registry/_id_/uninstall.mjs +55 -46
  113. package/dist/astro/routes/api/admin/plugins/registry/_id_/uninstall.mjs.map +1 -1
  114. package/dist/astro/routes/api/admin/plugins/registry/_id_/update.d.mts.map +1 -1
  115. package/dist/astro/routes/api/admin/plugins/registry/_id_/update.mjs +56 -47
  116. package/dist/astro/routes/api/admin/plugins/registry/_id_/update.mjs.map +1 -1
  117. package/dist/astro/routes/api/admin/plugins/registry/artifact.mjs +52 -46
  118. package/dist/astro/routes/api/admin/plugins/registry/artifact.mjs.map +1 -1
  119. package/dist/astro/routes/api/admin/plugins/registry/install.d.mts.map +1 -1
  120. package/dist/astro/routes/api/admin/plugins/registry/install.mjs +56 -47
  121. package/dist/astro/routes/api/admin/plugins/registry/install.mjs.map +1 -1
  122. package/dist/astro/routes/api/admin/plugins/updates.mjs +52 -46
  123. package/dist/astro/routes/api/admin/plugins/updates.mjs.map +1 -1
  124. package/dist/astro/routes/api/admin/themes/marketplace/_id_/index.mjs +52 -46
  125. package/dist/astro/routes/api/admin/themes/marketplace/_id_/index.mjs.map +1 -1
  126. package/dist/astro/routes/api/admin/themes/marketplace/_id_/thumbnail.mjs +4 -4
  127. package/dist/astro/routes/api/admin/themes/marketplace/index.mjs +52 -46
  128. package/dist/astro/routes/api/admin/themes/marketplace/index.mjs.map +1 -1
  129. package/dist/astro/routes/api/admin/users/_id_/disable.mjs +4 -4
  130. package/dist/astro/routes/api/admin/users/_id_/enable.mjs +3 -3
  131. package/dist/astro/routes/api/admin/users/_id_/index.mjs +10 -9
  132. package/dist/astro/routes/api/admin/users/_id_/index.mjs.map +1 -1
  133. package/dist/astro/routes/api/admin/users/_id_/send-recovery.mjs +6 -6
  134. package/dist/astro/routes/api/admin/users/_id_/send-recovery.mjs.map +1 -1
  135. package/dist/astro/routes/api/admin/users/index.mjs +9 -8
  136. package/dist/astro/routes/api/admin/users/index.mjs.map +1 -1
  137. package/dist/astro/routes/api/auth/dev-bypass.mjs +8 -8
  138. package/dist/astro/routes/api/auth/invite/accept.mjs +3 -3
  139. package/dist/astro/routes/api/auth/invite/complete.mjs +14 -13
  140. package/dist/astro/routes/api/auth/invite/complete.mjs.map +1 -1
  141. package/dist/astro/routes/api/auth/invite/index.mjs +12 -11
  142. package/dist/astro/routes/api/auth/invite/index.mjs.map +1 -1
  143. package/dist/astro/routes/api/auth/invite/register-options.mjs +13 -12
  144. package/dist/astro/routes/api/auth/invite/register-options.mjs.map +1 -1
  145. package/dist/astro/routes/api/auth/logout.mjs +4 -4
  146. package/dist/astro/routes/api/auth/magic-link/send.mjs +14 -13
  147. package/dist/astro/routes/api/auth/magic-link/send.mjs.map +1 -1
  148. package/dist/astro/routes/api/auth/magic-link/verify.mjs +4 -4
  149. package/dist/astro/routes/api/auth/me.mjs +10 -9
  150. package/dist/astro/routes/api/auth/me.mjs.map +1 -1
  151. package/dist/astro/routes/api/auth/mode.mjs +4 -4
  152. package/dist/astro/routes/api/auth/oauth/_provider_/callback.mjs +4 -4
  153. package/dist/astro/routes/api/auth/oauth/_provider_.mjs +2 -2
  154. package/dist/astro/routes/api/auth/passkey/_id_.mjs +9 -8
  155. package/dist/astro/routes/api/auth/passkey/_id_.mjs.map +1 -1
  156. package/dist/astro/routes/api/auth/passkey/index.mjs +3 -3
  157. package/dist/astro/routes/api/auth/passkey/options.mjs +15 -14
  158. package/dist/astro/routes/api/auth/passkey/options.mjs.map +1 -1
  159. package/dist/astro/routes/api/auth/passkey/register/options.mjs +13 -12
  160. package/dist/astro/routes/api/auth/passkey/register/options.mjs.map +1 -1
  161. package/dist/astro/routes/api/auth/passkey/register/verify.mjs +14 -13
  162. package/dist/astro/routes/api/auth/passkey/register/verify.mjs.map +1 -1
  163. package/dist/astro/routes/api/auth/passkey/verify.mjs +14 -13
  164. package/dist/astro/routes/api/auth/passkey/verify.mjs.map +1 -1
  165. package/dist/astro/routes/api/auth/signup/complete.mjs +14 -13
  166. package/dist/astro/routes/api/auth/signup/complete.mjs.map +1 -1
  167. package/dist/astro/routes/api/auth/signup/request.mjs +14 -13
  168. package/dist/astro/routes/api/auth/signup/request.mjs.map +1 -1
  169. package/dist/astro/routes/api/auth/signup/verify.mjs +3 -3
  170. package/dist/astro/routes/api/comments/_collection_/_contentId_/index.mjs +20 -19
  171. package/dist/astro/routes/api/comments/_collection_/_contentId_/index.mjs.map +1 -1
  172. package/dist/astro/routes/api/comments/_collection_/_contentId_/reactions.mjs +17 -16
  173. package/dist/astro/routes/api/comments/_collection_/_contentId_/reactions.mjs.map +1 -1
  174. package/dist/astro/routes/api/content/_collection_/_id_/compare.mjs +4 -4
  175. package/dist/astro/routes/api/content/_collection_/_id_/discard-draft.mjs +5 -5
  176. package/dist/astro/routes/api/content/_collection_/_id_/duplicate.mjs +5 -5
  177. package/dist/astro/routes/api/content/_collection_/_id_/permanent.mjs +4 -4
  178. package/dist/astro/routes/api/content/_collection_/_id_/preview-url.mjs +15 -15
  179. package/dist/astro/routes/api/content/_collection_/_id_/publish.mjs +11 -10
  180. package/dist/astro/routes/api/content/_collection_/_id_/publish.mjs.map +1 -1
  181. package/dist/astro/routes/api/content/_collection_/_id_/references/_relation_/children.mjs +21 -20
  182. package/dist/astro/routes/api/content/_collection_/_id_/references/_relation_/children.mjs.map +1 -1
  183. package/dist/astro/routes/api/content/_collection_/_id_/references/_relation_/parents.mjs +21 -20
  184. package/dist/astro/routes/api/content/_collection_/_id_/references/_relation_/parents.mjs.map +1 -1
  185. package/dist/astro/routes/api/content/_collection_/_id_/restore.mjs +5 -5
  186. package/dist/astro/routes/api/content/_collection_/_id_/revisions.mjs +4 -4
  187. package/dist/astro/routes/api/content/_collection_/_id_/schedule.mjs +11 -10
  188. package/dist/astro/routes/api/content/_collection_/_id_/schedule.mjs.map +1 -1
  189. package/dist/astro/routes/api/content/_collection_/_id_/terms/_taxonomy_.d.mts.map +1 -1
  190. package/dist/astro/routes/api/content/_collection_/_id_/terms/_taxonomy_.mjs +47 -34
  191. package/dist/astro/routes/api/content/_collection_/_id_/terms/_taxonomy_.mjs.map +1 -1
  192. package/dist/astro/routes/api/content/_collection_/_id_/translations.mjs +4 -4
  193. package/dist/astro/routes/api/content/_collection_/_id_/unpublish.mjs +5 -5
  194. package/dist/astro/routes/api/content/_collection_/_id_.mjs +11 -10
  195. package/dist/astro/routes/api/content/_collection_/_id_.mjs.map +1 -1
  196. package/dist/astro/routes/api/content/_collection_/authors.mjs +4 -4
  197. package/dist/astro/routes/api/content/_collection_/index.mjs +11 -10
  198. package/dist/astro/routes/api/content/_collection_/index.mjs.map +1 -1
  199. package/dist/astro/routes/api/content/_collection_/trash.mjs +10 -9
  200. package/dist/astro/routes/api/content/_collection_/trash.mjs.map +1 -1
  201. package/dist/astro/routes/api/dashboard.mjs +12 -10
  202. package/dist/astro/routes/api/dashboard.mjs.map +1 -1
  203. package/dist/astro/routes/api/dev/emails.mjs +4 -4
  204. package/dist/astro/routes/api/import/probe.d.mts +3 -3
  205. package/dist/astro/routes/api/import/probe.mjs +22 -20
  206. package/dist/astro/routes/api/import/probe.mjs.map +1 -1
  207. package/dist/astro/routes/api/import/wordpress/analyze.mjs +5 -5
  208. package/dist/astro/routes/api/import/wordpress/execute.d.mts +11 -11
  209. package/dist/astro/routes/api/import/wordpress/execute.mjs +18 -18
  210. package/dist/astro/routes/api/import/wordpress/execute.mjs.map +1 -1
  211. package/dist/astro/routes/api/import/wordpress/media.d.mts +10 -10
  212. package/dist/astro/routes/api/import/wordpress/media.mjs +14 -12
  213. package/dist/astro/routes/api/import/wordpress/media.mjs.map +1 -1
  214. package/dist/astro/routes/api/import/wordpress/prepare.mjs +13 -12
  215. package/dist/astro/routes/api/import/wordpress/prepare.mjs.map +1 -1
  216. package/dist/astro/routes/api/import/wordpress/rewrite-urls.d.mts +11 -11
  217. package/dist/astro/routes/api/import/wordpress/rewrite-urls.mjs +15 -15
  218. package/dist/astro/routes/api/import/wordpress-plugin/analyze.d.mts +1 -1
  219. package/dist/astro/routes/api/import/wordpress-plugin/analyze.mjs +22 -20
  220. package/dist/astro/routes/api/import/wordpress-plugin/analyze.mjs.map +1 -1
  221. package/dist/astro/routes/api/import/wordpress-plugin/callback.mjs +1 -1
  222. package/dist/astro/routes/api/import/wordpress-plugin/execute.d.mts +11 -11
  223. package/dist/astro/routes/api/import/wordpress-plugin/execute.mjs +32 -31
  224. package/dist/astro/routes/api/import/wordpress-plugin/execute.mjs.map +1 -1
  225. package/dist/astro/routes/api/manifest.mjs +6 -6
  226. package/dist/astro/routes/api/mcp.d.mts.map +1 -1
  227. package/dist/astro/routes/api/mcp.mjs +174 -72
  228. package/dist/astro/routes/api/mcp.mjs.map +1 -1
  229. package/dist/astro/routes/api/media/_id_/confirm.mjs +14 -12
  230. package/dist/astro/routes/api/media/_id_/confirm.mjs.map +1 -1
  231. package/dist/astro/routes/api/media/_id_/upload.mjs +7 -7
  232. package/dist/astro/routes/api/media/_id_/usage.mjs +17 -16
  233. package/dist/astro/routes/api/media/_id_/usage.mjs.map +1 -1
  234. package/dist/astro/routes/api/media/_id_.mjs +16 -15
  235. package/dist/astro/routes/api/media/_id_.mjs.map +1 -1
  236. package/dist/astro/routes/api/media/file/_...key_.mjs +3 -3
  237. package/dist/astro/routes/api/media/providers/_providerId_/_itemId_.mjs +4 -4
  238. package/dist/astro/routes/api/media/providers/_providerId_/index.mjs +4 -4
  239. package/dist/astro/routes/api/media/providers/index.mjs +4 -4
  240. package/dist/astro/routes/api/media/upload-url.mjs +11 -10
  241. package/dist/astro/routes/api/media/upload-url.mjs.map +1 -1
  242. package/dist/astro/routes/api/media.mjs +19 -16
  243. package/dist/astro/routes/api/media.mjs.map +1 -1
  244. package/dist/astro/routes/api/menus/_name_/items/_id_.mjs +13 -13
  245. package/dist/astro/routes/api/menus/_name_/items.mjs +13 -13
  246. package/dist/astro/routes/api/menus/_name_/reorder.mjs +13 -13
  247. package/dist/astro/routes/api/menus/_name_/translations.mjs +13 -13
  248. package/dist/astro/routes/api/menus/_name_.mjs +13 -13
  249. package/dist/astro/routes/api/menus/index.mjs +13 -13
  250. package/dist/astro/routes/api/oauth/authorize.mjs +6 -6
  251. package/dist/astro/routes/api/oauth/device/authorize.mjs +7 -7
  252. package/dist/astro/routes/api/oauth/device/code.mjs +10 -10
  253. package/dist/astro/routes/api/oauth/device/token.mjs +9 -9
  254. package/dist/astro/routes/api/oauth/register.mjs +4 -4
  255. package/dist/astro/routes/api/oauth/token/refresh.mjs +7 -7
  256. package/dist/astro/routes/api/oauth/token/revoke.mjs +7 -7
  257. package/dist/astro/routes/api/oauth/token.mjs +7 -7
  258. package/dist/astro/routes/api/openapi.json.mjs +183 -6
  259. package/dist/astro/routes/api/openapi.json.mjs.map +1 -1
  260. package/dist/astro/routes/api/plugins/_pluginId_/_...path_.d.mts.map +1 -1
  261. package/dist/astro/routes/api/plugins/_pluginId_/_...path_.mjs +8 -7
  262. package/dist/astro/routes/api/plugins/_pluginId_/_...path_.mjs.map +1 -1
  263. package/dist/astro/routes/api/redirects/404s/index.mjs +14 -13
  264. package/dist/astro/routes/api/redirects/404s/index.mjs.map +1 -1
  265. package/dist/astro/routes/api/redirects/404s/summary.mjs +14 -13
  266. package/dist/astro/routes/api/redirects/404s/summary.mjs.map +1 -1
  267. package/dist/astro/routes/api/redirects/_id_.mjs +16 -14
  268. package/dist/astro/routes/api/redirects/_id_.mjs.map +1 -1
  269. package/dist/astro/routes/api/redirects/index.mjs +16 -14
  270. package/dist/astro/routes/api/redirects/index.mjs.map +1 -1
  271. package/dist/astro/routes/api/relations/_id_/index.mjs +21 -20
  272. package/dist/astro/routes/api/relations/_id_/index.mjs.map +1 -1
  273. package/dist/astro/routes/api/relations/_id_/translations.mjs +16 -15
  274. package/dist/astro/routes/api/relations/_id_/translations.mjs.map +1 -1
  275. package/dist/astro/routes/api/relations/index.mjs +21 -20
  276. package/dist/astro/routes/api/relations/index.mjs.map +1 -1
  277. package/dist/astro/routes/api/revisions/_revisionId_/index.mjs +4 -4
  278. package/dist/astro/routes/api/revisions/_revisionId_/restore.mjs +5 -5
  279. package/dist/astro/routes/api/schema/collections/_slug_/fields/_fieldSlug_.mjs +52 -46
  280. package/dist/astro/routes/api/schema/collections/_slug_/fields/_fieldSlug_.mjs.map +1 -1
  281. package/dist/astro/routes/api/schema/collections/_slug_/fields/index.mjs +52 -46
  282. package/dist/astro/routes/api/schema/collections/_slug_/fields/index.mjs.map +1 -1
  283. package/dist/astro/routes/api/schema/collections/_slug_/fields/reorder.mjs +52 -46
  284. package/dist/astro/routes/api/schema/collections/_slug_/fields/reorder.mjs.map +1 -1
  285. package/dist/astro/routes/api/schema/collections/_slug_/index.d.mts.map +1 -1
  286. package/dist/astro/routes/api/schema/collections/_slug_/index.mjs +52 -46
  287. package/dist/astro/routes/api/schema/collections/_slug_/index.mjs.map +1 -1
  288. package/dist/astro/routes/api/schema/collections/index.mjs +52 -46
  289. package/dist/astro/routes/api/schema/collections/index.mjs.map +1 -1
  290. package/dist/astro/routes/api/schema/collections/reorder.d.mts +8 -0
  291. package/dist/astro/routes/api/schema/collections/reorder.d.mts.map +1 -0
  292. package/dist/astro/routes/api/schema/collections/reorder.mjs +71 -0
  293. package/dist/astro/routes/api/schema/collections/reorder.mjs.map +1 -0
  294. package/dist/astro/routes/api/schema/index.mjs +14 -11
  295. package/dist/astro/routes/api/schema/index.mjs.map +1 -1
  296. package/dist/astro/routes/api/schema/orphans/_slug_.mjs +52 -46
  297. package/dist/astro/routes/api/schema/orphans/_slug_.mjs.map +1 -1
  298. package/dist/astro/routes/api/schema/orphans/index.mjs +52 -46
  299. package/dist/astro/routes/api/schema/orphans/index.mjs.map +1 -1
  300. package/dist/astro/routes/api/search/enable.d.mts +1 -0
  301. package/dist/astro/routes/api/search/enable.d.mts.map +1 -1
  302. package/dist/astro/routes/api/search/enable.mjs +19 -15
  303. package/dist/astro/routes/api/search/enable.mjs.map +1 -1
  304. package/dist/astro/routes/api/search/index.mjs +13 -13
  305. package/dist/astro/routes/api/search/rebuild.mjs +15 -15
  306. package/dist/astro/routes/api/search/rebuild.mjs.map +1 -1
  307. package/dist/astro/routes/api/search/stats.mjs +9 -9
  308. package/dist/astro/routes/api/search/suggest.mjs +13 -13
  309. package/dist/astro/routes/api/sections/_slug_.mjs +13 -12
  310. package/dist/astro/routes/api/sections/_slug_.mjs.map +1 -1
  311. package/dist/astro/routes/api/sections/index.mjs +13 -12
  312. package/dist/astro/routes/api/sections/index.mjs.map +1 -1
  313. package/dist/astro/routes/api/settings/backups/archives/_name_.mjs +8 -8
  314. package/dist/astro/routes/api/settings/backups/archives/index.mjs +7 -7
  315. package/dist/astro/routes/api/settings/backups/export.mjs +8 -8
  316. package/dist/astro/routes/api/settings/backups/index.mjs +9 -9
  317. package/dist/astro/routes/api/settings/email.mjs +6 -6
  318. package/dist/astro/routes/api/settings.mjs +18 -17
  319. package/dist/astro/routes/api/settings.mjs.map +1 -1
  320. package/dist/astro/routes/api/setup/admin-verify.mjs +15 -14
  321. package/dist/astro/routes/api/setup/admin-verify.mjs.map +1 -1
  322. package/dist/astro/routes/api/setup/admin.mjs +14 -13
  323. package/dist/astro/routes/api/setup/admin.mjs.map +1 -1
  324. package/dist/astro/routes/api/setup/dev-bypass.mjs +34 -32
  325. package/dist/astro/routes/api/setup/dev-bypass.mjs.map +1 -1
  326. package/dist/astro/routes/api/setup/dev-reset.mjs +4 -4
  327. package/dist/astro/routes/api/setup/index.mjs +36 -34
  328. package/dist/astro/routes/api/setup/index.mjs.map +1 -1
  329. package/dist/astro/routes/api/setup/status.mjs +5 -5
  330. package/dist/astro/routes/api/snapshot.mjs +10 -10
  331. package/dist/astro/routes/api/taxonomies/_name_/reorder.d.mts +8 -0
  332. package/dist/astro/routes/api/taxonomies/_name_/reorder.d.mts.map +1 -0
  333. package/dist/astro/routes/api/taxonomies/_name_/reorder.mjs +44 -0
  334. package/dist/astro/routes/api/taxonomies/_name_/reorder.mjs.map +1 -0
  335. package/dist/astro/routes/api/taxonomies/_name_/terms/_slug_/translations.mjs +19 -18
  336. package/dist/astro/routes/api/taxonomies/_name_/terms/_slug_/translations.mjs.map +1 -1
  337. package/dist/astro/routes/api/taxonomies/_name_/terms/_slug_.mjs +19 -18
  338. package/dist/astro/routes/api/taxonomies/_name_/terms/_slug_.mjs.map +1 -1
  339. package/dist/astro/routes/api/taxonomies/_name_/terms/index.d.mts.map +1 -1
  340. package/dist/astro/routes/api/taxonomies/_name_/terms/index.mjs +21 -19
  341. package/dist/astro/routes/api/taxonomies/_name_/terms/index.mjs.map +1 -1
  342. package/dist/astro/routes/api/taxonomies/_name_/translations.d.mts +8 -0
  343. package/dist/astro/routes/api/taxonomies/_name_/translations.d.mts.map +1 -0
  344. package/dist/astro/routes/api/taxonomies/_name_/translations.mjs +46 -0
  345. package/dist/astro/routes/api/taxonomies/_name_/translations.mjs.map +1 -0
  346. package/dist/astro/routes/api/taxonomies/_name_.d.mts +19 -0
  347. package/dist/astro/routes/api/taxonomies/_name_.d.mts.map +1 -0
  348. package/dist/astro/routes/api/taxonomies/_name_.mjs +88 -0
  349. package/dist/astro/routes/api/taxonomies/_name_.mjs.map +1 -0
  350. package/dist/astro/routes/api/taxonomies/index.mjs +19 -18
  351. package/dist/astro/routes/api/taxonomies/index.mjs.map +1 -1
  352. package/dist/astro/routes/api/themes/preview.mjs +8 -8
  353. package/dist/astro/routes/api/typegen.mjs +6 -6
  354. package/dist/astro/routes/api/well-known/auth.mjs +2 -2
  355. package/dist/astro/routes/api/well-known/oauth-authorization-server.mjs +2 -2
  356. package/dist/astro/routes/api/well-known/oauth-protected-resource.mjs +2 -2
  357. package/dist/astro/routes/api/widget-areas/_name_/reorder.mjs +10 -9
  358. package/dist/astro/routes/api/widget-areas/_name_/reorder.mjs.map +1 -1
  359. package/dist/astro/routes/api/widget-areas/_name_/widgets/_id_.mjs +13 -12
  360. package/dist/astro/routes/api/widget-areas/_name_/widgets/_id_.mjs.map +1 -1
  361. package/dist/astro/routes/api/widget-areas/_name_/widgets.mjs +13 -12
  362. package/dist/astro/routes/api/widget-areas/_name_/widgets.mjs.map +1 -1
  363. package/dist/astro/routes/api/widget-areas/_name_.mjs +8 -7
  364. package/dist/astro/routes/api/widget-areas/_name_.mjs.map +1 -1
  365. package/dist/astro/routes/api/widget-areas/index.mjs +13 -12
  366. package/dist/astro/routes/api/widget-areas/index.mjs.map +1 -1
  367. package/dist/astro/routes/api/widget-components.mjs +4 -4
  368. package/dist/astro/routes/robots.txt.mjs +11 -10
  369. package/dist/astro/routes/robots.txt.mjs.map +1 -1
  370. package/dist/astro/routes/sitemap-_collection_.xml.mjs +14 -14
  371. package/dist/astro/routes/sitemap.xml.mjs +12 -11
  372. package/dist/astro/routes/sitemap.xml.mjs.map +1 -1
  373. package/dist/astro/types.d.mts +41 -17
  374. package/dist/astro/types.d.mts.map +1 -1
  375. package/dist/auth/providers/github.d.mts +1 -1
  376. package/dist/auth/providers/google.d.mts +1 -1
  377. package/dist/{authorize-R5iYYrpa.mjs → authorize-1iFJzPaZ.mjs} +2 -2
  378. package/dist/{authorize-R5iYYrpa.mjs.map → authorize-1iFJzPaZ.mjs.map} +1 -1
  379. package/dist/{backup-LpQ1V_sR.mjs → backup-LHjIAVNP.mjs} +5 -5
  380. package/dist/{backup-LpQ1V_sR.mjs.map → backup-LHjIAVNP.mjs.map} +1 -1
  381. package/dist/{base64-B-PsqheR.mjs → base64-CvLhUKQv.mjs} +1 -1
  382. package/dist/{base64-B-PsqheR.mjs.map → base64-CvLhUKQv.mjs.map} +1 -1
  383. package/dist/bundle-CBEXrBnb.mjs +663 -0
  384. package/dist/bundle-CBEXrBnb.mjs.map +1 -0
  385. package/dist/{byline-fields-T9ZLZMxJ.mjs → byline-fields-C5S8wygO.mjs} +2 -2
  386. package/dist/{byline-fields-T9ZLZMxJ.mjs.map → byline-fields-C5S8wygO.mjs.map} +1 -1
  387. package/dist/{byline-C5TAqs8N.mjs → byline-pEcoDps8.mjs} +9 -9
  388. package/dist/{byline-C5TAqs8N.mjs.map → byline-pEcoDps8.mjs.map} +1 -1
  389. package/dist/{byline-registry-BCuOp4UF.mjs → byline-registry-DDun8sxh.mjs} +4 -4
  390. package/dist/{byline-registry-BCuOp4UF.mjs.map → byline-registry-DDun8sxh.mjs.map} +1 -1
  391. package/dist/{bylines-B8-WGdja.mjs → bylines-BWemdX2k.mjs} +8 -8
  392. package/dist/{bylines-B8-WGdja.mjs.map → bylines-BWemdX2k.mjs.map} +1 -1
  393. package/dist/{bylines-DGuqBLjV.mjs → bylines-DJfSfXCL.mjs} +5 -5
  394. package/dist/{bylines-DGuqBLjV.mjs.map → bylines-DJfSfXCL.mjs.map} +1 -1
  395. package/dist/cache-CBJaDy_E.mjs +108 -0
  396. package/dist/cache-CBJaDy_E.mjs.map +1 -0
  397. package/dist/{challenge-store-BFzgFRog.mjs → challenge-store-CZyFVaad.mjs} +1 -1
  398. package/dist/{challenge-store-BFzgFRog.mjs.map → challenge-store-CZyFVaad.mjs.map} +1 -1
  399. package/dist/{chunks-D5dlPeRb.mjs → chunks-DfPax1I0.mjs} +2 -2
  400. package/dist/{chunks-D5dlPeRb.mjs.map → chunks-DfPax1I0.mjs.map} +1 -1
  401. package/dist/cli/index.mjs +193 -707
  402. package/dist/cli/index.mjs.map +1 -1
  403. package/dist/client/cf-access.d.mts +1 -1
  404. package/dist/client/index.d.mts +74 -4
  405. package/dist/client/index.d.mts.map +1 -1
  406. package/dist/client/index.mjs +25 -2
  407. package/dist/client/index.mjs.map +1 -1
  408. package/dist/collection-deletion-C8BugSGz.mjs +779 -0
  409. package/dist/collection-deletion-C8BugSGz.mjs.map +1 -0
  410. package/dist/{comment-DnTxxVHv.mjs → comment-Dxlep6cE.mjs} +3 -3
  411. package/dist/{comment-DnTxxVHv.mjs.map → comment-Dxlep6cE.mjs.map} +1 -1
  412. package/dist/{comment-reaction-BUlUz2bh.mjs → comment-reaction-D6qfHKBc.mjs} +2 -2
  413. package/dist/{comment-reaction-BUlUz2bh.mjs.map → comment-reaction-D6qfHKBc.mjs.map} +1 -1
  414. package/dist/{comments-QPKgK3nk.mjs → comments-CTOuhTSX.mjs} +3 -3
  415. package/dist/{comments-QPKgK3nk.mjs.map → comments-CTOuhTSX.mjs.map} +1 -1
  416. package/dist/{components-DZkL4Fx0.mjs → components-CQy3lh9x.mjs} +1 -1
  417. package/dist/{components-DZkL4Fx0.mjs.map → components-CQy3lh9x.mjs.map} +1 -1
  418. package/dist/{config-DyF3OKg_.mjs → config-C3EBstHi.mjs} +18 -2
  419. package/dist/config-C3EBstHi.mjs.map +1 -0
  420. package/dist/{content-CpfKV9QE.mjs → content-BNfwh7xX.mjs} +667 -183
  421. package/dist/content-BNfwh7xX.mjs.map +1 -0
  422. package/dist/content-list-query-DhQ84eVV.d.mts +26 -0
  423. package/dist/content-list-query-DhQ84eVV.d.mts.map +1 -0
  424. package/dist/content-refresh-DNERP4-f.mjs +2560 -0
  425. package/dist/content-refresh-DNERP4-f.mjs.map +1 -0
  426. package/dist/{context-kO4YZB03.mjs → context-DRgOvSnW.mjs} +28 -20
  427. package/dist/context-DRgOvSnW.mjs.map +1 -0
  428. package/dist/{cron-BlKIMD_e.mjs → cron-Y9aLtgrA.mjs} +1 -1
  429. package/dist/{cron-BlKIMD_e.mjs.map → cron-Y9aLtgrA.mjs.map} +1 -1
  430. package/dist/{dashboard-DoBwPnON.mjs → dashboard-CB8J89rJ.mjs} +45 -11
  431. package/dist/dashboard-CB8J89rJ.mjs.map +1 -0
  432. package/dist/db/index.d.mts +4 -4
  433. package/dist/db/index.mjs +3 -3
  434. package/dist/db/index.mjs.map +1 -1
  435. package/dist/db/libsql.d.mts +1 -1
  436. package/dist/db/postgres.d.mts +1 -1
  437. package/dist/db/sqlite.d.mts +1 -1
  438. package/dist/{db-errors-CcWLaRiR.mjs → db-errors-Cl-sKYTm.mjs} +1 -1
  439. package/dist/{db-errors-CcWLaRiR.mjs.map → db-errors-Cl-sKYTm.mjs.map} +1 -1
  440. package/dist/{default-C4v9KP56.mjs → default-DdDl3fxv.mjs} +1 -1
  441. package/dist/{default-C4v9KP56.mjs.map → default-DdDl3fxv.mjs.map} +1 -1
  442. package/dist/deferred-tasks-BMsa9F64.d.mts +9 -0
  443. package/dist/deferred-tasks-BMsa9F64.d.mts.map +1 -0
  444. package/dist/{device-flow-DhUsyJU6.mjs → device-flow-CaioYGK3.mjs} +5 -5
  445. package/dist/{device-flow-DhUsyJU6.mjs.map → device-flow-CaioYGK3.mjs.map} +1 -1
  446. package/dist/{dialect-helpers-DFwyWjTM.mjs → dialect-helpers-BSbfaO3F.mjs} +24 -16
  447. package/dist/dialect-helpers-BSbfaO3F.mjs.map +1 -0
  448. package/dist/dist-D_6CKR8z.mjs +810 -0
  449. package/dist/dist-D_6CKR8z.mjs.map +1 -0
  450. package/dist/{email-console-C-9Ng8DM.mjs → email-console-BHNjIwiB.mjs} +1 -1
  451. package/dist/{email-console-C-9Ng8DM.mjs.map → email-console-BHNjIwiB.mjs.map} +1 -1
  452. package/dist/{enrich-CFJJgxs_.mjs → enrich-_ySMEvEE.mjs} +2 -2
  453. package/dist/{enrich-CFJJgxs_.mjs.map → enrich-_ySMEvEE.mjs.map} +1 -1
  454. package/dist/{error-DmmN74gW.mjs → error-DupyJZE2.mjs} +3 -3
  455. package/dist/{error-DmmN74gW.mjs.map → error-DupyJZE2.mjs.map} +1 -1
  456. package/dist/{errors-DtEXIQQV.mjs → errors-CLUPm7aD.mjs} +15 -2
  457. package/dist/errors-CLUPm7aD.mjs.map +1 -0
  458. package/dist/{escape-CdW31WsG.mjs → escape-C_aLKP3H.mjs} +1 -1
  459. package/dist/{escape-CdW31WsG.mjs.map → escape-C_aLKP3H.mjs.map} +1 -1
  460. package/dist/{field-defs-cache-QMVnzTH6.mjs → field-defs-cache-hg6QkjV9.mjs} +5 -5
  461. package/dist/{field-defs-cache-QMVnzTH6.mjs.map → field-defs-cache-hg6QkjV9.mjs.map} +1 -1
  462. package/dist/{fts-manager-vncsZIJm.mjs → fts-manager-CZ-5dVwJ.mjs} +111 -61
  463. package/dist/fts-manager-CZ-5dVwJ.mjs.map +1 -0
  464. package/dist/{hash-Cb7U1b5M.mjs → hash-Cg0TXJPV.mjs} +1 -1
  465. package/dist/{hash-Cb7U1b5M.mjs.map → hash-Cg0TXJPV.mjs.map} +1 -1
  466. package/dist/{hreflang-CZbSx6Bg.d.mts → hreflang-D3Uehfv2.d.mts} +2 -2
  467. package/dist/{hreflang-CZbSx6Bg.d.mts.map → hreflang-D3Uehfv2.d.mts.map} +1 -1
  468. package/dist/{hreflang-Bg-zMpkr.mjs → hreflang-DNswoYsi.mjs} +7 -7
  469. package/dist/{hreflang-Bg-zMpkr.mjs.map → hreflang-DNswoYsi.mjs.map} +1 -1
  470. package/dist/{import-PKhLeXvn.mjs → import-B41u8Rot.mjs} +7 -7
  471. package/dist/{import-PKhLeXvn.mjs.map → import-B41u8Rot.mjs.map} +1 -1
  472. package/dist/{index-j9rTh3cp.d.mts → index-C3Y-rsyN.d.mts} +286 -93
  473. package/dist/index-C3Y-rsyN.d.mts.map +1 -0
  474. package/dist/{index-BeNto_Vs.d.mts → index-Cof4-Fab.d.mts} +5 -10
  475. package/dist/index-Cof4-Fab.d.mts.map +1 -0
  476. package/dist/index.d.mts +20 -19
  477. package/dist/index.mjs +79 -71
  478. package/dist/{init-lock-DJkX6Hto.mjs → init-lock-6b309ZrF.mjs} +1 -1
  479. package/dist/{init-lock-DJkX6Hto.mjs.map → init-lock-6b309ZrF.mjs.map} +1 -1
  480. package/dist/{load-BwTdWE8B.mjs → load-DmvJrtxS.mjs} +2 -2
  481. package/dist/{load-BwTdWE8B.mjs.map → load-DmvJrtxS.mjs.map} +1 -1
  482. package/dist/{loader-C1XOLV5b.mjs → loader-DLBqRiGP.mjs} +120 -64
  483. package/dist/loader-DLBqRiGP.mjs.map +1 -0
  484. package/dist/{manifest-schema-bCq54i7F.mjs → manifest-schema-BXbUAHod.mjs} +1 -1
  485. package/dist/{manifest-schema-bCq54i7F.mjs.map → manifest-schema-BXbUAHod.mjs.map} +1 -1
  486. package/dist/media/image-endpoint.mjs +1 -1
  487. package/dist/media/index.d.mts +1 -1
  488. package/dist/media/index.mjs +3 -2
  489. package/dist/media/index.mjs.map +1 -1
  490. package/dist/media/local-runtime.d.mts +12 -12
  491. package/dist/media/local-runtime.mjs +10 -9
  492. package/dist/media/local-runtime.mjs.map +1 -1
  493. package/dist/{media-DWIzoVFL.mjs → media-BWWWb8kg.mjs} +92 -3
  494. package/dist/media-BWWWb8kg.mjs.map +1 -0
  495. package/dist/{media-tQDZEdu7.mjs → media-CzhAn2--.mjs} +2 -2
  496. package/dist/{media-tQDZEdu7.mjs.map → media-CzhAn2--.mjs.map} +1 -1
  497. package/dist/{media-allowlist-B7TPD6aq.mjs → media-allowlist-BD6HhgXA.mjs} +14 -3
  498. package/dist/media-allowlist-BD6HhgXA.mjs.map +1 -0
  499. package/dist/{media-upload-Bc9Nc5Zf.mjs → media-upload-9yas9zGH.mjs} +11 -9
  500. package/dist/{media-upload-Bc9Nc5Zf.mjs.map → media-upload-9yas9zGH.mjs.map} +1 -1
  501. package/dist/{media-url-BCm5vBn6.mjs → media-url-BvoX88FA.mjs} +1 -1
  502. package/dist/{media-url-BCm5vBn6.mjs.map → media-url-BvoX88FA.mjs.map} +1 -1
  503. package/dist/{media-usage-DPJcNaAq.mjs → media-usage-De3qvwjc.mjs} +138 -61
  504. package/dist/media-usage-De3qvwjc.mjs.map +1 -0
  505. package/dist/media-usage-work-B9Bksh_b.mjs +152 -0
  506. package/dist/media-usage-work-B9Bksh_b.mjs.map +1 -0
  507. package/dist/media-usage-work-DrCbqBcl.mjs +424 -0
  508. package/dist/media-usage-work-DrCbqBcl.mjs.map +1 -0
  509. package/dist/media-usage-write-fence-aHEgN1zB.mjs +42 -0
  510. package/dist/media-usage-write-fence-aHEgN1zB.mjs.map +1 -0
  511. package/dist/{menus-C6qhqP4X.mjs → menus-CC-yn1F9.mjs} +554 -121
  512. package/dist/menus-CC-yn1F9.mjs.map +1 -0
  513. package/dist/{menus-BxPLFfIc.mjs → menus-fxvEDYE6.mjs} +5 -5
  514. package/dist/{menus-BxPLFfIc.mjs.map → menus-fxvEDYE6.mjs.map} +1 -1
  515. package/dist/{mode-fiXRMfeA.mjs → mode-Bpe-tNNy.mjs} +1 -1
  516. package/dist/{mode-fiXRMfeA.mjs.map → mode-Bpe-tNNy.mjs.map} +1 -1
  517. package/dist/{normalize-C-SHXmra.mjs → normalize-Bc-s_r-a.mjs} +1 -1
  518. package/dist/{normalize-C-SHXmra.mjs.map → normalize-Bc-s_r-a.mjs.map} +1 -1
  519. package/dist/{oauth-authorization-C9tFinly.mjs → oauth-authorization-BXO1MKej.mjs} +5 -5
  520. package/dist/{oauth-authorization-C9tFinly.mjs.map → oauth-authorization-BXO1MKej.mjs.map} +1 -1
  521. package/dist/{oauth-clients-BwTxE1aE.mjs → oauth-clients-C_DNqtRu.mjs} +1 -1
  522. package/dist/{oauth-clients-BwTxE1aE.mjs.map → oauth-clients-C_DNqtRu.mjs.map} +1 -1
  523. package/dist/{oauth-state-store-DaRUwPWO.mjs → oauth-state-store-DwAxMtk4.mjs} +1 -1
  524. package/dist/{oauth-state-store-DaRUwPWO.mjs.map → oauth-state-store-DwAxMtk4.mjs.map} +1 -1
  525. package/dist/{oauth-user-lookup-CzuzOSlF.mjs → oauth-user-lookup-BxfZizdk.mjs} +1 -1
  526. package/dist/{oauth-user-lookup-CzuzOSlF.mjs.map → oauth-user-lookup-BxfZizdk.mjs.map} +1 -1
  527. package/dist/object-cache/memory.d.mts +1 -1
  528. package/dist/{object-cache-Bok5j2ae.mjs → object-cache-71tPfV4A.mjs} +106 -5
  529. package/dist/object-cache-71tPfV4A.mjs.map +1 -0
  530. package/dist/{options-BlmBHTvX.mjs → options-CBXIHUoT.mjs} +1 -1
  531. package/dist/{options-BlmBHTvX.mjs.map → options-CBXIHUoT.mjs.map} +1 -1
  532. package/dist/{options-aeIs8WFu.d.mts → options-DRe1pIBL.d.mts} +4 -3
  533. package/dist/options-DRe1pIBL.d.mts.map +1 -0
  534. package/dist/page/index.d.mts +2 -2
  535. package/dist/{parse-BL49yb9D.mjs → parse-DFbuc-Fh.mjs} +2 -2
  536. package/dist/{parse-BL49yb9D.mjs.map → parse-DFbuc-Fh.mjs.map} +1 -1
  537. package/dist/{passkey-config-KMhgFjdQ.mjs → passkey-config-_2GOwwK8.mjs} +1 -1
  538. package/dist/{passkey-config-KMhgFjdQ.mjs.map → passkey-config-_2GOwwK8.mjs.map} +1 -1
  539. package/dist/{placeholder-Dxo5Zt58.d.mts → placeholder-CzW7Lshs.d.mts} +1 -1
  540. package/dist/{placeholder-Dxo5Zt58.d.mts.map → placeholder-CzW7Lshs.d.mts.map} +1 -1
  541. package/dist/plugin-types.d.mts +8 -1
  542. package/dist/plugin-types.d.mts.map +1 -1
  543. package/dist/plugin-utils.d.mts +10 -10
  544. package/dist/plugins/adapt-sandbox-entry.d.mts +10 -10
  545. package/dist/plugins/adapt-sandbox-entry.mjs +7 -4
  546. package/dist/plugins/adapt-sandbox-entry.mjs.map +1 -1
  547. package/dist/{portable-text-CNahFfj6.mjs → portable-text-DhKbDAGr.mjs} +1 -1
  548. package/dist/{portable-text-CNahFfj6.mjs.map → portable-text-DhKbDAGr.mjs.map} +1 -1
  549. package/dist/{preview-D4Jnbfx7.mjs → preview-PW-nOnq4.mjs} +2 -2
  550. package/dist/{preview-D4Jnbfx7.mjs.map → preview-PW-nOnq4.mjs.map} +1 -1
  551. package/dist/{public-url-DSGTnJFw.mjs → public-url-CWoFhQT8.mjs} +14 -3
  552. package/dist/public-url-CWoFhQT8.mjs.map +1 -0
  553. package/dist/{query-DCiXI7OZ.mjs → query-BgjfiLUQ.mjs} +38 -77
  554. package/dist/query-BgjfiLUQ.mjs.map +1 -0
  555. package/dist/{query-1xOcEy18.mjs → query-vgZNwIhh.mjs} +4 -4
  556. package/dist/{query-1xOcEy18.mjs.map → query-vgZNwIhh.mjs.map} +1 -1
  557. package/dist/{rate-limit-Vkp9gQ1Y.mjs → rate-limit-L5anykgo.mjs} +2 -2
  558. package/dist/{rate-limit-Vkp9gQ1Y.mjs.map → rate-limit-L5anykgo.mjs.map} +1 -1
  559. package/dist/{redirect-BJ6d1yHh.mjs → redirect-COsS6SWJ.mjs} +3 -3
  560. package/dist/{redirect-BJ6d1yHh.mjs.map → redirect-COsS6SWJ.mjs.map} +1 -1
  561. package/dist/{redirect-CDgfv9vh.mjs → redirect-KBNE3UEs.mjs} +1 -1
  562. package/dist/{redirect-CDgfv9vh.mjs.map → redirect-KBNE3UEs.mjs.map} +1 -1
  563. package/dist/{redirects-Cwkq2H-G.mjs → redirects-CufRQt0Q.mjs} +5 -5
  564. package/dist/{redirects-Cwkq2H-G.mjs.map → redirects-CufRQt0Q.mjs.map} +1 -1
  565. package/dist/{redirects-BOn2DIUs.mjs → redirects-cV9g7V-0.mjs} +149 -16
  566. package/dist/redirects-cV9g7V-0.mjs.map +1 -0
  567. package/dist/registry-C581V4TP.mjs +1275 -0
  568. package/dist/registry-C581V4TP.mjs.map +1 -0
  569. package/dist/{relation-DJ5DZh7B.mjs → relation-DtmAQH7s.mjs} +3 -3
  570. package/dist/{relation-DJ5DZh7B.mjs.map → relation-DtmAQH7s.mjs.map} +1 -1
  571. package/dist/{relations-C4duJnwI.mjs → relations-BBApI4e2.mjs} +3 -3
  572. package/dist/{relations-C4duJnwI.mjs.map → relations-BBApI4e2.mjs.map} +1 -1
  573. package/dist/{relations-DpTjftCl.mjs → relations-DICSyfsh.mjs} +6 -6
  574. package/dist/{relations-DpTjftCl.mjs.map → relations-DICSyfsh.mjs.map} +1 -1
  575. package/dist/{relations-DHFQGX0h.d.mts → relations-DItI3MN9.d.mts} +401 -40
  576. package/dist/relations-DItI3MN9.d.mts.map +1 -0
  577. package/dist/request-context.d.mts +3 -0
  578. package/dist/request-context.d.mts.map +1 -1
  579. package/dist/request-context.mjs.map +1 -1
  580. package/dist/{request-meta-DzXYYI-n.mjs → request-meta-DgZJh3zG.mjs} +2 -2
  581. package/dist/{request-meta-DzXYYI-n.mjs.map → request-meta-DgZJh3zG.mjs.map} +1 -1
  582. package/dist/{resolve-BUvFE0Lr.mjs → resolve-DOhVEvty.mjs} +2 -2
  583. package/dist/{resolve-BUvFE0Lr.mjs.map → resolve-DOhVEvty.mjs.map} +1 -1
  584. package/dist/{runner-BsI18UgP.mjs → runner-BiDvq5dv.mjs} +1404 -235
  585. package/dist/runner-BiDvq5dv.mjs.map +1 -0
  586. package/dist/{runner-CHdkERbt.d.mts → runner-CgQbELYC.d.mts} +2 -2
  587. package/dist/{runner-CHdkERbt.d.mts.map → runner-CgQbELYC.d.mts.map} +1 -1
  588. package/dist/runtime.d.mts +11 -11
  589. package/dist/runtime.mjs +5 -4
  590. package/dist/runtime.mjs.map +1 -1
  591. package/dist/{schema-eqZhkR0S.mjs → schema-BFyTg38T.mjs} +3 -3
  592. package/dist/{schema-eqZhkR0S.mjs.map → schema-BFyTg38T.mjs.map} +1 -1
  593. package/dist/schema-CeQSNwB3.mjs +390 -0
  594. package/dist/schema-CeQSNwB3.mjs.map +1 -0
  595. package/dist/{scopes-Be2d8bSb.mjs → scopes-BVeuhGBE.mjs} +3 -3
  596. package/dist/{scopes-Be2d8bSb.mjs.map → scopes-BVeuhGBE.mjs.map} +1 -1
  597. package/dist/{search-CeO678cp.mjs → search-BpuPKZb0.mjs} +26 -16
  598. package/dist/search-BpuPKZb0.mjs.map +1 -0
  599. package/dist/{secrets-870d-7yA.mjs → secrets-dtYs2hDo.mjs} +5 -5
  600. package/dist/{secrets-870d-7yA.mjs.map → secrets-dtYs2hDo.mjs.map} +1 -1
  601. package/dist/{sections-DSuEfirn.mjs → sections-COctk6hf.mjs} +3 -3
  602. package/dist/{sections-DSuEfirn.mjs.map → sections-COctk6hf.mjs.map} +1 -1
  603. package/dist/seed/index.d.mts +2 -2
  604. package/dist/seed/index.mjs +28 -26
  605. package/dist/seo/index.d.mts +3 -3
  606. package/dist/seo/index.mjs +20 -19
  607. package/dist/seo/index.mjs.map +1 -1
  608. package/dist/{seo-C3GDfT0V.mjs → seo-AFpVvTqr.mjs} +6 -4
  609. package/dist/seo-AFpVvTqr.mjs.map +1 -0
  610. package/dist/{seo-BAPKiED8.mjs → seo-CvDxfvFb.mjs} +3 -3
  611. package/dist/{seo-BAPKiED8.mjs.map → seo-CvDxfvFb.mjs.map} +1 -1
  612. package/dist/{service-DyFT-k-R.mjs → service-xMiMSTsR.mjs} +4 -4
  613. package/dist/{service-DyFT-k-R.mjs.map → service-xMiMSTsR.mjs.map} +1 -1
  614. package/dist/{session-user-BrK2zz7S.mjs → session-user-BzVemLkw.mjs} +2 -2
  615. package/dist/{session-user-BrK2zz7S.mjs.map → session-user-BzVemLkw.mjs.map} +1 -1
  616. package/dist/{settings-DgKouY2S.mjs → settings-B372MV0p.mjs} +7 -7
  617. package/dist/{settings-DgKouY2S.mjs.map → settings-B372MV0p.mjs.map} +1 -1
  618. package/dist/{settings-CREKyj8I.mjs → settings-BE9aqn_9.mjs} +3 -3
  619. package/dist/{settings-CREKyj8I.mjs.map → settings-BE9aqn_9.mjs.map} +1 -1
  620. package/dist/{setup-complete-L7bMK2VI.mjs → setup-complete-DF7TAfD5.mjs} +2 -2
  621. package/dist/{setup-complete-L7bMK2VI.mjs.map → setup-complete-DF7TAfD5.mjs.map} +1 -1
  622. package/dist/{setup-nonce-Ct5tjWcq.mjs → setup-nonce-Do-U_cg9.mjs} +1 -1
  623. package/dist/{setup-nonce-Ct5tjWcq.mjs.map → setup-nonce-Do-U_cg9.mjs.map} +1 -1
  624. package/dist/{single-flight-cache-C2exrGAi.mjs → single-flight-cache-B0eLKS6K.mjs} +2 -2
  625. package/dist/{single-flight-cache-C2exrGAi.mjs.map → single-flight-cache-B0eLKS6K.mjs.map} +1 -1
  626. package/dist/site-url-Bowsi9T-.mjs +16 -0
  627. package/dist/site-url-Bowsi9T-.mjs.map +1 -0
  628. package/dist/slugify-B994zkXC.mjs +17 -0
  629. package/dist/slugify-B994zkXC.mjs.map +1 -0
  630. package/dist/{snapshot-BdpUJKD-.mjs → snapshot-B5h6aPMh.mjs} +2 -2
  631. package/dist/{snapshot-BdpUJKD-.mjs.map → snapshot-B5h6aPMh.mjs.map} +1 -1
  632. package/dist/{ssrf-CviKqWmq.mjs → ssrf-Cpvg_n3A.mjs} +1 -1
  633. package/dist/{ssrf-CviKqWmq.mjs.map → ssrf-Cpvg_n3A.mjs.map} +1 -1
  634. package/dist/{state-xxv6ZTMv.mjs → state-DYwPue40.mjs} +1 -1
  635. package/dist/{state-xxv6ZTMv.mjs.map → state-DYwPue40.mjs.map} +1 -1
  636. package/dist/{status-COfycGIU.mjs → status-CWVYpbD8.mjs} +1 -1
  637. package/dist/{status-COfycGIU.mjs.map → status-CWVYpbD8.mjs.map} +1 -1
  638. package/dist/storage/local.d.mts +1 -1
  639. package/dist/storage/local.mjs +1 -1
  640. package/dist/storage/s3.d.mts +1 -1
  641. package/dist/storage/s3.mjs +1 -1
  642. package/dist/{taxonomies-B61CRSha.mjs → taxonomies-B0o9ExNV.mjs} +85 -75
  643. package/dist/taxonomies-B0o9ExNV.mjs.map +1 -0
  644. package/dist/{taxonomies-Dbdki3Un.mjs → taxonomies-Dk3MAklL.mjs} +360 -56
  645. package/dist/taxonomies-Dk3MAklL.mjs.map +1 -0
  646. package/dist/taxonomy-CPeM8d2o.mjs +484 -0
  647. package/dist/taxonomy-CPeM8d2o.mjs.map +1 -0
  648. package/dist/{tokens-DVltpO2D.mjs → tokens-C39klX8R.mjs} +2 -2
  649. package/dist/{tokens-DVltpO2D.mjs.map → tokens-C39klX8R.mjs.map} +1 -1
  650. package/dist/{transaction-D0FOsb3X.mjs → transaction-NQj4VJ7Z.mjs} +1 -1
  651. package/dist/{transaction-D0FOsb3X.mjs.map → transaction-NQj4VJ7Z.mjs.map} +1 -1
  652. package/dist/{transport-BWQo0Foy.mjs → transport--CfOflrp.mjs} +1 -1
  653. package/dist/{transport-BWQo0Foy.mjs.map → transport--CfOflrp.mjs.map} +1 -1
  654. package/dist/{transport-DokJOScS.d.mts → transport-B_rfeU-a.d.mts} +1 -1
  655. package/dist/{transport-DokJOScS.d.mts.map → transport-B_rfeU-a.d.mts.map} +1 -1
  656. package/dist/{trusted-proxy-CwjQj0YG.mjs → trusted-proxy-CEVekpby.mjs} +1 -1
  657. package/dist/{trusted-proxy-CwjQj0YG.mjs.map → trusted-proxy-CEVekpby.mjs.map} +1 -1
  658. package/dist/{types-o7xo7VgH.mjs → types-75KIqzL9.mjs} +20 -3
  659. package/dist/types-75KIqzL9.mjs.map +1 -0
  660. package/dist/{types-C9P3ysxq.d.mts → types-BPuloofb.d.mts} +1 -1
  661. package/dist/{types-C9P3ysxq.d.mts.map → types-BPuloofb.d.mts.map} +1 -1
  662. package/dist/{types-BD40g7zz.mjs → types-BW1syrlw.mjs} +1 -1
  663. package/dist/{types-BD40g7zz.mjs.map → types-BW1syrlw.mjs.map} +1 -1
  664. package/dist/{types-jISEalTX.d.mts → types-C3_AbkDP.d.mts} +53 -10
  665. package/dist/types-C3_AbkDP.d.mts.map +1 -0
  666. package/dist/{types-84Bque3-.d.mts → types-CAGdePf3.d.mts} +133 -1
  667. package/dist/types-CAGdePf3.d.mts.map +1 -0
  668. package/dist/{types-CcSZCcF1.d.mts → types-CFUfyt1s.d.mts} +1 -1
  669. package/dist/{types-CcSZCcF1.d.mts.map → types-CFUfyt1s.d.mts.map} +1 -1
  670. package/dist/{types-DQLZ58GV.d.mts → types-CPx2lIGo.d.mts} +1 -1
  671. package/dist/{types-DQLZ58GV.d.mts.map → types-CPx2lIGo.d.mts.map} +1 -1
  672. package/dist/{types-XrQQ-Aex.mjs → types-CQPWhPxE.mjs} +15 -11
  673. package/dist/types-CQPWhPxE.mjs.map +1 -0
  674. package/dist/{types-BQY7VYw6.d.mts → types-Cs-TFLNf.d.mts} +28 -8
  675. package/dist/types-Cs-TFLNf.d.mts.map +1 -0
  676. package/dist/types-CtzytVXn.mjs +18 -0
  677. package/dist/types-CtzytVXn.mjs.map +1 -0
  678. package/dist/{types-DqZVPILm.d.mts → types-D4_1Ga4L.d.mts} +44 -5
  679. package/dist/types-D4_1Ga4L.d.mts.map +1 -0
  680. package/dist/{types-Dr2GLlwu.d.mts → types-DefV3OiO.d.mts} +1 -1
  681. package/dist/{types-Dr2GLlwu.d.mts.map → types-DefV3OiO.d.mts.map} +1 -1
  682. package/dist/{types-DsAMyD_o.d.mts → types-X0MThr7x.d.mts} +1 -1
  683. package/dist/{types-DsAMyD_o.d.mts.map → types-X0MThr7x.d.mts.map} +1 -1
  684. package/dist/{upload-attempts-C5yd6Gae.mjs → upload-attempts-hlne3iA1.mjs} +1 -1
  685. package/dist/{upload-attempts-C5yd6Gae.mjs.map → upload-attempts-hlne3iA1.mjs.map} +1 -1
  686. package/dist/url-pattern-BHS0V5Ng.mjs +33 -0
  687. package/dist/url-pattern-BHS0V5Ng.mjs.map +1 -0
  688. package/dist/{user-BAumEmpA.mjs → user-sHgJ62SP.mjs} +3 -3
  689. package/dist/{user-BAumEmpA.mjs.map → user-sHgJ62SP.mjs.map} +1 -1
  690. package/dist/{utils-BbUgmeZG.mjs → utils-D4vD_Y98.mjs} +3 -3
  691. package/dist/{utils-BbUgmeZG.mjs.map → utils-D4vD_Y98.mjs.map} +1 -1
  692. package/dist/{validate-Bs_wT2ul.mjs → validate-BkqIG_Uj.mjs} +24 -5
  693. package/dist/validate-BkqIG_Uj.mjs.map +1 -0
  694. package/dist/{validate-VPnKoIzW.mjs → validate-BpwoDOgt.mjs} +25 -2
  695. package/dist/validate-BpwoDOgt.mjs.map +1 -0
  696. package/dist/{validate-CdYcY-Ln.d.mts → validate-DeGtBN84.d.mts} +25 -7
  697. package/dist/validate-DeGtBN84.d.mts.map +1 -0
  698. package/dist/{validation-BngR0nit.mjs → validation-CiJb_X5o.mjs} +14 -13
  699. package/dist/{validation-BngR0nit.mjs.map → validation-CiJb_X5o.mjs.map} +1 -1
  700. package/dist/version-x0NjTScG.mjs +7 -0
  701. package/dist/{version-Bdfb34kk.mjs.map → version-x0NjTScG.mjs.map} +1 -1
  702. package/dist/{widgets-L-VndTKD.mjs → widgets-Cwzvww0W.mjs} +3 -3
  703. package/dist/{widgets-L-VndTKD.mjs.map → widgets-Cwzvww0W.mjs.map} +1 -1
  704. package/dist/{wxr-taxonomies-DueaLFd9.d.mts → wxr-taxonomies-CmC0ZsDr.d.mts} +1 -1
  705. package/dist/{wxr-taxonomies-DueaLFd9.d.mts.map → wxr-taxonomies-CmC0ZsDr.d.mts.map} +1 -1
  706. package/dist/{wxr-taxonomies-BexjtNid.mjs → wxr-taxonomies-QZjWxjyk.mjs} +13 -32
  707. package/dist/{wxr-taxonomies-BexjtNid.mjs.map → wxr-taxonomies-QZjWxjyk.mjs.map} +1 -1
  708. package/dist/{zod-generator-DMzfga3g.mjs → zod-generator-D11MhxG4.mjs} +53 -6
  709. package/dist/zod-generator-D11MhxG4.mjs.map +1 -0
  710. package/package.json +18 -7
  711. package/src/after.ts +6 -1
  712. package/src/api/errors.ts +13 -0
  713. package/src/api/handlers/content.ts +172 -33
  714. package/src/api/handlers/dashboard.ts +12 -2
  715. package/src/api/handlers/index.ts +16 -0
  716. package/src/api/handlers/manifest.ts +2 -0
  717. package/src/api/handlers/marketplace.ts +14 -0
  718. package/src/api/handlers/media-allowlist.ts +13 -2
  719. package/src/api/handlers/media-usage-work.ts +188 -0
  720. package/src/api/handlers/media-usage.ts +5 -3
  721. package/src/api/handlers/registry.ts +14 -0
  722. package/src/api/handlers/revision.ts +19 -5
  723. package/src/api/handlers/schema.ts +46 -3
  724. package/src/api/handlers/seo.ts +5 -2
  725. package/src/api/handlers/snapshot.ts +1 -1
  726. package/src/api/handlers/taxonomies.ts +446 -83
  727. package/src/api/media-usage-write-fence.ts +64 -0
  728. package/src/api/openapi/document.ts +247 -0
  729. package/src/api/public-url.ts +14 -2
  730. package/src/api/schemas/common.ts +3 -1
  731. package/src/api/schemas/content.ts +122 -1
  732. package/src/api/schemas/media-usage.ts +133 -0
  733. package/src/api/schemas/schema.ts +91 -3
  734. package/src/api/schemas/search.ts +2 -0
  735. package/src/api/schemas/taxonomies.ts +58 -8
  736. package/src/api/site-url.ts +16 -6
  737. package/src/api/types.ts +1 -0
  738. package/src/astro/integration/index.ts +55 -42
  739. package/src/astro/integration/routes.ts +48 -4
  740. package/src/astro/integration/runtime.ts +28 -0
  741. package/src/astro/integration/virtual-modules.ts +27 -1
  742. package/src/astro/integration/vite-config.ts +16 -1
  743. package/src/astro/middleware/media-usage-write-fence.ts +30 -0
  744. package/src/astro/middleware/redirect.ts +14 -12
  745. package/src/astro/middleware/scoped-db.ts +35 -4
  746. package/src/astro/middleware.ts +131 -30
  747. package/src/astro/routes/api/admin/comments/[id]/status.ts +1 -1
  748. package/src/astro/routes/api/admin/media-usage/collection-deletions/index.ts +22 -0
  749. package/src/astro/routes/api/admin/media-usage/collection-deletions/retry.ts +22 -0
  750. package/src/astro/routes/api/admin/media-usage/work/index.ts +26 -0
  751. package/src/astro/routes/api/admin/media-usage/work/retry.ts +26 -0
  752. package/src/astro/routes/api/admin/plugins/[id]/disable.ts +4 -0
  753. package/src/astro/routes/api/admin/plugins/[id]/enable.ts +4 -0
  754. package/src/astro/routes/api/admin/plugins/[id]/uninstall.ts +4 -0
  755. package/src/astro/routes/api/admin/plugins/[id]/update.ts +4 -0
  756. package/src/astro/routes/api/admin/plugins/marketplace/[id]/install.ts +4 -0
  757. package/src/astro/routes/api/admin/plugins/registry/[id]/uninstall.ts +4 -0
  758. package/src/astro/routes/api/admin/plugins/registry/[id]/update.ts +4 -0
  759. package/src/astro/routes/api/admin/plugins/registry/install.ts +4 -0
  760. package/src/astro/routes/api/admin/users/[id]/send-recovery.ts +2 -2
  761. package/src/astro/routes/api/auth/invite/index.ts +2 -2
  762. package/src/astro/routes/api/auth/magic-link/send.ts +2 -2
  763. package/src/astro/routes/api/auth/signup/request.ts +2 -2
  764. package/src/astro/routes/api/comments/[collection]/[contentId]/index.ts +1 -1
  765. package/src/astro/routes/api/content/[collection]/[id]/terms/[taxonomy].ts +67 -31
  766. package/src/astro/routes/api/import/wordpress/execute.ts +3 -10
  767. package/src/astro/routes/api/mcp.ts +1 -0
  768. package/src/astro/routes/api/plugins/[pluginId]/[...path].ts +7 -1
  769. package/src/astro/routes/api/schema/collections/[slug]/index.ts +1 -7
  770. package/src/astro/routes/api/schema/collections/reorder.ts +31 -0
  771. package/src/astro/routes/api/schema/index.ts +2 -0
  772. package/src/astro/routes/api/search/enable.ts +5 -1
  773. package/src/astro/routes/api/search/rebuild.ts +6 -1
  774. package/src/astro/routes/api/taxonomies/[name]/reorder.ts +41 -0
  775. package/src/astro/routes/api/taxonomies/[name]/terms/index.ts +1 -0
  776. package/src/astro/routes/api/taxonomies/[name]/translations.ts +48 -0
  777. package/src/astro/routes/api/taxonomies/[name].ts +102 -0
  778. package/src/astro/types.ts +31 -4
  779. package/src/cleanup.ts +25 -26
  780. package/src/cli/commands/dev.ts +13 -3
  781. package/src/cli/commands/doctor.ts +193 -6
  782. package/src/cli/commands/export-seed.ts +6 -1
  783. package/src/cli/index.ts +1 -1
  784. package/src/client/index.ts +119 -0
  785. package/src/components/Block.astro +12 -0
  786. package/src/components/CommentForm.astro +1 -1
  787. package/src/components/Comments.astro +1 -1
  788. package/src/components/InlinePortableTextEditor.tsx +260 -32
  789. package/src/components/OrderedList.astro +14 -0
  790. package/src/components/PortableText.astro +26 -4
  791. package/src/components/index.ts +12 -1
  792. package/src/components/ordered-list.ts +549 -0
  793. package/src/content/converters/mark-safety.ts +120 -0
  794. package/src/content/converters/numbered-list.ts +148 -0
  795. package/src/content/converters/portable-text-to-prosemirror.ts +84 -25
  796. package/src/content/converters/prosemirror-to-portable-text.ts +35 -14
  797. package/src/content/converters/types.ts +2 -0
  798. package/src/content/portable-text-lists.ts +205 -0
  799. package/src/content-list-query.ts +29 -0
  800. package/src/database/dialect-helpers.ts +3 -22
  801. package/src/database/migrations/055_content_translation_group_locale_index.ts +67 -0
  802. package/src/database/migrations/056_taxonomy_term_sort_order.ts +189 -0
  803. package/src/database/migrations/057_collection_hidden.ts +24 -0
  804. package/src/database/migrations/058_collection_sort_order.ts +20 -0
  805. package/src/database/migrations/059_revision_prune_queue.ts +36 -0
  806. package/src/database/migrations/060_collection_admin_config.ts +16 -0
  807. package/src/database/migrations/061_media_usage_cleanup.ts +77 -0
  808. package/src/database/migrations/062_media_usage_cleanup_fence.ts +295 -0
  809. package/src/database/migrations/063_media_usage_incremental_work.ts +397 -0
  810. package/src/database/migrations/064_fts_plain_text.ts +253 -0
  811. package/src/database/migrations/065_media_usage_collection_deletion.ts +85 -0
  812. package/src/database/migrations/066_media_usage_reconciliation.ts +115 -0
  813. package/src/database/migrations/067_indexed_content_fields.ts +39 -0
  814. package/src/database/migrations/068_content_taxonomy_entry_groups.ts +61 -0
  815. package/src/database/migrations/069_collection_title_date_fields.ts +45 -0
  816. package/src/database/migrations/070_collection_routable.ts +18 -0
  817. package/src/database/migrations/runner.ts +32 -0
  818. package/src/database/repositories/content.ts +1051 -273
  819. package/src/database/repositories/media-usage-work.ts +848 -0
  820. package/src/database/repositories/media-usage.ts +1502 -138
  821. package/src/database/repositories/revision.ts +98 -22
  822. package/src/database/repositories/taxonomy.ts +429 -103
  823. package/src/database/repositories/types.ts +58 -2
  824. package/src/database/types.ts +147 -17
  825. package/src/database/validate.ts +39 -0
  826. package/src/db/adapters.ts +36 -0
  827. package/src/db/index.ts +3 -0
  828. package/src/deferred-tasks.ts +71 -0
  829. package/src/emdash-runtime.ts +493 -110
  830. package/src/fields/file.ts +7 -4
  831. package/src/fields/image.ts +8 -1
  832. package/src/fields/types.ts +18 -5
  833. package/src/i18n/config.ts +32 -0
  834. package/src/i18n/repair-locale-casing.ts +0 -14
  835. package/src/i18n/taxonomy-locale-diagnostic.ts +47 -0
  836. package/src/import/wxr-taxonomies.ts +7 -47
  837. package/src/index.ts +27 -2
  838. package/src/loader.ts +165 -89
  839. package/src/mcp/server.ts +242 -34
  840. package/src/media/usage/activation.ts +626 -0
  841. package/src/media/usage/capture-triggers.ts +543 -0
  842. package/src/media/usage/cleanup.ts +305 -0
  843. package/src/media/usage/collection-deletion-processor.ts +356 -0
  844. package/src/media/usage/collection-deletion.ts +836 -0
  845. package/src/media/usage/content-fields.ts +40 -3
  846. package/src/media/usage/content-refresh.ts +356 -47
  847. package/src/media/usage/content-repair.ts +180 -61
  848. package/src/media/usage/content-snapshots.ts +85 -105
  849. package/src/media/usage/gc.ts +50 -0
  850. package/src/media/usage/projection-fingerprint.ts +129 -0
  851. package/src/media/usage/reconciliation-processor.ts +372 -0
  852. package/src/media/usage/reconciliation.ts +1117 -0
  853. package/src/media/usage/source-key.ts +4 -0
  854. package/src/media/usage/types.ts +2 -0
  855. package/src/media/usage/work-processor.ts +248 -0
  856. package/src/menus/index.ts +246 -141
  857. package/src/object-cache/index.ts +160 -3
  858. package/src/plugin-types.ts +8 -0
  859. package/src/plugins/adapt-sandbox-entry.ts +24 -5
  860. package/src/plugins/context.ts +24 -7
  861. package/src/plugins/index.ts +9 -0
  862. package/src/plugins/routes.ts +77 -1
  863. package/src/plugins/sandbox/index.ts +10 -1
  864. package/src/plugins/sandbox/types.ts +78 -1
  865. package/src/plugins/scheduler/node.ts +13 -1
  866. package/src/plugins/scheduler/types.ts +2 -0
  867. package/src/plugins/storage-indexes.ts +50 -11
  868. package/src/plugins/types.ts +39 -2
  869. package/src/query.ts +50 -79
  870. package/src/redirects/cache.ts +79 -19
  871. package/src/request-context.ts +3 -0
  872. package/src/scheduled-publish.ts +6 -1
  873. package/src/scheduler-health.ts +46 -0
  874. package/src/schema/registry.ts +863 -249
  875. package/src/schema/types.ts +74 -8
  876. package/src/schema/url-pattern.ts +33 -0
  877. package/src/schema/zod-generator.ts +77 -5
  878. package/src/search/fts-manager.ts +167 -86
  879. package/src/search/index.ts +2 -0
  880. package/src/search/query.ts +32 -11
  881. package/src/search/types.ts +8 -0
  882. package/src/seed/apply.ts +89 -16
  883. package/src/seed/types.ts +21 -3
  884. package/src/seed/validate.ts +52 -2
  885. package/src/taxonomies/index.ts +88 -82
  886. package/src/taxonomies/term-counts.ts +23 -12
  887. package/src/ui-comments.ts +19 -0
  888. package/src/ui.ts +11 -3
  889. package/src/utils/slugify.ts +1 -29
  890. package/src/virtual-modules.d.ts +24 -0
  891. package/dist/adapters-C0ONzkUP.d.mts.map +0 -1
  892. package/dist/after-B1IIdH3Y.mjs +0 -29
  893. package/dist/after-B1IIdH3Y.mjs.map +0 -1
  894. package/dist/api-DgPbMlng.mjs.map +0 -1
  895. package/dist/apply-1_6ra7NP.mjs.map +0 -1
  896. package/dist/cache-B26cufFd.mjs +0 -65
  897. package/dist/cache-B26cufFd.mjs.map +0 -1
  898. package/dist/config-DyF3OKg_.mjs.map +0 -1
  899. package/dist/content-CpfKV9QE.mjs.map +0 -1
  900. package/dist/content-refresh-DgqUBeTv.mjs +0 -1629
  901. package/dist/content-refresh-DgqUBeTv.mjs.map +0 -1
  902. package/dist/context-kO4YZB03.mjs.map +0 -1
  903. package/dist/dashboard-DoBwPnON.mjs.map +0 -1
  904. package/dist/dialect-helpers-DFwyWjTM.mjs.map +0 -1
  905. package/dist/errors-DtEXIQQV.mjs.map +0 -1
  906. package/dist/fts-manager-vncsZIJm.mjs.map +0 -1
  907. package/dist/index-BeNto_Vs.d.mts.map +0 -1
  908. package/dist/index-j9rTh3cp.d.mts.map +0 -1
  909. package/dist/loader-C1XOLV5b.mjs.map +0 -1
  910. package/dist/media-DWIzoVFL.mjs.map +0 -1
  911. package/dist/media-allowlist-B7TPD6aq.mjs.map +0 -1
  912. package/dist/media-usage-DPJcNaAq.mjs.map +0 -1
  913. package/dist/menus-C6qhqP4X.mjs.map +0 -1
  914. package/dist/object-cache-Bok5j2ae.mjs.map +0 -1
  915. package/dist/options-aeIs8WFu.d.mts.map +0 -1
  916. package/dist/public-url-DSGTnJFw.mjs.map +0 -1
  917. package/dist/query-DCiXI7OZ.mjs.map +0 -1
  918. package/dist/redirects-BOn2DIUs.mjs.map +0 -1
  919. package/dist/registry-BP1JK2xh.mjs +0 -795
  920. package/dist/registry-BP1JK2xh.mjs.map +0 -1
  921. package/dist/relations-DHFQGX0h.d.mts.map +0 -1
  922. package/dist/runner-BsI18UgP.mjs.map +0 -1
  923. package/dist/search-CeO678cp.mjs.map +0 -1
  924. package/dist/seo-C3GDfT0V.mjs.map +0 -1
  925. package/dist/site-url-8N3kSyVZ.mjs +0 -13
  926. package/dist/site-url-8N3kSyVZ.mjs.map +0 -1
  927. package/dist/slugify-C_tqlU4G.mjs +0 -30
  928. package/dist/slugify-C_tqlU4G.mjs.map +0 -1
  929. package/dist/taxonomies-B61CRSha.mjs.map +0 -1
  930. package/dist/taxonomies-Dbdki3Un.mjs.map +0 -1
  931. package/dist/taxonomy-DvwWAPvA.mjs +0 -304
  932. package/dist/taxonomy-DvwWAPvA.mjs.map +0 -1
  933. package/dist/types-84Bque3-.d.mts.map +0 -1
  934. package/dist/types-BQY7VYw6.d.mts.map +0 -1
  935. package/dist/types-DqZVPILm.d.mts.map +0 -1
  936. package/dist/types-XrQQ-Aex.mjs.map +0 -1
  937. package/dist/types-jISEalTX.d.mts.map +0 -1
  938. package/dist/types-o7xo7VgH.mjs.map +0 -1
  939. package/dist/validate-Bs_wT2ul.mjs.map +0 -1
  940. package/dist/validate-CdYcY-Ln.d.mts.map +0 -1
  941. package/dist/validate-VPnKoIzW.mjs.map +0 -1
  942. package/dist/version-Bdfb34kk.mjs +0 -7
  943. package/dist/zod-generator-DMzfga3g.mjs.map +0 -1
  944. /package/dist/{api-tokens-CEsW_jCg.mjs → api-tokens-CyTsLszZ.mjs} +0 -0
  945. /package/dist/{ssrf-BB__xfNM.mjs → ssrf-DpXgKsna.mjs} +0 -0
  946. /package/dist/{types-CK0LxPUQ.mjs → types-CP1CflWf.mjs} +0 -0
@@ -1,10 +1,11 @@
1
- import { o as __exportAll } from "./runner-BsI18UgP.mjs";
2
- import { t as validateIdentifier } from "./validate-VPnKoIzW.mjs";
3
- import { o as invalidateCollectionCache } from "./object-cache-Bok5j2ae.mjs";
4
- import { n as chunks, t as SQL_BATCH_SIZE } from "./chunks-D5dlPeRb.mjs";
5
- import { n as isMissingTableError } from "./db-errors-CcWLaRiR.mjs";
6
- import { n as slugify } from "./slugify-C_tqlU4G.mjs";
7
- import { a as encodeCursor, i as decodeCursor, r as ScheduledNotDueError, t as EmDashValidationError } from "./types-XrQQ-Aex.mjs";
1
+ import { o as __exportAll } from "./runner-BiDvq5dv.mjs";
2
+ import { t as validateIdentifier } from "./validate-BpwoDOgt.mjs";
3
+ import { c as invalidateCollectionCache } from "./object-cache-71tPfV4A.mjs";
4
+ import { c as isIndexableFieldType } from "./types-75KIqzL9.mjs";
5
+ import { n as chunks, t as SQL_BATCH_SIZE } from "./chunks-DfPax1I0.mjs";
6
+ import { n as isMissingTableError } from "./db-errors-Cl-sKYTm.mjs";
7
+ import { n as slugify } from "./slugify-B994zkXC.mjs";
8
+ import { a as ScheduledNotDueError, i as InvalidCursorError, n as ContentMutationConflictError, o as decodeCursor, r as EmDashValidationError, s as encodeCursor, t as ContentCollectionNotFoundError } from "./types-CQPWhPxE.mjs";
8
9
  import { sql } from "kysely";
9
10
  import { monotonicFactory, ulid } from "ulidx";
10
11
 
@@ -76,6 +77,15 @@ var RevisionRepository = class {
76
77
  await this.db.insertInto("revisions").values(row).execute();
77
78
  const revision = await this.findById(id);
78
79
  if (!revision) throw new Error("Failed to create revision");
80
+ try {
81
+ await this.db.insertInto("_emdash_revision_prune_queue").values({
82
+ collection: input.collection,
83
+ entry_id: input.entryId,
84
+ revision_id: id
85
+ }).onConflict((conflict) => conflict.columns(["collection", "entry_id"]).doUpdateSet({ revision_id: id })).execute();
86
+ } catch (error) {
87
+ console.error(`[revisions] Failed to queue revision pruning for ${input.collection}/${input.entryId}:`, error);
88
+ }
79
89
  return revision;
80
90
  }
81
91
  /**
@@ -115,23 +125,56 @@ var RevisionRepository = class {
115
125
  */
116
126
  async deleteByEntry(collection, entryId) {
117
127
  const result = await this.db.deleteFrom("revisions").where("collection", "=", collection).where("entry_id", "=", entryId).executeTakeFirst();
128
+ try {
129
+ await this.db.deleteFrom("_emdash_revision_prune_queue").where("collection", "=", collection).where("entry_id", "=", entryId).execute();
130
+ } catch (error) {
131
+ console.error(`[revisions] Failed to clear queued revision pruning for ${collection}/${entryId}:`, error);
132
+ }
118
133
  return Number(result.numDeletedRows ?? 0);
119
134
  }
120
135
  /**
121
136
  * Delete old revisions, keeping the most recent N
122
137
  */
123
- async pruneOldRevisions(collection, entryId, keepCount) {
124
- const keepIds = (await this.db.selectFrom("revisions").select("id").where("collection", "=", collection).where("entry_id", "=", entryId).orderBy("created_at", "desc").orderBy("id", "desc").limit(keepCount).execute()).map((r) => r.id);
138
+ async pruneOldRevisions(collection, entryId, keepCount, throughRevisionId) {
139
+ validateIdentifier(collection, "collection");
140
+ const tableName = `ec_${collection}`;
141
+ let keepQuery = this.db.selectFrom("revisions").select("id").where("collection", "=", collection).where("entry_id", "=", entryId).orderBy("created_at", "desc").orderBy("id", "desc").limit(keepCount);
142
+ if (throughRevisionId) keepQuery = keepQuery.where("id", "<=", throughRevisionId);
143
+ const keepIds = (await keepQuery.execute()).map((r) => r.id);
125
144
  if (keepIds.length === 0) return 0;
126
- const result = await this.db.deleteFrom("revisions").where("collection", "=", collection).where("entry_id", "=", entryId).where("id", "not in", keepIds).executeTakeFirst();
127
- return Number(result.numDeletedRows ?? 0);
145
+ const result = await sql`
146
+ DELETE FROM revisions
147
+ WHERE collection = ${collection}
148
+ AND entry_id = ${entryId}
149
+ ${throughRevisionId ? sql`AND id <= ${throughRevisionId}` : sql``}
150
+ AND id NOT IN (${sql.join(keepIds.map((id) => sql`${id}`))})
151
+ AND NOT EXISTS (
152
+ SELECT 1 FROM ${sql.ref(tableName)} AS content
153
+ WHERE content.live_revision_id = revisions.id
154
+ OR content.draft_revision_id = revisions.id
155
+ )
156
+ `.execute(this.db);
157
+ return Number(result.numAffectedRows ?? 0);
128
158
  }
129
- /**
130
- * Update revision data in place
131
- * Used for autosave to avoid creating many small revisions.
132
- */
133
- async updateData(id, data) {
134
- await this.db.updateTable("revisions").set({ data: JSON.stringify(data) }).where("id", "=", id).execute();
159
+ async pruneQueuedEntry(collection, entryId, queuedRevisionId, keepCount) {
160
+ const pruned = await this.pruneOldRevisions(collection, entryId, keepCount, queuedRevisionId);
161
+ await this.db.deleteFrom("_emdash_revision_prune_queue").where("collection", "=", collection).where("entry_id", "=", entryId).where("revision_id", "=", queuedRevisionId).execute();
162
+ return pruned;
163
+ }
164
+ async deleteIfUnreferenced(collection, entryId, revisionId) {
165
+ validateIdentifier(collection, "collection");
166
+ const tableName = `ec_${collection}`;
167
+ return ((await sql`
168
+ DELETE FROM revisions
169
+ WHERE id = ${revisionId}
170
+ AND collection = ${collection}
171
+ AND entry_id = ${entryId}
172
+ AND NOT EXISTS (
173
+ SELECT 1 FROM ${sql.ref(tableName)} AS content
174
+ WHERE content.live_revision_id = revisions.id
175
+ OR content.draft_revision_id = revisions.id
176
+ )
177
+ `.execute(this.db)).numAffectedRows ?? 0n) > 0n;
135
178
  }
136
179
  /**
137
180
  * Convert database row to Revision object
@@ -150,9 +193,65 @@ var RevisionRepository = class {
150
193
 
151
194
  //#endregion
152
195
  //#region src/database/repositories/content.ts
153
- var content_exports = /* @__PURE__ */ __exportAll({ ContentRepository: () => ContentRepository });
196
+ var content_exports = /* @__PURE__ */ __exportAll({
197
+ ContentRepository: () => ContentRepository,
198
+ isSystemOrderField: () => isSystemOrderField
199
+ });
154
200
  const ULID_PATTERN = /^[0-9A-Z]{26}$/;
201
+ const SQLSTATE_PATTERN = /^[0-9A-Z]{5}$/;
202
+ const MAX_DRAFT_STAGE_ATTEMPTS = 32;
155
203
  const LIKE_WILDCARD_RE = /[\\%_]/g;
204
+ const MAX_INDEXED_FIELD_FILTERS = 20;
205
+ const MAX_IN_FILTER_VALUES = SQL_BATCH_SIZE;
206
+ const MAX_FILTER_STRING_LENGTH = 2048;
207
+ function nullableColumnMatch(column, value) {
208
+ validateIdentifier(column, "content column");
209
+ return value === null ? sql`${sql.ref(column)} IS NULL` : sql`${sql.ref(column)} = ${value}`;
210
+ }
211
+ function sameStoredValue(left, right) {
212
+ return Object.is(serializeValue(left), serializeValue(right));
213
+ }
214
+ function matchesPublication(observed, existing, revision, revisionId, slug, publishedAt, updatedAt) {
215
+ if (observed.version !== existing.version + 1 || observed.status !== "published" || observed.slug !== slug || observed.liveRevisionId !== revisionId || observed.draftRevisionId !== null || observed.scheduledAt !== null || observed.publishedAt !== publishedAt || observed.updatedAt !== updatedAt) return false;
216
+ return Object.entries(revision.data).every(([key, value]) => SYSTEM_COLUMNS.has(key) || key.startsWith("_") || sameStoredValue(observed.data[key], value));
217
+ }
218
+ function matchesLifecyclePublication(observed, existing, liveRevisionId, publishedAt, updatedAt) {
219
+ if (observed.version !== existing.version + 1 || observed.status !== "published" || observed.slug !== existing.slug || observed.liveRevisionId !== liveRevisionId || observed.draftRevisionId !== null || observed.scheduledAt !== null || observed.publishedAt !== publishedAt || observed.updatedAt !== updatedAt) return false;
220
+ return Object.entries(existing.data).every(([key, value]) => sameStoredValue(observed.data[key], value));
221
+ }
222
+ function matchesPublicationFence(observed, existing) {
223
+ return observed.version === existing.version && observed.status === existing.status && observed.liveRevisionId === existing.liveRevisionId && observed.draftRevisionId === existing.draftRevisionId && observed.scheduledAt === existing.scheduledAt;
224
+ }
225
+ function isConfirmedStatementFailure(error) {
226
+ if (typeof error !== "object" || error === null || !("code" in error)) return false;
227
+ const code = error.code;
228
+ return typeof code === "string" && (code.startsWith("SQLITE_") || SQLSTATE_PATTERN.test(code));
229
+ }
230
+ function encodeIndexedFieldCursor(field, value, id) {
231
+ const payload = {
232
+ version: 1,
233
+ field,
234
+ value
235
+ };
236
+ return encodeCursor(JSON.stringify(payload), id);
237
+ }
238
+ function decodeIndexedFieldCursor(cursor, field) {
239
+ const { orderValue, id } = decodeCursor(cursor);
240
+ let payload;
241
+ try {
242
+ payload = JSON.parse(orderValue);
243
+ } catch {
244
+ throw new InvalidCursorError(cursor);
245
+ }
246
+ if (payload === null || typeof payload !== "object") throw new InvalidCursorError(cursor);
247
+ const candidate = payload;
248
+ const validValue = candidate.value === null || typeof candidate.value === "string" || typeof candidate.value === "number";
249
+ if (candidate.version !== 1 || candidate.field !== field || !validValue) throw new InvalidCursorError(cursor);
250
+ return {
251
+ value: candidate.value,
252
+ id
253
+ };
254
+ }
156
255
  /**
157
256
  * Whitelist mapping a public date-filter field to its physical column. Keeping
158
257
  * this separate from `mapOrderField` makes the filterable set explicit and
@@ -164,6 +263,27 @@ const DATE_FILTER_COLUMNS = {
164
263
  publishedAt: "published_at"
165
264
  };
166
265
  /**
266
+ * Built-in sort fields → their physical columns. A closed set that blocks
267
+ * sorting by arbitrary columns; per-collection fields are allowed
268
+ * separately via `mapOrderField`'s `sortableExtras`.
269
+ */
270
+ const ORDER_FIELD_COLUMNS = {
271
+ createdAt: "created_at",
272
+ updatedAt: "updated_at",
273
+ publishedAt: "published_at",
274
+ scheduledAt: "scheduled_at",
275
+ deletedAt: "deleted_at",
276
+ title: "title",
277
+ name: "name",
278
+ slug: "slug",
279
+ status: "status",
280
+ locale: "locale"
281
+ };
282
+ /** True when `field` maps to a system column and needs no per-collection resolution. */
283
+ function isSystemOrderField(field) {
284
+ return field in ORDER_FIELD_COLUMNS;
285
+ }
286
+ /**
167
287
  * System columns that exist in every ec_* table
168
288
  */
169
289
  const SYSTEM_COLUMNS = new Set([
@@ -201,6 +321,15 @@ function serializeValue(value) {
201
321
  if (typeof value === "object") return JSON.stringify(value);
202
322
  return value;
203
323
  }
324
+ function writableContentData(data) {
325
+ const writable = {};
326
+ for (const [key, value] of Object.entries(data)) {
327
+ if (SYSTEM_COLUMNS.has(key)) continue;
328
+ validateIdentifier(key, "content field name");
329
+ writable[key] = value;
330
+ }
331
+ return writable;
332
+ }
204
333
  /**
205
334
  * Deserialize a value from database storage
206
335
  * Attempts to parse JSON strings that look like objects/arrays
@@ -237,7 +366,7 @@ var ContentRepository = class {
237
366
  * Create a new content item
238
367
  */
239
368
  async create(input) {
240
- const id = ulid();
369
+ const id = input.id ?? ulid();
241
370
  const now = (/* @__PURE__ */ new Date()).toISOString();
242
371
  const { type, slug, data, status = "draft", authorId, primaryBylineId, locale, translationOf, publishedAt, createdAt } = input;
243
372
  if (!type) throw new EmDashValidationError("Content type is required");
@@ -299,7 +428,7 @@ var ContentRepository = class {
299
428
  * (optionally scoped to a locale) and appends a numeric suffix (`-1`,
300
429
  * `-2`, etc.) on collision to guarantee uniqueness.
301
430
  *
302
- * Returns `null` if `baseSlug` is empty after slugification.
431
+ * Returns null when slug normalization cannot produce a value.
303
432
  */
304
433
  async generateUniqueSlug(type, text, locale) {
305
434
  const baseSlug = slugify(text);
@@ -462,7 +591,9 @@ var ContentRepository = class {
462
591
  const limit = Math.min(options.limit || 50, 100);
463
592
  const orderField = options.orderBy?.field || "createdAt";
464
593
  const orderDirection = options.orderBy?.direction || "desc";
465
- const dbField = this.mapOrderField(orderField);
594
+ const resolvedOrderField = await this.resolveOrderField(type, orderField, options.sortableExtras);
595
+ const dbField = resolvedOrderField.column;
596
+ const resolvedFieldFilters = await this.resolveFieldFilters(type, options.where?.fieldFilters);
466
597
  const safeOrderDirection = orderDirection.toLowerCase() === "asc" ? "ASC" : "DESC";
467
598
  let query = this.db.selectFrom(tableName).selectAll().where("deleted_at", "is", null);
468
599
  if (options.where?.status) query = query.where("status", "=", options.where.status);
@@ -470,13 +601,42 @@ var ContentRepository = class {
470
601
  if (options.where?.locale) query = query.where("locale", "=", options.where.locale);
471
602
  query = this.applySearchFilter(query, options.where, type);
472
603
  query = this.applyDateFilter(query, options.where);
473
- if (options.cursor) {
604
+ query = this.applyBylineFilter(query, options.where, type);
605
+ query = this.applyFieldFilters(query, resolvedFieldFilters);
606
+ if (options.cursor) if (resolvedOrderField.indexedCustomField) {
607
+ const { value, id: cursorId } = decodeIndexedFieldCursor(options.cursor, orderField);
608
+ const isPresent = sql`${sql.ref(dbField)} IS NOT NULL`;
609
+ const falseLiteral = sql`FALSE`;
610
+ const trueLiteral = sql`TRUE`;
611
+ if (safeOrderDirection === "ASC" && value === null) query = query.where(sql`
612
+ (${isPresent}) > ${falseLiteral}
613
+ OR ((${isPresent}) = ${falseLiteral} AND ${sql.ref("id")} > ${cursorId})
614
+ `);
615
+ else if (safeOrderDirection === "DESC" && value === null) query = query.where(sql`
616
+ (${isPresent}) = ${falseLiteral} AND ${sql.ref("id")} < ${cursorId}
617
+ `);
618
+ else if (safeOrderDirection === "ASC") query = query.where(sql`
619
+ (${isPresent}, ${sql.ref(dbField)}, ${sql.ref("id")})
620
+ > (${trueLiteral}, ${value}, ${cursorId})
621
+ `);
622
+ else query = query.where(sql`
623
+ (${isPresent}, ${sql.ref(dbField)}, ${sql.ref("id")})
624
+ < (${trueLiteral}, ${value}, ${cursorId})
625
+ `);
626
+ } else {
474
627
  const { orderValue, id: cursorId } = decodeCursor(options.cursor);
475
628
  if (safeOrderDirection === "DESC") query = query.where((eb) => eb.or([eb(dbField, "<", orderValue), eb.and([eb(dbField, "=", orderValue), eb("id", "<", cursorId)])]));
476
629
  else query = query.where((eb) => eb.or([eb(dbField, ">", orderValue), eb.and([eb(dbField, "=", orderValue), eb("id", ">", cursorId)])]));
477
630
  }
478
- query = query.orderBy(dbField, safeOrderDirection === "ASC" ? "asc" : "desc").orderBy("id", safeOrderDirection === "ASC" ? "asc" : "desc").limit(limit + 1);
479
- const [rows, total] = await Promise.all([query.execute(), this.count(type, options.where)]);
631
+ const indexedOrderFilter = resolvedOrderField.indexedCustomField ? resolvedFieldFilters.find((filter) => filter.column === dbField) : void 0;
632
+ if (resolvedOrderField.indexedCustomField && !indexedOrderFilter) query = query.orderBy(sql`${sql.ref(dbField)} IS NOT NULL`, safeOrderDirection === "ASC" ? "asc" : "desc");
633
+ if (indexedOrderFilter?.kind !== "null") query = query.orderBy(dbField, safeOrderDirection === "ASC" ? "asc" : "desc");
634
+ query = query.orderBy("id", safeOrderDirection === "ASC" ? "asc" : "desc").limit(limit + 1);
635
+ const [rowsResult, countResult] = await Promise.allSettled([query.execute(), this.countWithResolvedFilters(type, options.where, resolvedFieldFilters)]);
636
+ if (rowsResult.status === "rejected") throw rowsResult.reason;
637
+ if (countResult.status === "rejected") throw countResult.reason;
638
+ const rows = rowsResult.value;
639
+ const total = countResult.value;
480
640
  const hasMore = rows.length > limit;
481
641
  const items = rows.slice(0, limit);
482
642
  const mappedResult = {
@@ -486,7 +646,10 @@ var ContentRepository = class {
486
646
  if (hasMore && items.length > 0) {
487
647
  const lastRow = items.at(-1);
488
648
  const lastOrderValue = lastRow[dbField];
489
- mappedResult.nextCursor = encodeCursor(typeof lastOrderValue === "string" || typeof lastOrderValue === "number" ? String(lastOrderValue) : "", String(lastRow.id));
649
+ if (resolvedOrderField.indexedCustomField) {
650
+ if (lastOrderValue !== null && typeof lastOrderValue !== "string" && typeof lastOrderValue !== "number") throw new EmDashValidationError(`Invalid indexed value for order field: ${orderField}`);
651
+ mappedResult.nextCursor = encodeIndexedFieldCursor(orderField, lastOrderValue, String(lastRow.id));
652
+ } else mappedResult.nextCursor = encodeCursor(typeof lastOrderValue === "string" || typeof lastOrderValue === "number" ? String(lastOrderValue) : "", String(lastRow.id));
490
653
  }
491
654
  return mappedResult;
492
655
  }
@@ -503,23 +666,137 @@ var ContentRepository = class {
503
666
  if (input.scheduledAt !== void 0) updates.scheduled_at = input.scheduledAt;
504
667
  if (input.authorId !== void 0) updates.author_id = input.authorId;
505
668
  if (input.primaryBylineId !== void 0) updates.primary_byline_id = input.primaryBylineId;
506
- if (input.data !== void 0 && typeof input.data === "object") {
507
- for (const [key, value] of Object.entries(input.data)) if (!SYSTEM_COLUMNS.has(key)) {
508
- validateIdentifier(key, "content field name");
509
- updates[key] = serializeValue(value);
510
- }
511
- }
669
+ if (input.data !== void 0 && typeof input.data === "object") for (const [key, value] of Object.entries(writableContentData(input.data))) updates[key] = serializeValue(value);
512
670
  const hasColumnWrites = Object.keys(updates).length > 0;
513
671
  if (hasColumnWrites) updates.updated_at = now;
514
672
  updates.version = sql`version + 1`;
515
673
  await this.db.updateTable(tableName).set(updates).where("id", "=", id).where("deleted_at", "is", null).execute();
516
- if (input.status !== void 0 || input.publishedAt !== void 0 || input.scheduledAt !== void 0) await this.restampEntryPivot(type, id);
517
674
  if (hasColumnWrites) invalidateCollectionCache(type);
518
675
  const updated = await this.findById(type, id);
519
676
  if (!updated) throw new Error("Content not found");
520
677
  return updated;
521
678
  }
522
679
  /**
680
+ * Update plugin-authored fields without letting content columns diverge
681
+ * from the revision pointers that publication promotes.
682
+ */
683
+ async updateDraftAware(type, id, input) {
684
+ const data = input.data ? writableContentData(input.data) : {};
685
+ const stagedSlug = typeof input.slug === "string" ? input.slug : void 0;
686
+ if (!(Object.keys(data).length > 0 || stagedSlug !== void 0)) return this.update(type, id, {
687
+ ...input,
688
+ data
689
+ });
690
+ const collectionRows = await this.db.selectFrom("_emdash_collections as collection").leftJoin("_emdash_fields as field", "field.collection_id", "collection.id").select(["collection.supports", "field.slug as fieldSlug"]).where("collection.slug", "=", type).execute();
691
+ const supportsRaw = collectionRows[0]?.supports;
692
+ const supports = supportsRaw ? JSON.parse(supportsRaw) : [];
693
+ if (!Array.isArray(supports) || !supports.includes("revisions")) return this.update(type, id, {
694
+ ...input,
695
+ data
696
+ });
697
+ const fieldSlugs = new Set(collectionRows.map((row) => row.fieldSlug).filter(Boolean));
698
+ for (const field of Object.keys(data)) if (!fieldSlugs.has(field)) throw new EmDashValidationError(`Unknown field '${field}' in collection '${type}'`);
699
+ const revisionRepo = new RevisionRepository(this.db);
700
+ let existing = await this.findById(type, id);
701
+ for (let attempt = 0; existing && attempt < MAX_DRAFT_STAGE_ATTEMPTS; attempt++) {
702
+ let baseData = existing.data;
703
+ if (existing.draftRevisionId) {
704
+ const draft = await revisionRepo.findById(existing.draftRevisionId);
705
+ if (draft) baseData = draft.data;
706
+ }
707
+ const mergedData = {
708
+ ...baseData,
709
+ ...data
710
+ };
711
+ if (stagedSlug !== void 0) mergedData._slug = stagedSlug;
712
+ const revision = await revisionRepo.create({
713
+ collection: type,
714
+ entryId: id,
715
+ data: mergedData,
716
+ ...input.authorId ? { authorId: input.authorId } : {}
717
+ });
718
+ let staged;
719
+ try {
720
+ staged = await this.replaceDraftRevisionForUpdate(type, id, revision.id, existing, input);
721
+ } catch (error) {
722
+ await this.deleteUnstagedRevision(revisionRepo, type, id, revision.id);
723
+ throw error;
724
+ }
725
+ if (staged) {
726
+ const updated = await this.findById(type, id);
727
+ if (!updated) throw new Error("Content not found");
728
+ const draftData = {};
729
+ for (const [key, value] of Object.entries(mergedData)) if (!key.startsWith("_")) draftData[key] = value;
730
+ return {
731
+ ...updated,
732
+ data: {
733
+ ...updated.data,
734
+ ...draftData
735
+ }
736
+ };
737
+ }
738
+ await this.deleteUnstagedRevision(revisionRepo, type, id, revision.id);
739
+ existing = await this.findById(type, id);
740
+ }
741
+ if (!existing) throw new Error("Content not found");
742
+ throw new ContentMutationConflictError();
743
+ }
744
+ async deleteUnstagedRevision(revisionRepo, type, id, revisionId) {
745
+ try {
746
+ await revisionRepo.deleteIfUnreferenced(type, id, revisionId);
747
+ } catch (error) {
748
+ console.error(`[content] Failed to clean up unstaged revision ${revisionId}:`, error);
749
+ }
750
+ }
751
+ async replaceDraftRevisionForUpdate(type, id, revisionId, expected, input) {
752
+ const tableName = getTableName(type);
753
+ const assignments = [sql`draft_revision_id = ${revisionId}`];
754
+ let liveMetadataChanged = false;
755
+ if (input.status !== void 0) {
756
+ assignments.push(sql`status = ${input.status}`);
757
+ liveMetadataChanged = true;
758
+ }
759
+ if (input.slug === null) {
760
+ assignments.push(sql`slug = NULL`);
761
+ liveMetadataChanged = true;
762
+ }
763
+ if (input.publishedAt !== void 0) {
764
+ assignments.push(sql`published_at = ${input.publishedAt}`);
765
+ liveMetadataChanged = true;
766
+ }
767
+ if (input.scheduledAt !== void 0) {
768
+ assignments.push(sql`scheduled_at = ${input.scheduledAt}`);
769
+ liveMetadataChanged = true;
770
+ }
771
+ if (input.authorId !== void 0) {
772
+ assignments.push(sql`author_id = ${input.authorId}`);
773
+ liveMetadataChanged = true;
774
+ }
775
+ if (input.primaryBylineId !== void 0) {
776
+ assignments.push(sql`primary_byline_id = ${input.primaryBylineId}`);
777
+ liveMetadataChanged = true;
778
+ }
779
+ if (liveMetadataChanged) assignments.push(sql`updated_at = ${(/* @__PURE__ */ new Date()).toISOString()}`);
780
+ assignments.push(sql`version = version + 1`);
781
+ const changed = ((await sql`
782
+ UPDATE ${sql.ref(tableName)}
783
+ SET ${sql.join(assignments, sql`, `)}
784
+ WHERE id = ${id}
785
+ AND deleted_at IS NULL
786
+ AND version = ${expected.version}
787
+ AND ${nullableColumnMatch("live_revision_id", expected.liveRevisionId)}
788
+ AND ${nullableColumnMatch("draft_revision_id", expected.draftRevisionId)}
789
+ AND EXISTS (
790
+ SELECT 1 FROM revisions
791
+ WHERE revisions.id = ${revisionId}
792
+ AND revisions.collection = ${type}
793
+ AND revisions.entry_id = ${id}
794
+ )
795
+ `.execute(this.db)).numAffectedRows ?? 0n) > 0n;
796
+ if (changed && liveMetadataChanged) invalidateCollectionCache(type);
797
+ return changed;
798
+ }
799
+ /**
523
800
  * Delete content (soft delete - moves to trash)
524
801
  */
525
802
  async delete(type, id) {
@@ -531,10 +808,7 @@ var ContentRepository = class {
531
808
  WHERE id = ${id}
532
809
  AND deleted_at IS NULL
533
810
  `.execute(this.db)).numAffectedRows ?? 0n) > 0n;
534
- if (changed) {
535
- await this.restampEntryPivot(type, id);
536
- invalidateCollectionCache(type);
537
- }
811
+ if (changed) invalidateCollectionCache(type);
538
812
  return changed;
539
813
  }
540
814
  /**
@@ -550,35 +824,10 @@ var ContentRepository = class {
550
824
  RETURNING *
551
825
  `.execute(this.db)).rows[0];
552
826
  if (!restored) return null;
553
- await this.restampEntryPivot(type, id);
554
827
  invalidateCollectionCache(type);
555
828
  return this.mapRow(type, restored);
556
829
  }
557
830
  /**
558
- * Re-stamp the denormalized filter + sort columns on every
559
- * `content_taxonomies` pivot row for an entry from its authoritative `ec_*`
560
- * row (migration 051). Called after any mutation that moves one of those
561
- * columns so a taxonomy-filtered listing can seek the entry directly.
562
- *
563
- * A single correlated `UPDATE` reads the post-mutation values from `ec_*`, so
564
- * the pivot converges to the authoritative row. This is NOT atomic with the
565
- * `ec_*` mutation on D1 (no transactions), which is why the read path
566
- * re-checks the real predicates on the joined `ec_*` row. Untagged entries
567
- * have no pivot rows, so the statement is a cheap no-op for them.
568
- */
569
- async restampEntryPivot(type, id) {
570
- const tableName = getTableName(type);
571
- await sql`
572
- UPDATE content_taxonomies
573
- SET (status, scheduled_at, deleted_at, locale, published_at, created_at) = (
574
- SELECT status, scheduled_at, deleted_at, locale, published_at, created_at
575
- FROM ${sql.ref(tableName)}
576
- WHERE ${sql.ref(tableName)}.id = ${id}
577
- )
578
- WHERE collection = ${type} AND entry_id = ${id}
579
- `.execute(this.db);
580
- }
581
- /**
582
831
  * Permanently delete content (cannot be undone)
583
832
  */
584
833
  /**
@@ -675,7 +924,7 @@ var ContentRepository = class {
675
924
  const pattern = `%${term.replace(LIKE_WILDCARD_RE, (c) => `\\${c}`)}%`;
676
925
  return query.where((eb) => eb.or(columns.map((col) => {
677
926
  validateIdentifier(col, "search column");
678
- return eb(sql`lower(${sql.ref(col)})`, "like", sql`lower(${pattern}) escape '\\'`);
927
+ return sql`lower(CAST(${sql.ref(col)} AS TEXT)) LIKE lower(${pattern}) ESCAPE '\\'`;
679
928
  })));
680
929
  }
681
930
  /**
@@ -697,9 +946,57 @@ var ContentRepository = class {
697
946
  return next;
698
947
  }
699
948
  /**
949
+ * Apply the optional byline filter as a correlated (NOT) EXISTS against
950
+ * `_emdash_content_bylines`.
951
+ *
952
+ * Correlating from the content table preserves the outer sort index so
953
+ * `LIMIT` can short-circuit. `mode: "none"` tests the junction rather than
954
+ * `primary_byline_id` because the two are written in the same call but
955
+ * are not atomically consistent, so the junction is authoritative.
956
+ *
957
+ * Whether a credit *renders* is locale-scoped; whether one *exists* is
958
+ * not. Both are needed: the first decides what the filter matches, the
959
+ * second decides whether the author fallback applies at all.
960
+ */
961
+ applyBylineFilter(query, where, type) {
962
+ const filter = where?.bylineFilter;
963
+ if (!filter) return query;
964
+ const tableName = getTableName(type);
965
+ const idColumn = `${tableName}.id`;
966
+ const authorColumn = `${tableName}.author_id`;
967
+ const localeColumn = `${tableName}.locale`;
968
+ const creditRenders = (eb, bylineIds) => {
969
+ let sub = eb.selectFrom("_emdash_content_bylines as cb").innerJoin("_emdash_bylines as b", "b.translation_group", "cb.byline_id").select("cb.id").where("cb.collection_slug", "=", type).whereRef("cb.content_id", "=", idColumn);
970
+ sub = filter.locale ? sub.where("b.locale", "=", filter.locale) : sub.whereRef("b.locale", "=", localeColumn);
971
+ if (bylineIds) sub = sub.where("cb.byline_id", "in", bylineIds);
972
+ return eb.exists(sub);
973
+ };
974
+ const hasExplicitCredit = (eb) => eb.exists(eb.selectFrom("_emdash_content_bylines as cb").select("cb.id").where("cb.collection_slug", "=", type).whereRef("cb.content_id", "=", idColumn));
975
+ const authorHasByline = (eb, bylineIds) => {
976
+ let sub = eb.selectFrom("_emdash_bylines as b").select("b.id").whereRef("b.user_id", "=", authorColumn);
977
+ sub = filter.locale ? sub.where("b.locale", "=", filter.locale) : sub.whereRef("b.locale", "=", localeColumn);
978
+ if (bylineIds) sub = sub.where("b.translation_group", "in", bylineIds);
979
+ return eb.exists(sub);
980
+ };
981
+ if (filter.mode === "none") return query.where((eb) => {
982
+ const uncredited = eb.not(creditRenders(eb));
983
+ return filter.includeInferred ? eb.and([uncredited, eb.or([hasExplicitCredit(eb), eb.not(authorHasByline(eb))])]) : uncredited;
984
+ });
985
+ const bylineIds = filter.bylineIds ?? [];
986
+ if (bylineIds.length === 0) return query.where(() => sql`1 = 0`);
987
+ return query.where((eb) => {
988
+ if (!filter.includeInferred) return creditRenders(eb, bylineIds);
989
+ return eb.or([creditRenders(eb, bylineIds), eb.and([eb.not(hasExplicitCredit(eb)), authorHasByline(eb, bylineIds)])]);
990
+ });
991
+ }
992
+ /**
700
993
  * Count content items
701
994
  */
702
995
  async count(type, where) {
996
+ const resolvedFieldFilters = await this.resolveFieldFilters(type, where?.fieldFilters);
997
+ return this.countWithResolvedFilters(type, where, resolvedFieldFilters);
998
+ }
999
+ async countWithResolvedFilters(type, where, resolvedFieldFilters) {
703
1000
  const tableName = getTableName(type);
704
1001
  let query = this.db.selectFrom(tableName).select((eb) => eb.fn.count("id").as("count")).where("deleted_at", "is", null);
705
1002
  if (where?.status) query = query.where("status", "=", where.status);
@@ -707,6 +1004,8 @@ var ContentRepository = class {
707
1004
  if (where?.locale) query = query.where("locale", "=", where.locale);
708
1005
  query = this.applySearchFilter(query, where, type);
709
1006
  query = this.applyDateFilter(query, where);
1007
+ query = this.applyBylineFilter(query, where, type);
1008
+ query = this.applyFieldFilters(query, resolvedFieldFilters);
710
1009
  const result = await query.executeTakeFirst();
711
1010
  return Number(result?.count || 0);
712
1011
  }
@@ -720,19 +1019,22 @@ var ContentRepository = class {
720
1019
  const tableName = getTableName(type);
721
1020
  return (await this.db.selectFrom(tableName).select("author_id").distinct().where("deleted_at", "is", null).where("author_id", "is not", null).execute()).map((row) => row.author_id).filter((id) => id !== null);
722
1021
  }
723
- async getStats(type) {
1022
+ async getStats(type, now = /* @__PURE__ */ new Date()) {
724
1023
  const tableName = getTableName(type);
1024
+ const nowIso = now.toISOString();
725
1025
  const result = await this.db.selectFrom(tableName).select((eb) => [
726
1026
  eb.fn.count("id").as("total"),
727
1027
  eb.fn.sum(eb.case().when("status", "=", "published").then(1).else(0).end()).as("published"),
728
1028
  eb.fn.sum(eb.case().when("status", "=", "draft").then(1).else(0).end()).as("draft"),
729
- sql`SUM(CASE WHEN scheduled_at IS NOT NULL THEN 1 ELSE 0 END)`.as("scheduled")
1029
+ sql`SUM(CASE WHEN scheduled_at IS NOT NULL THEN 1 ELSE 0 END)`.as("scheduled"),
1030
+ sql`SUM(CASE WHEN scheduled_at IS NOT NULL AND scheduled_at <= ${nowIso} THEN 1 ELSE 0 END)`.as("overdue_scheduled")
730
1031
  ]).where("deleted_at", "is", null).executeTakeFirst();
731
1032
  return {
732
1033
  total: Number(result?.total || 0),
733
1034
  published: Number(result?.published || 0),
734
1035
  draft: Number(result?.draft || 0),
735
- scheduled: Number(result?.scheduled || 0)
1036
+ scheduled: Number(result?.scheduled || 0),
1037
+ overdueScheduled: Number(result?.overdue_scheduled || 0)
736
1038
  };
737
1039
  }
738
1040
  /**
@@ -758,7 +1060,6 @@ var ContentRepository = class {
758
1060
  WHERE id = ${id}
759
1061
  AND deleted_at IS NULL
760
1062
  `.execute(this.db);
761
- await this.restampEntryPivot(type, id);
762
1063
  invalidateCollectionCache(type);
763
1064
  const updated = await this.findById(type, id);
764
1065
  if (!updated) throw new Error("Content not found");
@@ -785,7 +1086,6 @@ var ContentRepository = class {
785
1086
  AND scheduled_at IS NOT NULL
786
1087
  AND deleted_at IS NULL
787
1088
  `.execute(this.db);
788
- await this.restampEntryPivot(type, id);
789
1089
  invalidateCollectionCache(type);
790
1090
  const updated = await this.findById(type, id);
791
1091
  if (!updated) throw new Error("Content not found");
@@ -835,6 +1135,10 @@ var ContentRepository = class {
835
1135
  * Lets callers resolve many edge groups without an N+1 per group. The caller
836
1136
  * groups the flat result by `translationGroup` itself.
837
1137
  *
1138
+ * `translation_group` leads the sort so the ordering follows
1139
+ * `idx_{table}_del_tg_locale` past its `deleted_at` equality; callers group by
1140
+ * `translationGroup`, so the per-group locale order they rely on is preserved.
1141
+ *
838
1142
  * `publishedOnly` restricts the result to `status = 'published'` — reference
839
1143
  * reads pass this for callers without `content:read_drafts` so draft/scheduled
840
1144
  * entries never leak through an edge traversal.
@@ -856,7 +1160,7 @@ var ContentRepository = class {
856
1160
  WHERE translation_group IN (${sql.join(chunk)})
857
1161
  AND deleted_at IS NULL
858
1162
  ${publishedFilter}
859
- ORDER BY locale ASC
1163
+ ORDER BY translation_group ASC, locale ASC
860
1164
  `.execute(this.db);
861
1165
  for (const row of result.rows) items.push(this.mapRow(type, row));
862
1166
  }
@@ -925,6 +1229,8 @@ var ContentRepository = class {
925
1229
  * Syncs the draft revision's data into the content table columns so the
926
1230
  * content table always reflects the published version.
927
1231
  * If no draft revision exists, creates one from current data and publishes it.
1232
+ * When `promoteRevision` is false, publishes the current content-table data
1233
+ * by changing lifecycle metadata only.
928
1234
  *
929
1235
  * `publishedAt` (optional) overrides the publication timestamp. If omitted,
930
1236
  * the existing `published_at` is preserved (idempotent re-publish keeps the
@@ -932,98 +1238,155 @@ var ContentRepository = class {
932
1238
  * an explicit value to backdate a publish (e.g. when migrating content from
933
1239
  * another CMS).
934
1240
  *
935
- * `requireDue` (optional) gates the publish on the row still being due:
936
- * `scheduled_at` non-null and in the past. Used by the scheduled-publishing
937
- * sweep to avoid publishing content an editor unscheduled or rescheduled
938
- * between selection and publish. It claims the row with a single conditional
939
- * UPDATE (clearing `scheduled_at`) before any other write, so it is atomic
940
- * even on D1 (no multi-statement transactions) and serialises against
941
- * `unschedule()` and concurrent sweeps — no TOCTOU and no double publish.
1241
+ * `requireDue` gates the final update on the row still being due.
1242
+ * `expectedScheduledAt` additionally fences changes made after a sweep
1243
+ * selected the row but before publication preparation began.
942
1244
  */
943
- async publish(type, id, publishedAt, requireDue = false) {
1245
+ async publish(type, id, publishedAt, requireDue = false, expectedScheduledAt, promoteRevision = true, requireSlug = true) {
944
1246
  const tableName = getTableName(type);
945
1247
  const now = (/* @__PURE__ */ new Date()).toISOString();
946
1248
  const existing = await this.findById(type, id);
947
1249
  if (!existing) throw new EmDashValidationError("Content item not found");
948
- let claimedScheduledAt = null;
949
- let claimedUpdatedAt = null;
950
- if (requireDue) {
951
- if (((await sql`
952
- UPDATE ${sql.ref(tableName)}
953
- SET scheduled_at = NULL,
954
- updated_at = ${now}
955
- WHERE id = ${id}
956
- AND scheduled_at IS NOT NULL
957
- AND scheduled_at <= ${now}
958
- AND deleted_at IS NULL
959
- `.execute(this.db)).numAffectedRows ?? 0n) === 0n) throw new ScheduledNotDueError();
960
- claimedScheduledAt = existing.scheduledAt;
961
- claimedUpdatedAt = existing.updatedAt;
962
- }
963
- let publishCommitted = false;
964
- try {
1250
+ if (requireDue && expectedScheduledAt !== void 0 && existing.scheduledAt !== expectedScheduledAt) throw new ScheduledNotDueError();
1251
+ if (!promoteRevision && requireSlug && !existing.slug?.trim()) throw new EmDashValidationError("Cannot publish routable content without a slug");
1252
+ if (!promoteRevision) {
965
1253
  const revisionRepo = new RevisionRepository(this.db);
966
- let revisionToPublish = existing.draftRevisionId || existing.liveRevisionId;
967
- if (!revisionToPublish) revisionToPublish = (await revisionRepo.create({
968
- collection: type,
969
- entryId: id,
970
- data: existing.data
971
- })).id;
972
- const revision = await revisionRepo.findById(revisionToPublish);
973
- if (revision) {
974
- const stagedSlug = typeof revision.data._slug === "string" ? revision.data._slug : null;
975
- if (stagedSlug !== null && stagedSlug !== existing.slug && existing.locale !== null) {
976
- const conflict = await this.findBySlugIncludingTrashed(type, stagedSlug, existing.locale);
977
- if (conflict && conflict.id !== id) throw new EmDashValidationError(`Cannot publish: slug '${stagedSlug}' is already used by another entry in this collection (id: ${conflict.id}). Choose a different slug.`, { code: "SLUG_CONFLICT" });
1254
+ let provisionalRevisionId = null;
1255
+ try {
1256
+ let liveRevisionId = existing.liveRevisionId;
1257
+ if (!liveRevisionId) {
1258
+ const revision = await revisionRepo.create({
1259
+ collection: type,
1260
+ entryId: id,
1261
+ data: existing.data
1262
+ });
1263
+ liveRevisionId = revision.id;
1264
+ provisionalRevisionId = revision.id;
978
1265
  }
979
- if (stagedSlug !== null) await sql`
1266
+ const intendedPublishedAt = publishedAt ?? existing.publishedAt ?? now;
1267
+ const duePredicate = requireDue ? sql`AND scheduled_at IS NOT NULL AND scheduled_at <= ${now}` : sql``;
1268
+ let published = false;
1269
+ try {
1270
+ published = ((await sql`
980
1271
  UPDATE ${sql.ref(tableName)}
981
- SET slug = ${stagedSlug}
1272
+ SET live_revision_id = ${liveRevisionId},
1273
+ draft_revision_id = NULL,
1274
+ status = 'published',
1275
+ scheduled_at = NULL,
1276
+ published_at = ${intendedPublishedAt},
1277
+ updated_at = ${now},
1278
+ version = version + 1
982
1279
  WHERE id = ${id}
983
- `.execute(this.db);
984
- await this.syncDataColumns(type, id, revision.data);
1280
+ AND deleted_at IS NULL
1281
+ AND version = ${existing.version}
1282
+ AND status = ${existing.status}
1283
+ AND ${nullableColumnMatch("live_revision_id", existing.liveRevisionId)}
1284
+ AND ${nullableColumnMatch("draft_revision_id", existing.draftRevisionId)}
1285
+ AND ${nullableColumnMatch("scheduled_at", existing.scheduledAt)}
1286
+ ${duePredicate}
1287
+ `.execute(this.db)).numAffectedRows ?? 0n) > 0n;
1288
+ } catch (error) {
1289
+ if (isConfirmedStatementFailure(error)) throw error;
1290
+ let observed;
1291
+ try {
1292
+ observed = await this.findById(type, id);
1293
+ } catch (reconciliationError) {
1294
+ throw new Error("Unable to confirm whether content publication completed", { cause: reconciliationError });
1295
+ }
1296
+ if (!observed) throw new Error("Unable to confirm whether content publication completed", { cause: error });
1297
+ published = matchesLifecyclePublication(observed, existing, liveRevisionId, intendedPublishedAt, now);
1298
+ if (!published && matchesPublicationFence(observed, existing)) throw error;
1299
+ if (!published) throw new Error("Unable to confirm whether content publication completed", { cause: error });
1300
+ }
1301
+ if (!published) throw requireDue ? new ScheduledNotDueError() : new ContentMutationConflictError();
1302
+ invalidateCollectionCache(type);
1303
+ const updated = await this.findById(type, id);
1304
+ if (!updated) throw new Error("Content not found");
1305
+ return updated;
1306
+ } catch (error) {
1307
+ if (provisionalRevisionId) try {
1308
+ await revisionRepo.deleteIfUnreferenced(type, id, provisionalRevisionId);
1309
+ } catch (cleanupError) {
1310
+ console.error(`[content] Failed to clean up provisional revision ${provisionalRevisionId}:`, cleanupError);
1311
+ }
1312
+ throw error;
985
1313
  }
986
- if (publishedAt !== void 0) await sql`
987
- UPDATE ${sql.ref(tableName)}
988
- SET live_revision_id = ${revisionToPublish},
989
- draft_revision_id = NULL,
990
- status = 'published',
991
- scheduled_at = NULL,
992
- published_at = ${publishedAt},
993
- updated_at = ${now}
994
- WHERE id = ${id}
995
- AND deleted_at IS NULL
996
- `.execute(this.db);
997
- else await sql`
1314
+ }
1315
+ const revisionRepo = new RevisionRepository(this.db);
1316
+ let provisionalRevisionId = null;
1317
+ try {
1318
+ let revisionToPublish = existing.draftRevisionId || existing.liveRevisionId;
1319
+ if (!revisionToPublish) {
1320
+ const revision = await revisionRepo.create({
1321
+ collection: type,
1322
+ entryId: id,
1323
+ data: existing.data
1324
+ });
1325
+ revisionToPublish = revision.id;
1326
+ provisionalRevisionId = revision.id;
1327
+ }
1328
+ const revision = await revisionRepo.findById(revisionToPublish);
1329
+ if (!revision || revision.collection !== type || revision.entryId !== id) throw new EmDashValidationError("Revision does not belong to the specified content item");
1330
+ const stagedSlug = typeof revision.data._slug === "string" ? revision.data._slug : null;
1331
+ const intendedSlug = stagedSlug ?? existing.slug;
1332
+ if (requireSlug && !intendedSlug?.trim()) throw new EmDashValidationError("Cannot publish routable content without a slug");
1333
+ const intendedPublishedAt = publishedAt ?? existing.publishedAt ?? now;
1334
+ if (stagedSlug !== null && stagedSlug !== existing.slug && existing.locale !== null) {
1335
+ const conflict = await this.findBySlugIncludingTrashed(type, stagedSlug, existing.locale);
1336
+ if (conflict && conflict.id !== id) throw new EmDashValidationError(`Cannot publish: slug '${stagedSlug}' is already used by another entry in this collection (id: ${conflict.id}). Choose a different slug.`, { code: "SLUG_CONFLICT" });
1337
+ }
1338
+ const assignments = [];
1339
+ if (stagedSlug !== null) assignments.push(sql`slug = ${stagedSlug}`);
1340
+ for (const [key, value] of Object.entries(revision.data)) {
1341
+ if (SYSTEM_COLUMNS.has(key) || key.startsWith("_")) continue;
1342
+ validateIdentifier(key, "content field name");
1343
+ assignments.push(sql`${sql.ref(key)} = ${serializeValue(value)}`);
1344
+ }
1345
+ assignments.push(sql`live_revision_id = ${revisionToPublish}`, sql`draft_revision_id = NULL`, sql`status = 'published'`, sql`scheduled_at = NULL`, sql`published_at = ${intendedPublishedAt}`, sql`updated_at = ${now}`, sql`version = version + 1`);
1346
+ const duePredicate = requireDue ? sql`AND scheduled_at IS NOT NULL AND scheduled_at <= ${now}` : sql``;
1347
+ let promoted = false;
1348
+ try {
1349
+ promoted = ((await sql`
998
1350
  UPDATE ${sql.ref(tableName)}
999
- SET live_revision_id = ${revisionToPublish},
1000
- draft_revision_id = NULL,
1001
- status = 'published',
1002
- scheduled_at = NULL,
1003
- published_at = COALESCE(published_at, ${now}),
1004
- updated_at = ${now}
1351
+ SET ${sql.join(assignments, sql`, `)}
1005
1352
  WHERE id = ${id}
1006
1353
  AND deleted_at IS NULL
1007
- `.execute(this.db);
1008
- publishCommitted = true;
1009
- await this.restampEntryPivot(type, id);
1354
+ AND version = ${existing.version}
1355
+ AND status = ${existing.status}
1356
+ AND ${nullableColumnMatch("live_revision_id", existing.liveRevisionId)}
1357
+ AND ${nullableColumnMatch("draft_revision_id", existing.draftRevisionId)}
1358
+ AND ${nullableColumnMatch("scheduled_at", existing.scheduledAt)}
1359
+ ${duePredicate}
1360
+ AND EXISTS (
1361
+ SELECT 1 FROM revisions
1362
+ WHERE revisions.id = ${revisionToPublish}
1363
+ AND revisions.collection = ${type}
1364
+ AND revisions.entry_id = ${id}
1365
+ )
1366
+ `.execute(this.db)).numAffectedRows ?? 0n) > 0n;
1367
+ } catch (error) {
1368
+ if (isConfirmedStatementFailure(error)) throw error;
1369
+ let observed;
1370
+ try {
1371
+ observed = await this.findById(type, id);
1372
+ } catch (reconciliationError) {
1373
+ throw new Error("Unable to confirm whether content publication completed", { cause: reconciliationError });
1374
+ }
1375
+ if (!observed) throw new Error("Unable to confirm whether content publication completed", { cause: error });
1376
+ promoted = matchesPublication(observed, existing, revision, revisionToPublish, intendedSlug, intendedPublishedAt, now);
1377
+ if (!promoted && matchesPublicationFence(observed, existing)) throw error;
1378
+ if (!promoted) throw new Error("Unable to confirm whether content publication completed", { cause: error });
1379
+ }
1380
+ if (!promoted) throw requireDue ? new ScheduledNotDueError() : new ContentMutationConflictError();
1381
+ invalidateCollectionCache(type);
1010
1382
  const updated = await this.findById(type, id);
1011
1383
  if (!updated) throw new Error("Content not found");
1012
- invalidateCollectionCache(type);
1013
1384
  return updated;
1014
1385
  } catch (error) {
1015
- if (requireDue && claimedScheduledAt && !publishCommitted) try {
1016
- await sql`
1017
- UPDATE ${sql.ref(tableName)}
1018
- SET scheduled_at = ${claimedScheduledAt},
1019
- updated_at = ${claimedUpdatedAt ?? now}
1020
- WHERE id = ${id}
1021
- AND scheduled_at IS NULL
1022
- AND deleted_at IS NULL
1023
- AND (status != 'published' OR draft_revision_id IS NOT NULL)
1024
- `.execute(this.db);
1025
- } catch (restoreError) {
1026
- console.error(`[content] Failed to restore schedule for ${type}/${id} after publish failure:`, restoreError);
1386
+ if (provisionalRevisionId) try {
1387
+ await revisionRepo.deleteIfUnreferenced(type, id, provisionalRevisionId);
1388
+ } catch (cleanupError) {
1389
+ console.error(`[content] Failed to clean up provisional revision ${provisionalRevisionId}:`, cleanupError);
1027
1390
  }
1028
1391
  throw error;
1029
1392
  }
@@ -1064,7 +1427,6 @@ var ContentRepository = class {
1064
1427
  WHERE id = ${id}
1065
1428
  AND deleted_at IS NULL
1066
1429
  `.execute(this.db);
1067
- await this.restampEntryPivot(type, id);
1068
1430
  invalidateCollectionCache(type);
1069
1431
  const updated = await this.findById(type, id);
1070
1432
  if (!updated) throw new Error("Content not found");
@@ -1082,17 +1444,31 @@ var ContentRepository = class {
1082
1444
  * content row pointing at a missing or unrelated revision.
1083
1445
  */
1084
1446
  async setDraftRevision(type, id, revisionId) {
1085
- const tableName = getTableName(type);
1086
- if (!await this.findById(type, id)) throw new EmDashValidationError("Content item not found");
1447
+ const existing = await this.findById(type, id);
1448
+ if (!existing) throw new EmDashValidationError("Content item not found");
1087
1449
  const revision = await new RevisionRepository(this.db).findById(revisionId);
1088
1450
  if (!revision) throw new EmDashValidationError("Revision not found");
1089
1451
  if (revision.collection !== type || revision.entryId !== id) throw new EmDashValidationError("Revision does not belong to the specified content item");
1090
- await sql`
1452
+ if (!await this.replaceDraftRevision(type, id, revisionId, existing)) throw new ContentMutationConflictError();
1453
+ }
1454
+ async replaceDraftRevision(type, id, revisionId, expected) {
1455
+ const tableName = getTableName(type);
1456
+ return ((await sql`
1091
1457
  UPDATE ${sql.ref(tableName)}
1092
- SET draft_revision_id = ${revisionId}
1458
+ SET draft_revision_id = ${revisionId},
1459
+ version = version + 1
1093
1460
  WHERE id = ${id}
1094
1461
  AND deleted_at IS NULL
1095
- `.execute(this.db);
1462
+ AND version = ${expected.version}
1463
+ AND ${nullableColumnMatch("live_revision_id", expected.liveRevisionId)}
1464
+ AND ${nullableColumnMatch("draft_revision_id", expected.draftRevisionId)}
1465
+ AND EXISTS (
1466
+ SELECT 1 FROM revisions
1467
+ WHERE revisions.id = ${revisionId}
1468
+ AND revisions.collection = ${type}
1469
+ AND revisions.entry_id = ${id}
1470
+ )
1471
+ `.execute(this.db)).numAffectedRows ?? 0n) > 0n;
1096
1472
  }
1097
1473
  /**
1098
1474
  * Discard pending draft changes
@@ -1116,23 +1492,6 @@ var ContentRepository = class {
1116
1492
  return updated;
1117
1493
  }
1118
1494
  /**
1119
- * Sync data columns in the content table from a data object.
1120
- * Used to promote revision data into the content table on publish.
1121
- * Keys starting with _ are revision metadata (e.g. _slug) and are skipped.
1122
- */
1123
- async syncDataColumns(type, id, data) {
1124
- const tableName = getTableName(type);
1125
- const updates = {};
1126
- for (const [key, value] of Object.entries(data)) {
1127
- if (SYSTEM_COLUMNS.has(key)) continue;
1128
- if (key.startsWith("_")) continue;
1129
- validateIdentifier(key, "content field name");
1130
- updates[key] = serializeValue(value);
1131
- }
1132
- if (Object.keys(updates).length === 0) return;
1133
- await this.db.updateTable(tableName).set(updates).where("id", "=", id).execute();
1134
- }
1135
- /**
1136
1495
  * Count content items with a pending schedule.
1137
1496
  * Includes both draft-scheduled (status='scheduled') and published
1138
1497
  * posts with scheduled draft changes (status='published', scheduled_at set).
@@ -1173,28 +1532,153 @@ var ContentRepository = class {
1173
1532
  translationGroup: row.translation_group ?? null
1174
1533
  };
1175
1534
  }
1535
+ normalizeFilterScalar(field, type, value) {
1536
+ if (type === "number" || type === "integer") {
1537
+ if (typeof value !== "number" || !Number.isFinite(value)) throw new EmDashValidationError(`Filter for field "${field}" must use a finite number`);
1538
+ if (type === "integer" && !Number.isInteger(value)) throw new EmDashValidationError(`Filter for field "${field}" must use an integer`);
1539
+ return value;
1540
+ }
1541
+ if (type === "boolean") {
1542
+ if (typeof value !== "boolean") throw new EmDashValidationError(`Filter for field "${field}" must use a boolean`);
1543
+ return value ? 1 : 0;
1544
+ }
1545
+ if (typeof value !== "string") throw new EmDashValidationError(`Filter for field "${field}" must use a string`);
1546
+ if (value.length > MAX_FILTER_STRING_LENGTH) throw new EmDashValidationError(`Filter value for field "${field}" exceeds ${MAX_FILTER_STRING_LENGTH} characters`);
1547
+ return value;
1548
+ }
1549
+ normalizeFieldFilter(field, type, value) {
1550
+ if (value === null) return {
1551
+ column: field,
1552
+ kind: "null"
1553
+ };
1554
+ if (typeof value !== "object") return {
1555
+ column: field,
1556
+ kind: "exact",
1557
+ value: this.normalizeFilterScalar(field, type, value)
1558
+ };
1559
+ if (Array.isArray(value)) throw new EmDashValidationError(`Invalid filter for field "${field}"`);
1560
+ const record = value;
1561
+ const keys = Object.keys(record);
1562
+ if (keys.length === 1 && keys[0] === "in") {
1563
+ if (!Array.isArray(record.in) || record.in.length === 0) throw new EmDashValidationError(`IN filter for field "${field}" must not be empty`);
1564
+ if (record.in.length > MAX_IN_FILTER_VALUES) throw new EmDashValidationError(`IN filter for field "${field}" exceeds ${MAX_IN_FILTER_VALUES} values`);
1565
+ return {
1566
+ column: field,
1567
+ kind: "in",
1568
+ values: record.in.map((entry) => this.normalizeFilterScalar(field, type, entry))
1569
+ };
1570
+ }
1571
+ const rangeKeys = new Set([
1572
+ "gt",
1573
+ "gte",
1574
+ "lt",
1575
+ "lte"
1576
+ ]);
1577
+ if (keys.length === 0 || keys.some((key) => !rangeKeys.has(key))) throw new EmDashValidationError(`Invalid filter operator for field "${field}"`);
1578
+ if (type === "boolean") throw new EmDashValidationError(`Boolean field "${field}" does not support range filters`);
1579
+ const bounds = {};
1580
+ for (const key of keys) {
1581
+ if (record[key] === void 0) continue;
1582
+ bounds[key] = this.normalizeFilterScalar(field, type, record[key]);
1583
+ }
1584
+ if (Object.keys(bounds).length === 0) throw new EmDashValidationError(`Range filter for field "${field}" has no bounds`);
1585
+ return {
1586
+ column: field,
1587
+ kind: "range",
1588
+ bounds
1589
+ };
1590
+ }
1591
+ async collectionExists(type) {
1592
+ return await this.db.selectFrom("_emdash_collections").where("slug", "=", type).select("id").executeTakeFirst() !== void 0;
1593
+ }
1594
+ async resolveFieldFilters(type, filters) {
1595
+ const resolvedFilters = filters ?? {};
1596
+ const fields = Object.keys(resolvedFilters);
1597
+ if (fields.length === 0) return [];
1598
+ if (fields.length > MAX_INDEXED_FIELD_FILTERS) {
1599
+ if (!await this.collectionExists(type)) return [];
1600
+ throw new EmDashValidationError(`Content list queries support at most ${MAX_INDEXED_FIELD_FILTERS} indexed field filters`);
1601
+ }
1602
+ const rows = await this.db.selectFrom("_emdash_fields as field").innerJoin("_emdash_collections as collection", "collection.id", "field.collection_id").where("collection.slug", "=", type).where("field.slug", "in", fields).where("field.indexed", "=", 1).select(["field.slug", "field.type"]).execute();
1603
+ const metadata = new Map(rows.map((row) => [row.slug, row.type]));
1604
+ if (metadata.size === 0 && !await this.collectionExists(type)) return [];
1605
+ for (const field of fields) try {
1606
+ validateIdentifier(field, "content filter field");
1607
+ } catch {
1608
+ throw new EmDashValidationError(`Invalid content filter field: ${field}`);
1609
+ }
1610
+ const normalized = fields.map((field) => {
1611
+ const fieldType = metadata.get(field);
1612
+ if (!fieldType || !isIndexableFieldType(fieldType)) throw new EmDashValidationError(`Cannot filter by field "${field}". Custom fields must be indexed before filtering.`);
1613
+ return this.normalizeFieldFilter(field, fieldType, resolvedFilters[field]);
1614
+ });
1615
+ if (normalized.reduce((total, filter) => {
1616
+ if (filter.kind === "null") return total;
1617
+ if (filter.kind === "exact") return total + 1;
1618
+ if (filter.kind === "in") return total + filter.values.length;
1619
+ return total + Object.keys(filter.bounds).length;
1620
+ }, 0) > SQL_BATCH_SIZE) throw new EmDashValidationError(`Indexed field filters have a total operand budget of ${SQL_BATCH_SIZE}`);
1621
+ return normalized;
1622
+ }
1623
+ applyFieldFilters(query, filters) {
1624
+ let next = query;
1625
+ for (const filter of filters) {
1626
+ const column = sql.ref(filter.column);
1627
+ const isPresent = sql`${column} IS NOT NULL`;
1628
+ if (filter.kind === "null") {
1629
+ next = next.where(() => sql`(${isPresent}) = FALSE AND ${column} IS NULL`);
1630
+ continue;
1631
+ }
1632
+ if (filter.kind === "exact") {
1633
+ next = next.where(() => sql`(${isPresent}) = TRUE AND ${column} = ${filter.value}`);
1634
+ continue;
1635
+ }
1636
+ if (filter.kind === "in") {
1637
+ const values = sql.join(filter.values.map((value) => sql`${value}`), sql`, `);
1638
+ next = next.where(() => sql`(${isPresent}) = TRUE AND ${column} IN (${values})`);
1639
+ continue;
1640
+ }
1641
+ next = next.where(() => sql`(${isPresent}) = TRUE`);
1642
+ if (filter.bounds.gt !== void 0) next = next.where(() => sql`${column} > ${filter.bounds.gt}`);
1643
+ if (filter.bounds.gte !== void 0) next = next.where(() => sql`${column} >= ${filter.bounds.gte}`);
1644
+ if (filter.bounds.lt !== void 0) next = next.where(() => sql`${column} < ${filter.bounds.lt}`);
1645
+ if (filter.bounds.lte !== void 0) next = next.where(() => sql`${column} <= ${filter.bounds.lte}`);
1646
+ }
1647
+ return next;
1648
+ }
1176
1649
  /**
1177
1650
  * Map order field names to database columns.
1178
1651
  * Only allows known fields to prevent column enumeration via crafted orderBy values.
1179
1652
  */
1180
- mapOrderField(field) {
1181
- const mapped = {
1182
- createdAt: "created_at",
1183
- updatedAt: "updated_at",
1184
- publishedAt: "published_at",
1185
- scheduledAt: "scheduled_at",
1186
- deletedAt: "deleted_at",
1187
- title: "title",
1188
- name: "name",
1189
- slug: "slug",
1190
- status: "status",
1191
- locale: "locale"
1192
- }[field];
1193
- if (!mapped) throw new EmDashValidationError(`Invalid order field: ${field}`);
1194
- return mapped;
1653
+ mapOrderField(field, sortableExtras = []) {
1654
+ const mapped = ORDER_FIELD_COLUMNS[field];
1655
+ if (mapped) return mapped;
1656
+ if (sortableExtras.includes(field)) {
1657
+ validateIdentifier(field, "order field");
1658
+ return field;
1659
+ }
1660
+ throw new EmDashValidationError(`Invalid order field: ${field}`);
1661
+ }
1662
+ async resolveOrderField(type, field, sortableExtras = []) {
1663
+ try {
1664
+ return {
1665
+ column: this.mapOrderField(field, sortableExtras),
1666
+ indexedCustomField: false
1667
+ };
1668
+ } catch (error) {
1669
+ if (!(error instanceof EmDashValidationError)) throw error;
1670
+ }
1671
+ const customField = await this.db.selectFrom("_emdash_collections as collection").leftJoin("_emdash_fields as field", (join) => join.onRef("field.collection_id", "=", "collection.id").on("field.slug", "=", field).on("field.indexed", "=", 1)).where("collection.slug", "=", type).select(["collection.id as collectionId", "field.slug as fieldSlug"]).executeTakeFirst();
1672
+ if (!customField) throw new ContentCollectionNotFoundError(type);
1673
+ if (!customField.fieldSlug) throw new EmDashValidationError(`Invalid order field: ${field}. Custom fields must be indexed before sorting.`);
1674
+ validateIdentifier(customField.fieldSlug, "content order field");
1675
+ return {
1676
+ column: customField.fieldSlug,
1677
+ indexedCustomField: true
1678
+ };
1195
1679
  }
1196
1680
  };
1197
1681
 
1198
1682
  //#endregion
1199
- export { content_exports as n, RevisionRepository as r, ContentRepository as t };
1200
- //# sourceMappingURL=content-CpfKV9QE.mjs.map
1683
+ export { RevisionRepository as i, content_exports as n, isSystemOrderField as r, ContentRepository as t };
1684
+ //# sourceMappingURL=content-BNfwh7xX.mjs.map