emdash 0.25.1 → 0.26.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.
- package/dist/api/route-utils.d.mts +3 -3
- package/dist/api/route-utils.mjs +11 -11
- package/dist/{api-D2_sbavn.mjs → api-BMfveMoB.mjs} +15 -15
- package/dist/{api-D2_sbavn.mjs.map → api-BMfveMoB.mjs.map} +1 -1
- package/dist/{apply-Bk2mAuLn.mjs → apply--IVNSdXn.mjs} +18 -16
- package/dist/apply--IVNSdXn.mjs.map +1 -0
- package/dist/astro/index.d.mts +7 -7
- package/dist/astro/index.mjs +2 -1
- package/dist/astro/index.mjs.map +1 -1
- package/dist/astro/middleware/auth.d.mts +7 -7
- package/dist/astro/middleware/auth.mjs +2 -2
- package/dist/astro/middleware/redirect.mjs +4 -4
- package/dist/astro/middleware.d.mts +1 -1
- package/dist/astro/middleware.mjs +85 -85
- package/dist/astro/middleware.mjs.map +1 -1
- package/dist/astro/routes/api/admin/allowed-domains/_domain_.mjs +3 -3
- package/dist/astro/routes/api/admin/allowed-domains/index.mjs +3 -3
- package/dist/astro/routes/api/admin/api-tokens/_id_.mjs +2 -2
- package/dist/astro/routes/api/admin/api-tokens/index.mjs +3 -3
- package/dist/astro/routes/api/admin/byline-fields/_slug_/usage.mjs +3 -3
- package/dist/astro/routes/api/admin/byline-fields/_slug_.mjs +4 -4
- package/dist/astro/routes/api/admin/byline-fields/index.mjs +4 -4
- package/dist/astro/routes/api/admin/byline-fields/reorder.mjs +4 -4
- package/dist/astro/routes/api/admin/bylines/_id_/index.mjs +10 -10
- package/dist/astro/routes/api/admin/bylines/_id_/translations.mjs +10 -10
- package/dist/astro/routes/api/admin/bylines/index.mjs +10 -10
- package/dist/astro/routes/api/admin/comments/_id_/status.mjs +8 -8
- package/dist/astro/routes/api/admin/comments/_id_.mjs +6 -6
- package/dist/astro/routes/api/admin/comments/bulk.mjs +7 -7
- package/dist/astro/routes/api/admin/comments/counts.mjs +6 -6
- package/dist/astro/routes/api/admin/comments/index.mjs +7 -7
- package/dist/astro/routes/api/admin/hooks/exclusive/_hookName_.mjs +4 -4
- package/dist/astro/routes/api/admin/hooks/exclusive/index.mjs +3 -3
- package/dist/astro/routes/api/admin/oauth-clients/_id_.mjs +3 -3
- package/dist/astro/routes/api/admin/oauth-clients/index.mjs +3 -3
- package/dist/astro/routes/api/admin/plugins/_id_/disable.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/_id_/enable.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/_id_/index.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/_id_/uninstall.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/_id_/update.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/index.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/marketplace/_id_/icon.mjs +3 -3
- package/dist/astro/routes/api/admin/plugins/marketplace/_id_/index.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/marketplace/_id_/install.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/marketplace/index.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/registry/_id_/uninstall.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/registry/_id_/update.mjs +29 -29
- package/dist/astro/routes/api/admin/plugins/registry/artifact.mjs +28 -28
- package/dist/astro/routes/api/admin/plugins/registry/install.mjs +29 -29
- package/dist/astro/routes/api/admin/plugins/updates.mjs +28 -28
- package/dist/astro/routes/api/admin/themes/marketplace/_id_/index.mjs +28 -28
- package/dist/astro/routes/api/admin/themes/marketplace/_id_/thumbnail.mjs +3 -3
- package/dist/astro/routes/api/admin/themes/marketplace/index.mjs +28 -28
- package/dist/astro/routes/api/admin/users/_id_/disable.mjs +2 -2
- package/dist/astro/routes/api/admin/users/_id_/enable.mjs +2 -2
- package/dist/astro/routes/api/admin/users/_id_/index.mjs +3 -3
- package/dist/astro/routes/api/admin/users/_id_/send-recovery.mjs +2 -2
- package/dist/astro/routes/api/admin/users/index.mjs +3 -3
- package/dist/astro/routes/api/auth/dev-bypass.mjs +3 -3
- package/dist/astro/routes/api/auth/invite/accept.mjs +2 -2
- package/dist/astro/routes/api/auth/invite/complete.mjs +3 -3
- package/dist/astro/routes/api/auth/invite/index.mjs +3 -3
- package/dist/astro/routes/api/auth/invite/register-options.mjs +3 -3
- package/dist/astro/routes/api/auth/logout.mjs +2 -2
- package/dist/astro/routes/api/auth/magic-link/send.mjs +4 -4
- package/dist/astro/routes/api/auth/magic-link/verify.mjs +2 -2
- package/dist/astro/routes/api/auth/me.mjs +4 -4
- package/dist/astro/routes/api/auth/passkey/_id_.mjs +3 -3
- package/dist/astro/routes/api/auth/passkey/index.mjs +2 -2
- package/dist/astro/routes/api/auth/passkey/options.mjs +4 -4
- package/dist/astro/routes/api/auth/passkey/register/options.mjs +3 -3
- package/dist/astro/routes/api/auth/passkey/register/verify.mjs +3 -3
- package/dist/astro/routes/api/auth/passkey/verify.mjs +3 -3
- package/dist/astro/routes/api/auth/signup/complete.mjs +3 -3
- package/dist/astro/routes/api/auth/signup/request.mjs +4 -4
- package/dist/astro/routes/api/auth/signup/verify.mjs +2 -2
- package/dist/astro/routes/api/comments/_collection_/_contentId_/index.mjs +7 -7
- package/dist/astro/routes/api/comments/_collection_/_contentId_/reactions.mjs +7 -7
- package/dist/astro/routes/api/content/_collection_/_id_/compare.mjs +3 -3
- package/dist/astro/routes/api/content/_collection_/_id_/discard-draft.mjs +3 -3
- package/dist/astro/routes/api/content/_collection_/_id_/duplicate.mjs +3 -3
- package/dist/astro/routes/api/content/_collection_/_id_/permanent.mjs +3 -3
- package/dist/astro/routes/api/content/_collection_/_id_/preview-url.mjs +4 -4
- package/dist/astro/routes/api/content/_collection_/_id_/publish.mjs +4 -4
- package/dist/astro/routes/api/content/_collection_/_id_/restore.mjs +3 -3
- package/dist/astro/routes/api/content/_collection_/_id_/revisions.mjs +3 -3
- package/dist/astro/routes/api/content/_collection_/_id_/schedule.mjs +4 -4
- package/dist/astro/routes/api/content/_collection_/_id_/terms/_taxonomy_.mjs +9 -9
- package/dist/astro/routes/api/content/_collection_/_id_/translations.mjs +3 -3
- package/dist/astro/routes/api/content/_collection_/_id_/unpublish.mjs +3 -3
- package/dist/astro/routes/api/content/_collection_/_id_.mjs +4 -4
- package/dist/astro/routes/api/content/_collection_/authors.mjs +3 -3
- package/dist/astro/routes/api/content/_collection_/index.mjs +4 -4
- package/dist/astro/routes/api/content/_collection_/trash.mjs +4 -4
- package/dist/astro/routes/api/dashboard.mjs +8 -8
- package/dist/astro/routes/api/dev/emails.mjs +2 -2
- package/dist/astro/routes/api/import/probe.d.mts +2 -2
- package/dist/astro/routes/api/import/probe.mjs +4 -4
- package/dist/astro/routes/api/import/wordpress/analyze.mjs +3 -3
- package/dist/astro/routes/api/import/wordpress/execute.d.mts +7 -7
- package/dist/astro/routes/api/import/wordpress/execute.mjs +9 -9
- package/dist/astro/routes/api/import/wordpress/media.d.mts +7 -7
- package/dist/astro/routes/api/import/wordpress/media.mjs +4 -4
- package/dist/astro/routes/api/import/wordpress/prepare.mjs +6 -6
- package/dist/astro/routes/api/import/wordpress/rewrite-urls.mjs +5 -5
- package/dist/astro/routes/api/import/wordpress-plugin/analyze.mjs +4 -4
- package/dist/astro/routes/api/import/wordpress-plugin/execute.mjs +7 -7
- package/dist/astro/routes/api/manifest.mjs +3 -3
- package/dist/astro/routes/api/mcp.mjs +34 -34
- package/dist/astro/routes/api/media/_id_/confirm.mjs +4 -4
- package/dist/astro/routes/api/media/_id_.mjs +4 -4
- package/dist/astro/routes/api/media/file/_...key_.mjs +2 -2
- package/dist/astro/routes/api/media/providers/_providerId_/_itemId_.mjs +3 -3
- package/dist/astro/routes/api/media/providers/_providerId_/index.mjs +3 -3
- package/dist/astro/routes/api/media/providers/index.mjs +3 -3
- package/dist/astro/routes/api/media/upload-url.mjs +4 -4
- package/dist/astro/routes/api/media.mjs +5 -5
- package/dist/astro/routes/api/menus/_name_/items/_id_.mjs +6 -6
- package/dist/astro/routes/api/menus/_name_/items.mjs +6 -6
- package/dist/astro/routes/api/menus/_name_/reorder.mjs +6 -6
- package/dist/astro/routes/api/menus/_name_/translations.mjs +6 -6
- package/dist/astro/routes/api/menus/_name_.mjs +6 -6
- package/dist/astro/routes/api/menus/index.mjs +6 -6
- package/dist/astro/routes/api/oauth/device/authorize.mjs +3 -3
- package/dist/astro/routes/api/oauth/device/code.mjs +4 -4
- package/dist/astro/routes/api/oauth/device/token.mjs +4 -4
- package/dist/astro/routes/api/oauth/register.mjs +2 -2
- package/dist/astro/routes/api/oauth/token/refresh.mjs +3 -3
- package/dist/astro/routes/api/oauth/token/revoke.mjs +3 -3
- package/dist/astro/routes/api/oauth/token.mjs +2 -2
- package/dist/astro/routes/api/openapi.json.mjs +2 -2
- package/dist/astro/routes/api/plugins/_pluginId_/_...path_.mjs +3 -3
- package/dist/astro/routes/api/redirects/404s/index.mjs +6 -6
- package/dist/astro/routes/api/redirects/404s/summary.mjs +6 -6
- package/dist/astro/routes/api/redirects/_id_.mjs +7 -7
- package/dist/astro/routes/api/redirects/index.mjs +7 -7
- package/dist/astro/routes/api/revisions/_revisionId_/index.mjs +3 -3
- package/dist/astro/routes/api/revisions/_revisionId_/restore.mjs +3 -3
- package/dist/astro/routes/api/schema/collections/_slug_/fields/_fieldSlug_.mjs +28 -28
- package/dist/astro/routes/api/schema/collections/_slug_/fields/index.mjs +28 -28
- package/dist/astro/routes/api/schema/collections/_slug_/fields/reorder.mjs +28 -28
- package/dist/astro/routes/api/schema/collections/_slug_/index.mjs +28 -28
- package/dist/astro/routes/api/schema/collections/index.mjs +28 -28
- package/dist/astro/routes/api/schema/index.mjs +6 -6
- package/dist/astro/routes/api/schema/orphans/_slug_.mjs +28 -28
- package/dist/astro/routes/api/schema/orphans/index.mjs +28 -28
- package/dist/astro/routes/api/search/enable.mjs +7 -7
- package/dist/astro/routes/api/search/index.mjs +6 -6
- package/dist/astro/routes/api/search/rebuild.mjs +7 -7
- package/dist/astro/routes/api/search/stats.mjs +6 -6
- package/dist/astro/routes/api/search/suggest.mjs +6 -6
- package/dist/astro/routes/api/sections/_slug_.mjs +6 -6
- package/dist/astro/routes/api/sections/index.mjs +6 -6
- package/dist/astro/routes/api/settings/email.mjs +4 -4
- package/dist/astro/routes/api/settings.mjs +9 -9
- package/dist/astro/routes/api/setup/admin-verify.mjs +3 -3
- package/dist/astro/routes/api/setup/admin.mjs +3 -3
- package/dist/astro/routes/api/setup/dev-bypass.mjs +17 -17
- package/dist/astro/routes/api/setup/dev-reset.mjs +2 -2
- package/dist/astro/routes/api/setup/index.mjs +18 -18
- package/dist/astro/routes/api/setup/status.mjs +3 -3
- package/dist/astro/routes/api/snapshot.mjs +3 -3
- package/dist/astro/routes/api/taxonomies/_name_/terms/_slug_/translations.mjs +9 -9
- package/dist/astro/routes/api/taxonomies/_name_/terms/_slug_.mjs +9 -9
- package/dist/astro/routes/api/taxonomies/_name_/terms/index.mjs +9 -9
- package/dist/astro/routes/api/taxonomies/index.mjs +9 -9
- package/dist/astro/routes/api/themes/preview.mjs +3 -3
- package/dist/astro/routes/api/typegen.mjs +5 -5
- package/dist/astro/routes/api/widget-areas/_name_/reorder.mjs +4 -4
- package/dist/astro/routes/api/widget-areas/_name_/widgets/_id_.mjs +6 -6
- package/dist/astro/routes/api/widget-areas/_name_/widgets.mjs +6 -6
- package/dist/astro/routes/api/widget-areas/_name_.mjs +5 -5
- package/dist/astro/routes/api/widget-areas/index.mjs +6 -6
- package/dist/astro/routes/api/widget-components.mjs +2 -2
- package/dist/astro/routes/robots.txt.mjs +5 -5
- package/dist/astro/routes/sitemap-_collection_.xml.mjs +10 -9
- package/dist/astro/routes/sitemap-_collection_.xml.mjs.map +1 -1
- package/dist/astro/routes/sitemap.xml.mjs +5 -5
- package/dist/astro/types.d.mts +7 -7
- package/dist/{authorize-CuxZ0i2t.mjs → authorize-BZnOGJFo.mjs} +2 -2
- package/dist/{authorize-CuxZ0i2t.mjs.map → authorize-BZnOGJFo.mjs.map} +1 -1
- package/dist/{byline-C-YajfV7.mjs → byline-LL8lyqdb.mjs} +6 -6
- package/dist/{byline-C-YajfV7.mjs.map → byline-LL8lyqdb.mjs.map} +1 -1
- package/dist/{bylines-D4KADDAi.mjs → bylines-BmJ7Vg7J.mjs} +4 -4
- package/dist/{bylines-D4KADDAi.mjs.map → bylines-BmJ7Vg7J.mjs.map} +1 -1
- package/dist/{bylines-CPc_q2Vd.mjs → bylines-DE47vP8d.mjs} +5 -5
- package/dist/{bylines-CPc_q2Vd.mjs.map → bylines-DE47vP8d.mjs.map} +1 -1
- package/dist/{cache-C35VWD5D.mjs → cache-D9jF5bYw.mjs} +2 -2
- package/dist/{cache-C35VWD5D.mjs.map → cache-D9jF5bYw.mjs.map} +1 -1
- package/dist/{chunks-BHgcHh2C.mjs → chunks-OCG163rN.mjs} +2 -2
- package/dist/{chunks-BHgcHh2C.mjs.map → chunks-OCG163rN.mjs.map} +1 -1
- package/dist/cli/index.mjs +16 -16
- package/dist/{comment-BDx50EX5.mjs → comment-D9BLDpZI.mjs} +3 -3
- package/dist/{comment-BDx50EX5.mjs.map → comment-D9BLDpZI.mjs.map} +1 -1
- package/dist/{comment-reaction-Gv_pgfI3.mjs → comment-reaction-Drl9SkNu.mjs} +2 -2
- package/dist/{comment-reaction-Gv_pgfI3.mjs.map → comment-reaction-Drl9SkNu.mjs.map} +1 -1
- package/dist/{comments-CXHuQ6jI.mjs → comments-BjJ9SKGU.mjs} +3 -3
- package/dist/{comments-CXHuQ6jI.mjs.map → comments-BjJ9SKGU.mjs.map} +1 -1
- package/dist/{content-B43-YrIq.mjs → content-ncUWWjna.mjs} +4 -4
- package/dist/{content-B43-YrIq.mjs.map → content-ncUWWjna.mjs.map} +1 -1
- package/dist/{context-BW3N7wyt.mjs → context-C_g-iJVA.mjs} +7 -7
- package/dist/{context-BW3N7wyt.mjs.map → context-C_g-iJVA.mjs.map} +1 -1
- package/dist/{dashboard-FIe0S512.mjs → dashboard-CotyqQrW.mjs} +4 -4
- package/dist/{dashboard-FIe0S512.mjs.map → dashboard-CotyqQrW.mjs.map} +1 -1
- package/dist/db/index.d.mts +2 -2
- package/dist/db/index.mjs +1 -1
- package/dist/{error-DXnK2wF4.mjs → error-rVGiqWDt.mjs} +2 -2
- package/dist/{error-DXnK2wF4.mjs.map → error-rVGiqWDt.mjs.map} +1 -1
- package/dist/{field-defs-cache-CYYx8xlG.mjs → field-defs-cache-ljXzJCfc.mjs} +2 -2
- package/dist/{field-defs-cache-CYYx8xlG.mjs.map → field-defs-cache-ljXzJCfc.mjs.map} +1 -1
- package/dist/{fts-manager-DW_NR-Fs.mjs → fts-manager-BbCCbEKA.mjs} +2 -2
- package/dist/{fts-manager-DW_NR-Fs.mjs.map → fts-manager-BbCCbEKA.mjs.map} +1 -1
- package/dist/{index-Cz6_JBL3.d.mts → index-BRNabKrx.d.mts} +36 -11
- package/dist/index-BRNabKrx.d.mts.map +1 -0
- package/dist/{index-qbL02uhs.d.mts → index-Dt0OKJB4.d.mts} +2 -2
- package/dist/{index-qbL02uhs.d.mts.map → index-Dt0OKJB4.d.mts.map} +1 -1
- package/dist/index.d.mts +8 -8
- package/dist/index.mjs +38 -38
- package/dist/{load-DMFi4n1p.mjs → load-DMjXghbZ.mjs} +2 -2
- package/dist/{load-DMFi4n1p.mjs.map → load-DMjXghbZ.mjs.map} +1 -1
- package/dist/{loader-DrpofRon.mjs → loader-BA_zhkS_.mjs} +81 -18
- package/dist/loader-BA_zhkS_.mjs.map +1 -0
- package/dist/{manifest-schema-BOfPXse0.mjs → manifest-schema-kPGX7VS-.mjs} +3 -1
- package/dist/manifest-schema-kPGX7VS-.mjs.map +1 -0
- package/dist/media/local-runtime.d.mts +7 -7
- package/dist/media/local-runtime.mjs +5 -5
- package/dist/{media-BjKxjzk8.mjs → media-C5t_eCnk.mjs} +2 -2
- package/dist/{media-BjKxjzk8.mjs.map → media-C5t_eCnk.mjs.map} +1 -1
- package/dist/{menus-8O6xNcYW.mjs → menus-CBb6UrMU.mjs} +3 -3
- package/dist/{menus-8O6xNcYW.mjs.map → menus-CBb6UrMU.mjs.map} +1 -1
- package/dist/{menus-CxqJ-z-N.mjs → menus-CYH09a41.mjs} +50 -68
- package/dist/menus-CYH09a41.mjs.map +1 -0
- package/dist/{object-cache-SEb2IM4Z.mjs → object-cache-CHbHv83-.mjs} +8 -4
- package/dist/object-cache-CHbHv83-.mjs.map +1 -0
- package/dist/{options-BvClpP5Q.d.mts → options-41nCWqi9.d.mts} +2 -2
- package/dist/{options-BvClpP5Q.d.mts.map → options-41nCWqi9.d.mts.map} +1 -1
- package/dist/page/index.d.mts +5 -2
- package/dist/page/index.d.mts.map +1 -1
- package/dist/page/index.mjs +3 -2
- package/dist/page/index.mjs.map +1 -1
- package/dist/{parse-DqMWHQ8x.mjs → parse-BwAdS7FZ.mjs} +2 -2
- package/dist/{parse-DqMWHQ8x.mjs.map → parse-BwAdS7FZ.mjs.map} +1 -1
- package/dist/plugin-types.d.mts +4 -2
- package/dist/plugin-types.d.mts.map +1 -1
- package/dist/plugin-utils.d.mts +7 -7
- package/dist/plugins/adapt-sandbox-entry.d.mts +7 -7
- package/dist/plugins/adapt-sandbox-entry.mjs +1 -1
- package/dist/{query-34pfm02Q.mjs → query-BpQb-blG.mjs} +14 -14
- package/dist/{query-34pfm02Q.mjs.map → query-BpQb-blG.mjs.map} +1 -1
- package/dist/{rate-limit-CBQK4ygJ.mjs → rate-limit-Dap6HMNM.mjs} +2 -2
- package/dist/{rate-limit-CBQK4ygJ.mjs.map → rate-limit-Dap6HMNM.mjs.map} +1 -1
- package/dist/{redirect-C1KVGYWe.mjs → redirect-_M0trWoo.mjs} +2 -2
- package/dist/{redirect-C1KVGYWe.mjs.map → redirect-_M0trWoo.mjs.map} +1 -1
- package/dist/{redirects-DgnypVir.mjs → redirects-w0V9vj_j.mjs} +3 -3
- package/dist/{redirects-DgnypVir.mjs.map → redirects-w0V9vj_j.mjs.map} +1 -1
- package/dist/{registry-3aOAS4My.mjs → registry-g8yYt4cC.mjs} +4 -4
- package/dist/{registry-3aOAS4My.mjs.map → registry-g8yYt4cC.mjs.map} +1 -1
- package/dist/{runner-CEtq-6Sm.d.mts → runner-BbR3DfrL.d.mts} +2 -2
- package/dist/{runner-CEtq-6Sm.d.mts.map → runner-BbR3DfrL.d.mts.map} +1 -1
- package/dist/{runner-BsquExlK.mjs → runner-DPdt_Wpa.mjs} +250 -178
- package/dist/runner-DPdt_Wpa.mjs.map +1 -0
- package/dist/runtime.d.mts +7 -7
- package/dist/runtime.mjs +2 -2
- package/dist/{schema-BGwx8AQY.mjs → schema-DoLd3j2e.mjs} +5 -5
- package/dist/{schema-BGwx8AQY.mjs.map → schema-DoLd3j2e.mjs.map} +1 -1
- package/dist/{search-Gl747zMP.mjs → search-BR0ZeZmh.mjs} +4 -4
- package/dist/{search-Gl747zMP.mjs.map → search-BR0ZeZmh.mjs.map} +1 -1
- package/dist/{sections-C-umuuLj.mjs → sections-5J2YJPqJ.mjs} +3 -3
- package/dist/{sections-C-umuuLj.mjs.map → sections-5J2YJPqJ.mjs.map} +1 -1
- package/dist/seed/index.d.mts +2 -2
- package/dist/seed/index.mjs +15 -15
- package/dist/{seo-BNzkiK_W.mjs → seo-DKeXHkzE.mjs} +3 -3
- package/dist/{seo-BNzkiK_W.mjs.map → seo-DKeXHkzE.mjs.map} +1 -1
- package/dist/{service-CQHK_10l.mjs → service-BbO2s8gT.mjs} +2 -2
- package/dist/{service-CQHK_10l.mjs.map → service-BbO2s8gT.mjs.map} +1 -1
- package/dist/{settings-fPSR6dJa.mjs → settings-BMNr9Dmi.mjs} +3 -3
- package/dist/{settings-fPSR6dJa.mjs.map → settings-BMNr9Dmi.mjs.map} +1 -1
- package/dist/{settings-C4tXRYiG.mjs → settings-DJeki-97.mjs} +4 -4
- package/dist/{settings-C4tXRYiG.mjs.map → settings-DJeki-97.mjs.map} +1 -1
- package/dist/{taxonomies-DbAtL6m4.mjs → taxonomies-CM_fUqLU.mjs} +5 -4
- package/dist/taxonomies-CM_fUqLU.mjs.map +1 -0
- package/dist/{taxonomies-n8w72lLQ.mjs → taxonomies-D13i2ctt.mjs} +75 -20
- package/dist/taxonomies-D13i2ctt.mjs.map +1 -0
- package/dist/{taxonomy-BBUlGug5.mjs → taxonomy-BU0LjdVb.mjs} +4 -4
- package/dist/{taxonomy-BBUlGug5.mjs.map → taxonomy-BU0LjdVb.mjs.map} +1 -1
- package/dist/{types-h2Cwbzi2.d.mts → types-BYnDBVwe.d.mts} +24 -5
- package/dist/{types-h2Cwbzi2.d.mts.map → types-BYnDBVwe.d.mts.map} +1 -1
- package/dist/{types-CmI1OyQg.mjs → types-CZgK3EMW.mjs} +2 -2
- package/dist/{types-CmI1OyQg.mjs.map → types-CZgK3EMW.mjs.map} +1 -1
- package/dist/{types-B-gIxFCE.d.mts → types-xIfVRNLp.d.mts} +38 -1
- package/dist/types-xIfVRNLp.d.mts.map +1 -0
- package/dist/{user-JAuc8VUf.mjs → user-DkG2jKCp.mjs} +3 -3
- package/dist/{user-JAuc8VUf.mjs.map → user-DkG2jKCp.mjs.map} +1 -1
- package/dist/{validate-Va_An3qb.d.mts → validate-CG0V0wNR.d.mts} +2 -2
- package/dist/{validate-Va_An3qb.d.mts.map → validate-CG0V0wNR.d.mts.map} +1 -1
- package/dist/{validate-BzXHWnkV.mjs → validate-CuJ1Ps9j.mjs} +2 -2
- package/dist/{validate-BzXHWnkV.mjs.map → validate-CuJ1Ps9j.mjs.map} +1 -1
- package/dist/{validation-B6DKPTtU.mjs → validation-CwUfTdGF.mjs} +5 -5
- package/dist/{validation-B6DKPTtU.mjs.map → validation-CwUfTdGF.mjs.map} +1 -1
- package/dist/version-BoNBItP_.mjs +7 -0
- package/dist/{version-DHdCA24u.mjs.map → version-BoNBItP_.mjs.map} +1 -1
- package/dist/{widgets-C2RbFN0G.mjs → widgets-BfOZ-ajY.mjs} +2 -2
- package/dist/{widgets-C2RbFN0G.mjs.map → widgets-BfOZ-ajY.mjs.map} +1 -1
- package/dist/{zod-generator-xEHODMJf.mjs → zod-generator-gFsRuNNy.mjs} +6 -3
- package/dist/zod-generator-gFsRuNNy.mjs.map +1 -0
- package/package.json +5 -5
- package/src/api/handlers/taxonomies.ts +5 -1
- package/src/astro/integration/virtual-modules.ts +15 -0
- package/src/astro/routes/sitemap-[collection].xml.ts +5 -4
- package/src/components/EmDashHead.astro +23 -3
- package/src/components/JsonLdScript.astro +9 -0
- package/src/database/migrations/036_i18n_menus_and_taxonomies.ts +16 -0
- package/src/database/migrations/046_media_usage_index.ts +115 -0
- package/src/database/migrations/047_restore_taxonomy_parent_index.ts +29 -0
- package/src/database/migrations/runner.ts +4 -0
- package/src/database/repositories/media-usage.ts +444 -0
- package/src/database/types.ts +39 -0
- package/src/emdash-runtime.ts +61 -52
- package/src/index.ts +3 -0
- package/src/loader.ts +110 -31
- package/src/media/usage/extractor.ts +302 -0
- package/src/media/usage/types.ts +46 -0
- package/src/object-cache/index.ts +8 -2
- package/src/page/metadata.ts +23 -3
- package/src/plugin-types.ts +10 -0
- package/src/plugins/define-plugin.ts +14 -5
- package/src/plugins/hooks.ts +53 -65
- package/src/plugins/index.ts +5 -0
- package/src/plugins/manager.ts +22 -0
- package/src/plugins/manifest-schema.ts +2 -0
- package/src/plugins/types.ts +35 -3
- package/src/schema/zod-generator.ts +9 -1
- package/src/seed/apply.ts +6 -0
- package/src/taxonomies/index.ts +121 -18
- package/dist/apply-Bk2mAuLn.mjs.map +0 -1
- package/dist/index-Cz6_JBL3.d.mts.map +0 -1
- package/dist/loader-DrpofRon.mjs.map +0 -1
- package/dist/manifest-schema-BOfPXse0.mjs.map +0 -1
- package/dist/menus-CxqJ-z-N.mjs.map +0 -1
- package/dist/object-cache-SEb2IM4Z.mjs.map +0 -1
- package/dist/runner-BsquExlK.mjs.map +0 -1
- package/dist/taxonomies-DbAtL6m4.mjs.map +0 -1
- package/dist/taxonomies-n8w72lLQ.mjs.map +0 -1
- package/dist/types-B-gIxFCE.d.mts.map +0 -1
- package/dist/version-DHdCA24u.mjs +0 -7
- package/dist/zod-generator-xEHODMJf.mjs.map +0 -1
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import type { FieldType } from "../../schema/types.js";
|
|
2
|
+
|
|
3
|
+
export type MediaKind =
|
|
4
|
+
| "image"
|
|
5
|
+
| "video"
|
|
6
|
+
| "audio"
|
|
7
|
+
| "document"
|
|
8
|
+
| "archive"
|
|
9
|
+
| "font"
|
|
10
|
+
| "text"
|
|
11
|
+
| "other";
|
|
12
|
+
|
|
13
|
+
export type MediaUsageReferenceType = "image_field" | "file_field" | "portable_text_image";
|
|
14
|
+
|
|
15
|
+
export interface MediaUsageExtractionSubField {
|
|
16
|
+
slug: string;
|
|
17
|
+
type: FieldType;
|
|
18
|
+
label?: string;
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
export interface MediaUsageExtractionValidation {
|
|
22
|
+
subFields?: readonly MediaUsageExtractionSubField[];
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
export interface MediaUsageExtractionField {
|
|
26
|
+
slug: string;
|
|
27
|
+
type: FieldType;
|
|
28
|
+
validation?: MediaUsageExtractionValidation | null;
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
export interface ExtractMediaUsageOccurrencesInput {
|
|
32
|
+
fields: readonly MediaUsageExtractionField[];
|
|
33
|
+
data: Record<string, unknown>;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
export interface ExtractedMediaUsageOccurrence {
|
|
37
|
+
fieldSlug: string;
|
|
38
|
+
fieldPath: string;
|
|
39
|
+
occurrenceIndex: number;
|
|
40
|
+
referenceType: MediaUsageReferenceType;
|
|
41
|
+
mediaId: string | null;
|
|
42
|
+
provider: string;
|
|
43
|
+
providerAssetId: string;
|
|
44
|
+
mediaKind: MediaKind | null;
|
|
45
|
+
mimeType: string | null;
|
|
46
|
+
}
|
|
@@ -167,7 +167,7 @@ async function getBackend(): Promise<ObjectCacheBackend | null> {
|
|
|
167
167
|
} catch (error) {
|
|
168
168
|
// Importing the virtual module fails outside an Astro/Vite context
|
|
169
169
|
// (e.g. unit tests, CLI). Treat as "no cache configured".
|
|
170
|
-
if (import.meta.env
|
|
170
|
+
if (import.meta.env?.DEV) {
|
|
171
171
|
console.warn("[object-cache] backend unavailable:", error);
|
|
172
172
|
}
|
|
173
173
|
holder.backend = null;
|
|
@@ -378,7 +378,7 @@ export async function cachedQuery<T>(options: CachedQueryOptions<T>): Promise<T>
|
|
|
378
378
|
const encoded = encode({ e: currentEpochs, v: value } satisfies CacheEnvelope<T>);
|
|
379
379
|
await backend.set(fullKey, encoded, ttl);
|
|
380
380
|
} catch (error) {
|
|
381
|
-
if (import.meta.env
|
|
381
|
+
if (import.meta.env?.DEV) {
|
|
382
382
|
console.warn("[object-cache] set failed:", error);
|
|
383
383
|
}
|
|
384
384
|
}
|
|
@@ -388,6 +388,12 @@ export async function cachedQuery<T>(options: CachedQueryOptions<T>): Promise<T>
|
|
|
388
388
|
return value;
|
|
389
389
|
}
|
|
390
390
|
|
|
391
|
+
/** Whether object-cache reads are active for the current request. */
|
|
392
|
+
export async function isObjectCacheActive(): Promise<boolean> {
|
|
393
|
+
const backend = await getBackend();
|
|
394
|
+
return backend !== null && !shouldBypass();
|
|
395
|
+
}
|
|
396
|
+
|
|
391
397
|
/**
|
|
392
398
|
* Invalidate every cached value in `namespace` by bumping its epoch.
|
|
393
399
|
*
|
package/src/page/metadata.ts
CHANGED
|
@@ -20,6 +20,10 @@ export interface ResolvedPageMetadata {
|
|
|
20
20
|
jsonld: Array<{ id?: string; json: string }>;
|
|
21
21
|
}
|
|
22
22
|
|
|
23
|
+
interface RenderPageMetadataOptions {
|
|
24
|
+
includeJsonLd?: boolean;
|
|
25
|
+
}
|
|
26
|
+
|
|
23
27
|
// ── Validation ──────────────────────────────────────────────────
|
|
24
28
|
|
|
25
29
|
/** Schemes safe for use in link href attributes */
|
|
@@ -66,6 +70,16 @@ export function safeJsonLdSerialize(value: unknown): string {
|
|
|
66
70
|
.replace(JSONLD_U2029_RE, "\\u2029");
|
|
67
71
|
}
|
|
68
72
|
|
|
73
|
+
export async function createSha256CspHash(value: string): Promise<string> {
|
|
74
|
+
const digest = await crypto.subtle.digest("SHA-256", new TextEncoder().encode(value));
|
|
75
|
+
const bytes = new Uint8Array(digest);
|
|
76
|
+
let binary = "";
|
|
77
|
+
for (const byte of bytes) {
|
|
78
|
+
binary += String.fromCharCode(byte);
|
|
79
|
+
}
|
|
80
|
+
return `sha256-${btoa(binary)}`;
|
|
81
|
+
}
|
|
82
|
+
|
|
69
83
|
// ── Merge / dedupe ──────────────────────────────────────────────
|
|
70
84
|
|
|
71
85
|
/**
|
|
@@ -155,8 +169,12 @@ export function resolvePageMetadata(
|
|
|
155
169
|
// ── HTML rendering ──────────────────────────────────────────────
|
|
156
170
|
|
|
157
171
|
/** Render resolved metadata to an HTML string for embedding in <head> */
|
|
158
|
-
export function renderPageMetadata(
|
|
172
|
+
export function renderPageMetadata(
|
|
173
|
+
metadata: ResolvedPageMetadata,
|
|
174
|
+
options: RenderPageMetadataOptions = {},
|
|
175
|
+
): string {
|
|
159
176
|
const parts: string[] = [];
|
|
177
|
+
const includeJsonLd = options.includeJsonLd ?? true;
|
|
160
178
|
|
|
161
179
|
for (const m of metadata.meta) {
|
|
162
180
|
parts.push(`<meta name="${escapeHtmlAttr(m.name)}" content="${escapeHtmlAttr(m.content)}">`);
|
|
@@ -177,8 +195,10 @@ export function renderPageMetadata(metadata: ResolvedPageMetadata): string {
|
|
|
177
195
|
parts.push(tag);
|
|
178
196
|
}
|
|
179
197
|
|
|
180
|
-
|
|
181
|
-
|
|
198
|
+
if (includeJsonLd) {
|
|
199
|
+
for (const j of metadata.jsonld) {
|
|
200
|
+
parts.push(`<script type="application/ld+json">${j.json}</script>`);
|
|
201
|
+
}
|
|
182
202
|
}
|
|
183
203
|
|
|
184
204
|
return parts.join("\n");
|
package/src/plugin-types.ts
CHANGED
|
@@ -51,12 +51,17 @@ import type {
|
|
|
51
51
|
ContentAfterPublishHandler,
|
|
52
52
|
ContentAfterRestoreHandler,
|
|
53
53
|
ContentAfterSaveHandler,
|
|
54
|
+
ContentAfterScheduleHandler,
|
|
54
55
|
ContentAfterUnpublishHandler,
|
|
56
|
+
ContentAfterUnscheduleHandler,
|
|
55
57
|
ContentBeforeDeleteHandler,
|
|
56
58
|
ContentBeforeSaveHandler,
|
|
57
59
|
ContentDeleteEvent,
|
|
58
60
|
ContentHookEvent,
|
|
59
61
|
ContentPublishStateChangeEvent,
|
|
62
|
+
ContentRestoreStateChangeEvent,
|
|
63
|
+
ContentScheduleStateChangeEvent,
|
|
64
|
+
ContentStateChangeEvent,
|
|
60
65
|
CronEvent,
|
|
61
66
|
CronHandler,
|
|
62
67
|
EmailAfterSendEvent,
|
|
@@ -99,6 +104,8 @@ export interface HookHandlers {
|
|
|
99
104
|
"content:afterPublish": ContentAfterPublishHandler;
|
|
100
105
|
"content:afterUnpublish": ContentAfterUnpublishHandler;
|
|
101
106
|
"content:afterRestore": ContentAfterRestoreHandler;
|
|
107
|
+
"content:afterSchedule": ContentAfterScheduleHandler;
|
|
108
|
+
"content:afterUnschedule": ContentAfterUnscheduleHandler;
|
|
102
109
|
"media:beforeUpload": MediaBeforeUploadHandler;
|
|
103
110
|
"media:afterUpload": MediaAfterUploadHandler;
|
|
104
111
|
cron: CronHandler;
|
|
@@ -228,6 +235,9 @@ export type {
|
|
|
228
235
|
ContentDeleteEvent,
|
|
229
236
|
ContentHookEvent,
|
|
230
237
|
ContentPublishStateChangeEvent,
|
|
238
|
+
ContentRestoreStateChangeEvent,
|
|
239
|
+
ContentScheduleStateChangeEvent,
|
|
240
|
+
ContentStateChangeEvent,
|
|
231
241
|
CronEvent,
|
|
232
242
|
EmailAfterSendEvent,
|
|
233
243
|
EmailBeforeSendEvent,
|
|
@@ -22,11 +22,6 @@ import type {
|
|
|
22
22
|
PluginStorageConfig,
|
|
23
23
|
} from "./types.js";
|
|
24
24
|
|
|
25
|
-
// Plugin ID validation patterns
|
|
26
|
-
const SIMPLE_ID = /^[a-z0-9-]+$/;
|
|
27
|
-
const SCOPED_ID = /^@[a-z0-9-]+\/[a-z0-9-]+$/;
|
|
28
|
-
const SEMVER_PATTERN = /^\d+\.\d+\.\d+/;
|
|
29
|
-
|
|
30
25
|
/**
|
|
31
26
|
* Define a native EmDash plugin.
|
|
32
27
|
*
|
|
@@ -94,6 +89,20 @@ export function definePlugin<TStorage extends PluginStorageConfig>(
|
|
|
94
89
|
function defineNativePlugin<TStorage extends PluginStorageConfig>(
|
|
95
90
|
definition: PluginDefinition<TStorage>,
|
|
96
91
|
): ResolvedPlugin<TStorage> {
|
|
92
|
+
// Declared function-local (not module scope) on purpose. Under
|
|
93
|
+
// `ssr.noExternal` the worker entry can instantiate native plugins during a
|
|
94
|
+
// circular module init, reaching this function before module-scope consts
|
|
95
|
+
// initialize -> "Cannot access 'SIMPLE_ID' before initialization" -> every
|
|
96
|
+
// route 500s on Cloudflare Workers. Call-time consts evaluate after the
|
|
97
|
+
// literals are parsed, so the temporal dead zone cannot occur regardless of
|
|
98
|
+
// bundle ordering. See #1370.
|
|
99
|
+
// oxlint-disable-next-line e18e/prefer-static-regex -- call-time on purpose (see #1370)
|
|
100
|
+
const SIMPLE_ID = /^[a-z0-9-]+$/;
|
|
101
|
+
// oxlint-disable-next-line e18e/prefer-static-regex -- call-time on purpose (see #1370)
|
|
102
|
+
const SCOPED_ID = /^@[a-z0-9-]+\/[a-z0-9-]+$/;
|
|
103
|
+
// oxlint-disable-next-line e18e/prefer-static-regex -- call-time on purpose (see #1370)
|
|
104
|
+
const SEMVER_PATTERN = /^\d+\.\d+\.\d+/;
|
|
105
|
+
|
|
97
106
|
const {
|
|
98
107
|
id,
|
|
99
108
|
version,
|
package/src/plugins/hooks.ts
CHANGED
|
@@ -17,7 +17,7 @@ import type {
|
|
|
17
17
|
PluginContext,
|
|
18
18
|
ContentHookEvent,
|
|
19
19
|
ContentDeleteEvent,
|
|
20
|
-
|
|
20
|
+
ContentStateChangeEvent,
|
|
21
21
|
MediaUploadEvent,
|
|
22
22
|
MediaAfterUploadEvent,
|
|
23
23
|
LifecycleEvent,
|
|
@@ -33,7 +33,9 @@ import type {
|
|
|
33
33
|
ContentAfterDeleteHandler,
|
|
34
34
|
ContentAfterPublishHandler,
|
|
35
35
|
ContentAfterRestoreHandler,
|
|
36
|
+
ContentAfterScheduleHandler,
|
|
36
37
|
ContentAfterUnpublishHandler,
|
|
38
|
+
ContentAfterUnscheduleHandler,
|
|
37
39
|
MediaBeforeUploadHandler,
|
|
38
40
|
MediaAfterUploadHandler,
|
|
39
41
|
LifecycleHandler,
|
|
@@ -68,6 +70,8 @@ type HookNameV2 =
|
|
|
68
70
|
| "content:afterPublish"
|
|
69
71
|
| "content:afterUnpublish"
|
|
70
72
|
| "content:afterRestore"
|
|
73
|
+
| "content:afterSchedule"
|
|
74
|
+
| "content:afterUnschedule"
|
|
71
75
|
| "media:beforeUpload"
|
|
72
76
|
| "media:afterUpload"
|
|
73
77
|
| "cron"
|
|
@@ -84,6 +88,13 @@ type HookNameV2 =
|
|
|
84
88
|
/**
|
|
85
89
|
* Map from hook name to handler type — used for type-safe hook retrieval
|
|
86
90
|
*/
|
|
91
|
+
type ContentStateChangeHookName =
|
|
92
|
+
| "content:afterPublish"
|
|
93
|
+
| "content:afterUnpublish"
|
|
94
|
+
| "content:afterRestore"
|
|
95
|
+
| "content:afterSchedule"
|
|
96
|
+
| "content:afterUnschedule";
|
|
97
|
+
|
|
87
98
|
interface HookHandlerMap {
|
|
88
99
|
"plugin:install": LifecycleHandler;
|
|
89
100
|
"plugin:activate": LifecycleHandler;
|
|
@@ -96,6 +107,8 @@ interface HookHandlerMap {
|
|
|
96
107
|
"content:afterPublish": ContentAfterPublishHandler;
|
|
97
108
|
"content:afterUnpublish": ContentAfterUnpublishHandler;
|
|
98
109
|
"content:afterRestore": ContentAfterRestoreHandler;
|
|
110
|
+
"content:afterSchedule": ContentAfterScheduleHandler;
|
|
111
|
+
"content:afterUnschedule": ContentAfterUnscheduleHandler;
|
|
99
112
|
"media:beforeUpload": MediaBeforeUploadHandler;
|
|
100
113
|
"media:afterUpload": MediaAfterUploadHandler;
|
|
101
114
|
cron: CronHandler;
|
|
@@ -224,6 +237,8 @@ export class HookPipeline {
|
|
|
224
237
|
this.registerPluginHook(plugin, "content:afterPublish");
|
|
225
238
|
this.registerPluginHook(plugin, "content:afterUnpublish");
|
|
226
239
|
this.registerPluginHook(plugin, "content:afterRestore");
|
|
240
|
+
this.registerPluginHook(plugin, "content:afterSchedule");
|
|
241
|
+
this.registerPluginHook(plugin, "content:afterUnschedule");
|
|
227
242
|
this.registerPluginHook(plugin, "media:beforeUpload");
|
|
228
243
|
this.registerPluginHook(plugin, "media:afterUpload");
|
|
229
244
|
this.registerPluginHook(plugin, "cron");
|
|
@@ -269,6 +284,8 @@ export class HookPipeline {
|
|
|
269
284
|
["content:afterPublish", "content:read"],
|
|
270
285
|
["content:afterUnpublish", "content:read"],
|
|
271
286
|
["content:afterRestore", "content:read"],
|
|
287
|
+
["content:afterSchedule", "content:read"],
|
|
288
|
+
["content:afterUnschedule", "content:read"],
|
|
272
289
|
// Media
|
|
273
290
|
["media:beforeUpload", "media:write"],
|
|
274
291
|
["media:afterUpload", "media:read"],
|
|
@@ -653,18 +670,19 @@ export class HookPipeline {
|
|
|
653
670
|
}
|
|
654
671
|
|
|
655
672
|
/**
|
|
656
|
-
* Run content
|
|
673
|
+
* Run content state-change hooks that all share the same event shape.
|
|
657
674
|
*/
|
|
658
|
-
async
|
|
675
|
+
private async runContentStateChangeHook(
|
|
676
|
+
name: ContentStateChangeHookName,
|
|
659
677
|
content: Record<string, unknown>,
|
|
660
678
|
collection: string,
|
|
661
679
|
): Promise<HookResult<void>[]> {
|
|
662
|
-
const hooks = this.getTypedHooks(
|
|
680
|
+
const hooks = this.getTypedHooks(name);
|
|
663
681
|
const results: HookResult<void>[] = [];
|
|
664
682
|
|
|
665
683
|
for (const hook of hooks) {
|
|
666
684
|
const { handler } = hook;
|
|
667
|
-
const event:
|
|
685
|
+
const event: ContentStateChangeEvent = { content, collection };
|
|
668
686
|
const ctx = this.getContext(hook.pluginId);
|
|
669
687
|
const start = Date.now();
|
|
670
688
|
|
|
@@ -692,6 +710,16 @@ export class HookPipeline {
|
|
|
692
710
|
return results;
|
|
693
711
|
}
|
|
694
712
|
|
|
713
|
+
/**
|
|
714
|
+
* Run content:afterPublish hooks (fire-and-forget).
|
|
715
|
+
*/
|
|
716
|
+
async runContentAfterPublish(
|
|
717
|
+
content: Record<string, unknown>,
|
|
718
|
+
collection: string,
|
|
719
|
+
): Promise<HookResult<void>[]> {
|
|
720
|
+
return this.runContentStateChangeHook("content:afterPublish", content, collection);
|
|
721
|
+
}
|
|
722
|
+
|
|
695
723
|
/**
|
|
696
724
|
* Run content:afterUnpublish hooks (fire-and-forget).
|
|
697
725
|
*/
|
|
@@ -699,37 +727,7 @@ export class HookPipeline {
|
|
|
699
727
|
content: Record<string, unknown>,
|
|
700
728
|
collection: string,
|
|
701
729
|
): Promise<HookResult<void>[]> {
|
|
702
|
-
|
|
703
|
-
const results: HookResult<void>[] = [];
|
|
704
|
-
|
|
705
|
-
for (const hook of hooks) {
|
|
706
|
-
const { handler } = hook;
|
|
707
|
-
const event: ContentPublishStateChangeEvent = { content, collection };
|
|
708
|
-
const ctx = this.getContext(hook.pluginId);
|
|
709
|
-
const start = Date.now();
|
|
710
|
-
|
|
711
|
-
try {
|
|
712
|
-
await this.executeWithTimeout(() => handler(event, ctx), hook.timeout);
|
|
713
|
-
results.push({
|
|
714
|
-
success: true,
|
|
715
|
-
pluginId: hook.pluginId,
|
|
716
|
-
duration: Date.now() - start,
|
|
717
|
-
});
|
|
718
|
-
} catch (error) {
|
|
719
|
-
results.push({
|
|
720
|
-
success: false,
|
|
721
|
-
error: error instanceof Error ? error : new Error(String(error)),
|
|
722
|
-
pluginId: hook.pluginId,
|
|
723
|
-
duration: Date.now() - start,
|
|
724
|
-
});
|
|
725
|
-
|
|
726
|
-
if (hook.errorPolicy === "abort") {
|
|
727
|
-
throw error;
|
|
728
|
-
}
|
|
729
|
-
}
|
|
730
|
-
}
|
|
731
|
-
|
|
732
|
-
return results;
|
|
730
|
+
return this.runContentStateChangeHook("content:afterUnpublish", content, collection);
|
|
733
731
|
}
|
|
734
732
|
|
|
735
733
|
/**
|
|
@@ -739,37 +737,27 @@ export class HookPipeline {
|
|
|
739
737
|
content: Record<string, unknown>,
|
|
740
738
|
collection: string,
|
|
741
739
|
): Promise<HookResult<void>[]> {
|
|
742
|
-
|
|
743
|
-
|
|
744
|
-
|
|
745
|
-
for (const hook of hooks) {
|
|
746
|
-
const { handler } = hook;
|
|
747
|
-
const event: ContentPublishStateChangeEvent = { content, collection };
|
|
748
|
-
const ctx = this.getContext(hook.pluginId);
|
|
749
|
-
const start = Date.now();
|
|
750
|
-
|
|
751
|
-
try {
|
|
752
|
-
await this.executeWithTimeout(() => handler(event, ctx), hook.timeout);
|
|
753
|
-
results.push({
|
|
754
|
-
success: true,
|
|
755
|
-
pluginId: hook.pluginId,
|
|
756
|
-
duration: Date.now() - start,
|
|
757
|
-
});
|
|
758
|
-
} catch (error) {
|
|
759
|
-
results.push({
|
|
760
|
-
success: false,
|
|
761
|
-
error: error instanceof Error ? error : new Error(String(error)),
|
|
762
|
-
pluginId: hook.pluginId,
|
|
763
|
-
duration: Date.now() - start,
|
|
764
|
-
});
|
|
740
|
+
return this.runContentStateChangeHook("content:afterRestore", content, collection);
|
|
741
|
+
}
|
|
765
742
|
|
|
766
|
-
|
|
767
|
-
|
|
768
|
-
|
|
769
|
-
|
|
770
|
-
|
|
743
|
+
/**
|
|
744
|
+
* Run content:afterSchedule hooks (fire-and-forget).
|
|
745
|
+
*/
|
|
746
|
+
async runContentAfterSchedule(
|
|
747
|
+
content: Record<string, unknown>,
|
|
748
|
+
collection: string,
|
|
749
|
+
): Promise<HookResult<void>[]> {
|
|
750
|
+
return this.runContentStateChangeHook("content:afterSchedule", content, collection);
|
|
751
|
+
}
|
|
771
752
|
|
|
772
|
-
|
|
753
|
+
/**
|
|
754
|
+
* Run content:afterUnschedule hooks (fire-and-forget).
|
|
755
|
+
*/
|
|
756
|
+
async runContentAfterUnschedule(
|
|
757
|
+
content: Record<string, unknown>,
|
|
758
|
+
collection: string,
|
|
759
|
+
): Promise<HookResult<void>[]> {
|
|
760
|
+
return this.runContentStateChangeHook("content:afterUnschedule", content, collection);
|
|
773
761
|
}
|
|
774
762
|
|
|
775
763
|
// =========================================================================
|
package/src/plugins/index.ts
CHANGED
|
@@ -128,6 +128,9 @@ export type {
|
|
|
128
128
|
ContentHookEvent,
|
|
129
129
|
ContentDeleteEvent,
|
|
130
130
|
ContentPublishStateChangeEvent,
|
|
131
|
+
ContentRestoreStateChangeEvent,
|
|
132
|
+
ContentScheduleStateChangeEvent,
|
|
133
|
+
ContentStateChangeEvent,
|
|
131
134
|
MediaUploadEvent,
|
|
132
135
|
MediaAfterUploadEvent,
|
|
133
136
|
LifecycleEvent,
|
|
@@ -149,6 +152,8 @@ export type {
|
|
|
149
152
|
ContentBeforeDeleteHandler,
|
|
150
153
|
ContentAfterDeleteHandler,
|
|
151
154
|
ContentAfterRestoreHandler,
|
|
155
|
+
ContentAfterScheduleHandler,
|
|
156
|
+
ContentAfterUnscheduleHandler,
|
|
152
157
|
MediaBeforeUploadHandler,
|
|
153
158
|
MediaAfterUploadHandler,
|
|
154
159
|
LifecycleHandler,
|
package/src/plugins/manager.ts
CHANGED
|
@@ -381,6 +381,28 @@ export class PluginManager {
|
|
|
381
381
|
return this.hookPipeline!.runContentAfterRestore(content, collection);
|
|
382
382
|
}
|
|
383
383
|
|
|
384
|
+
/**
|
|
385
|
+
* Run content:afterSchedule hooks across all active plugins
|
|
386
|
+
*/
|
|
387
|
+
async runContentAfterSchedule(
|
|
388
|
+
content: Record<string, unknown>,
|
|
389
|
+
collection: string,
|
|
390
|
+
): Promise<HookResult<void>[]> {
|
|
391
|
+
this.ensureInitialized();
|
|
392
|
+
return this.hookPipeline!.runContentAfterSchedule(content, collection);
|
|
393
|
+
}
|
|
394
|
+
|
|
395
|
+
/**
|
|
396
|
+
* Run content:afterUnschedule hooks across all active plugins
|
|
397
|
+
*/
|
|
398
|
+
async runContentAfterUnschedule(
|
|
399
|
+
content: Record<string, unknown>,
|
|
400
|
+
collection: string,
|
|
401
|
+
): Promise<HookResult<void>[]> {
|
|
402
|
+
this.ensureInitialized();
|
|
403
|
+
return this.hookPipeline!.runContentAfterUnschedule(content, collection);
|
|
404
|
+
}
|
|
405
|
+
|
|
384
406
|
/**
|
|
385
407
|
* Run media:beforeUpload hooks across all active plugins
|
|
386
408
|
*/
|
package/src/plugins/types.ts
CHANGED
|
@@ -725,13 +725,29 @@ export interface ContentDeleteEvent {
|
|
|
725
725
|
}
|
|
726
726
|
|
|
727
727
|
/**
|
|
728
|
-
* Content
|
|
728
|
+
* Content state-change hook event (fired after publish, unpublish, restore,
|
|
729
|
+
* schedule, or unschedule).
|
|
729
730
|
*/
|
|
730
|
-
export interface
|
|
731
|
+
export interface ContentStateChangeEvent {
|
|
731
732
|
content: Record<string, unknown>;
|
|
732
733
|
collection: string;
|
|
733
734
|
}
|
|
734
735
|
|
|
736
|
+
/**
|
|
737
|
+
* Content publish/unpublish hook event.
|
|
738
|
+
*/
|
|
739
|
+
export type ContentPublishStateChangeEvent = ContentStateChangeEvent;
|
|
740
|
+
|
|
741
|
+
/**
|
|
742
|
+
* Content restore hook event.
|
|
743
|
+
*/
|
|
744
|
+
export type ContentRestoreStateChangeEvent = ContentStateChangeEvent;
|
|
745
|
+
|
|
746
|
+
/**
|
|
747
|
+
* Content schedule/unschedule hook event.
|
|
748
|
+
*/
|
|
749
|
+
export type ContentScheduleStateChangeEvent = ContentStateChangeEvent;
|
|
750
|
+
|
|
735
751
|
/**
|
|
736
752
|
* Media hook event
|
|
737
753
|
*/
|
|
@@ -792,7 +808,17 @@ export type ContentAfterUnpublishHandler = (
|
|
|
792
808
|
) => Promise<void>;
|
|
793
809
|
|
|
794
810
|
export type ContentAfterRestoreHandler = (
|
|
795
|
-
event:
|
|
811
|
+
event: ContentRestoreStateChangeEvent,
|
|
812
|
+
ctx: PluginContext,
|
|
813
|
+
) => Promise<void>;
|
|
814
|
+
|
|
815
|
+
export type ContentAfterScheduleHandler = (
|
|
816
|
+
event: ContentScheduleStateChangeEvent,
|
|
817
|
+
ctx: PluginContext,
|
|
818
|
+
) => Promise<void>;
|
|
819
|
+
|
|
820
|
+
export type ContentAfterUnscheduleHandler = (
|
|
821
|
+
event: ContentScheduleStateChangeEvent,
|
|
796
822
|
ctx: PluginContext,
|
|
797
823
|
) => Promise<void>;
|
|
798
824
|
|
|
@@ -982,6 +1008,10 @@ export interface PluginHooks {
|
|
|
982
1008
|
| HookConfig<ContentAfterUnpublishHandler>
|
|
983
1009
|
| ContentAfterUnpublishHandler;
|
|
984
1010
|
"content:afterRestore"?: HookConfig<ContentAfterRestoreHandler> | ContentAfterRestoreHandler;
|
|
1011
|
+
"content:afterSchedule"?: HookConfig<ContentAfterScheduleHandler> | ContentAfterScheduleHandler;
|
|
1012
|
+
"content:afterUnschedule"?:
|
|
1013
|
+
| HookConfig<ContentAfterUnscheduleHandler>
|
|
1014
|
+
| ContentAfterUnscheduleHandler;
|
|
985
1015
|
|
|
986
1016
|
// Media hooks
|
|
987
1017
|
"media:beforeUpload"?: HookConfig<MediaBeforeUploadHandler> | MediaBeforeUploadHandler;
|
|
@@ -1302,6 +1332,8 @@ export interface ResolvedPluginHooks {
|
|
|
1302
1332
|
"content:afterPublish"?: ResolvedHook<ContentAfterPublishHandler>;
|
|
1303
1333
|
"content:afterUnpublish"?: ResolvedHook<ContentAfterUnpublishHandler>;
|
|
1304
1334
|
"content:afterRestore"?: ResolvedHook<ContentAfterRestoreHandler>;
|
|
1335
|
+
"content:afterSchedule"?: ResolvedHook<ContentAfterScheduleHandler>;
|
|
1336
|
+
"content:afterUnschedule"?: ResolvedHook<ContentAfterUnscheduleHandler>;
|
|
1305
1337
|
"media:beforeUpload"?: ResolvedHook<MediaBeforeUploadHandler>;
|
|
1306
1338
|
"media:afterUpload"?: ResolvedHook<MediaAfterUploadHandler>;
|
|
1307
1339
|
cron?: ResolvedHook<CronHandler>;
|
|
@@ -86,7 +86,15 @@ function getBaseSchema(type: FieldType, field: Field): ZodTypeAny {
|
|
|
86
86
|
return z.preprocess((v) => (v === 0 || v === 1 ? Boolean(v) : v), z.boolean());
|
|
87
87
|
|
|
88
88
|
case "datetime":
|
|
89
|
-
|
|
89
|
+
// Accept every value that legitimately round-trips through the admin
|
|
90
|
+
// and seeds: ISO with `Z`, ISO with a timezone offset, a naive
|
|
91
|
+
// datetime (`YYYY-MM-DDTHH:mm[:ss]` -- what `<input type="datetime-local">`
|
|
92
|
+
// and many seeds produce), and a date-only value. The admin re-sends
|
|
93
|
+
// every loaded field on autosave, so a stored naive datetime must
|
|
94
|
+
// validate or the entry becomes unsavable through its own editor
|
|
95
|
+
// (#1368; same class as #867). `z.iso.*` retains semantic validation,
|
|
96
|
+
// so impossible dates are still rejected.
|
|
97
|
+
return z.iso.datetime({ offset: true, local: true }).or(z.iso.date());
|
|
90
98
|
|
|
91
99
|
case "select": {
|
|
92
100
|
const options = field.validation?.options;
|
package/src/seed/apply.ts
CHANGED
|
@@ -346,6 +346,12 @@ export async function applySeed(
|
|
|
346
346
|
}
|
|
347
347
|
}
|
|
348
348
|
}
|
|
349
|
+
|
|
350
|
+
// Seeded/updated defs change which taxonomies exist — clear the
|
|
351
|
+
// isolate-wide defs + names caches so later reads in this isolate
|
|
352
|
+
// (e.g. an auto-seed triggered mid-request) reflect them immediately.
|
|
353
|
+
const { invalidateTaxonomyDefsCache } = await import("../taxonomies/index.js");
|
|
354
|
+
invalidateTaxonomyDefsCache();
|
|
349
355
|
}
|
|
350
356
|
|
|
351
357
|
// 6. Bylines
|