@riverbankcms/sdk 0.144.0 → 0.145.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 (162) hide show
  1. package/dist/{PreviewEditorSidebar-CQZNnFiM.mjs → PreviewEditorSidebar-O-V6Pl5a.mjs} +4 -4
  2. package/dist/{PreviewEditorUI-DCNxnmI0.mjs → PreviewEditorUI-1UlX_9cw.mjs} +3 -3
  3. package/dist/{PreviewQueryProvider-BCYICImX.mjs → PreviewQueryProvider-BxGwdOCV.mjs} +1 -1
  4. package/dist/{SdkPreviewModeRuntime-BJolUbr1.mjs → SdkPreviewModeRuntime-DYbA_4iv.mjs} +419 -348
  5. package/dist/{SiteChromeCustomizeContext-CKgEpoxi.mjs → SiteChromeCustomizeContext-CNTKQ9nx.mjs} +2081 -1313
  6. package/dist/_dts/ai/src/contracts/proposals.d.ts +4719 -66
  7. package/dist/_dts/ai/src/contracts/siteStyleProposalSchemas.d.ts +429 -6
  8. package/dist/_dts/api/src/appointmentEndpointDefinitions.d.ts +49 -0
  9. package/dist/_dts/api/src/appointmentServiceCategoryEndpoints.d.ts +75 -0
  10. package/dist/_dts/api/src/appointmentServiceContracts.d.ts +80 -0
  11. package/dist/_dts/api/src/appointmentSetup.d.ts +8 -1
  12. package/dist/_dts/api/src/bookingManagementEndpoints.d.ts +2 -12
  13. package/dist/_dts/api/src/communications.d.ts +14 -22
  14. package/dist/_dts/api/src/contentRuntime.d.ts +2 -0
  15. package/dist/_dts/api/src/endpoints.d.ts +105 -58
  16. package/dist/_dts/api/src/indexExtendedTypes.d.ts +1 -1
  17. package/dist/_dts/api/src/launchReadiness.d.ts +2 -0
  18. package/dist/_dts/api/src/newsletterEndpointDefinitions.d.ts +0 -23
  19. package/dist/_dts/api/src/onboarding/confirmationResend.d.ts +3 -0
  20. package/dist/_dts/api/src/publicBookingService.d.ts +35 -1
  21. package/dist/_dts/api/src/publicExperience/newsletterEndpoints.d.ts +13 -0
  22. package/dist/_dts/api/src/publicNewsletterEndpointDefinitions.d.ts +58 -0
  23. package/dist/_dts/api/src/schemas/admin-observability-logs.d.ts +3 -3
  24. package/dist/_dts/api/src/siteManagementEndpoints.d.ts +2 -6
  25. package/dist/_dts/api/src/types.d.ts +2 -1
  26. package/dist/_dts/blocks/src/PageRenderer.d.ts +4 -4
  27. package/dist/_dts/blocks/src/bindings/index.d.ts +2 -2
  28. package/dist/_dts/blocks/src/contracts/proof-block-islands.d.ts +24 -0
  29. package/dist/_dts/blocks/src/index.d.ts +1 -1
  30. package/dist/_dts/blocks/src/pageRenderJoins.d.ts +68 -0
  31. package/dist/_dts/blocks/src/pageRenderPlan.d.ts +8 -27
  32. package/dist/_dts/blocks/src/pageRenderPreparation.d.ts +7 -4
  33. package/dist/_dts/blocks/src/pageRendererBoundaries.d.ts +40 -23
  34. package/dist/_dts/blocks/src/server.d.ts +1 -1
  35. package/dist/_dts/blocks/src/system/blocks/appointment-services.d.ts +2 -0
  36. package/dist/_dts/blocks/src/system/blocks/events/eventSelectionFields.d.ts +2 -2
  37. package/dist/_dts/blocks/src/system/blocks/events/shared/calendarWindow.d.ts +1 -1
  38. package/dist/_dts/blocks/src/system/blocks/location-map.d.ts +2 -2
  39. package/dist/_dts/blocks/src/system/blocks/media-text.d.ts +47 -47
  40. package/dist/_dts/blocks/src/system/manifest/schema.d.ts +29 -3
  41. package/dist/_dts/blocks/src/system/runtime/hooks/useHeadlessBookingFlow.d.ts +8 -1
  42. package/dist/_dts/blocks/src/system/runtime/nodes/appointment-services.d.ts +22 -2
  43. package/dist/_dts/blocks/src/system/runtime/nodes/booking-form.headless.state.d.ts +3 -1
  44. package/dist/_dts/blocks/src/system/runtime/nodes/booking-form.interactive.d.ts +57 -2
  45. package/dist/_dts/blocks/src/system/runtime/nodes/booking-form.service-categories.d.ts +29 -0
  46. package/dist/_dts/blocks/src/system/runtime/nodes/booking-form.service-choices.d.ts +13 -0
  47. package/dist/_dts/blocks/src/system/runtime/nodes/booking-form.state.d.ts +3 -3
  48. package/dist/_dts/blocks/src/system/runtime/nodes/booking-runtime-sources.d.ts +13 -1
  49. package/dist/_dts/blocks/src/system/runtime/nodes/event-registration/eventSourceRecovery.d.ts +1 -1
  50. package/dist/_dts/blocks/src/system/runtime/nodes/events/shared/eventCollectionContract.d.ts +3 -3
  51. package/dist/_dts/blocks/src/system/runtime/nodes/newsletter-form.submission.d.ts +20 -1
  52. package/dist/_dts/content-editor/src/ui/editorSnapshot.d.ts +2 -0
  53. package/dist/_dts/content-model/src/content-types/schema.d.ts +1 -1
  54. package/dist/_dts/core/src/appointment-service-categories.d.ts +108 -0
  55. package/dist/_dts/core/src/editor-state.d.ts +6 -0
  56. package/dist/_dts/core/src/index.d.ts +1 -0
  57. package/dist/_dts/core/src/public-profile.d.ts +9 -0
  58. package/dist/_dts/db/src/generated/supabase/database.types.d.ts +663 -241
  59. package/dist/_dts/editor-blocks/src/block-editor/types.d.ts +6 -0
  60. package/dist/_dts/editor-blocks/src/widgets/site-option-picker/loaders.d.ts +16 -1
  61. package/dist/_dts/editor-blocks/src/widgets/site-option-picker/types.d.ts +13 -0
  62. package/dist/_dts/editor-blocks/src/widgets/site-option-picker/utils.d.ts +29 -0
  63. package/dist/_dts/preview-next/src/client/blocks/BoundaryControl.d.ts +7 -2
  64. package/dist/_dts/preview-next/src/client/blocks/composer/mergeDrafts.d.ts +1 -1
  65. package/dist/_dts/preview-next/src/client/blocks/composer/types.d.ts +1 -0
  66. package/dist/_dts/preview-next/src/client/blocks/previewProjection/applyPreviewProjections.d.ts +1 -3
  67. package/dist/_dts/preview-next/src/client/blocks/previewProjection/runtimeContentDecoration.d.ts +2 -2
  68. package/dist/_dts/preview-next/src/client/blocks/previewProjection/types.d.ts +2 -2
  69. package/dist/_dts/preview-next/src/client/preview/PreviewEntryControllerProvider.d.ts +1 -0
  70. package/dist/_dts/sdk/src/client/runtimeCacheKeys.d.ts +8 -0
  71. package/dist/_dts/sdk/src/client/types.d.ts +1 -1
  72. package/dist/_dts/sdk/src/contracts/index.d.ts +1 -1
  73. package/dist/_dts/sdk/src/contracts/page.d.ts +7 -2
  74. package/dist/_dts/sdk/src/contracts/system-block-content.d.ts +5 -0
  75. package/dist/_dts/sdk/src/manifest/passes/pass1-fields.d.ts +2 -2
  76. package/dist/_dts/sdk/src/public-api/contracts.d.ts +6 -8
  77. package/dist/_dts/sdk/src/rendering/blocks-page-renderer.d.ts +2 -2
  78. package/dist/_dts/sdk/src/rendering/components/pageShared.d.ts +2 -2
  79. package/dist/_dts/sdk/src/rendering/helpers/loadContent.d.ts +1 -1
  80. package/dist/_dts/sdk/src/rendering/hooks/useContent.d.ts +1 -1
  81. package/dist/_dts/sdk/src/version.d.ts +1 -1
  82. package/dist/_dts/surfaces/src/index.d.ts +1 -0
  83. package/dist/_dts/theme-core/src/layout/boundaryCss.d.ts +3 -0
  84. package/dist/_dts/theme-core/src/site-styles/compositionBudget.d.ts +8 -0
  85. package/dist/_dts/theme-core/src/site-styles/contentTemplateRuntimeCompiler.d.ts +3 -2
  86. package/dist/_dts/theme-core/src/site-styles/designState.d.ts +1 -3
  87. package/dist/_dts/theme-core/src/site-styles/generatedDesignPipeline.d.ts +3 -0
  88. package/dist/_dts/theme-core/src/site-styles/index.d.ts +3 -0
  89. package/dist/_dts/theme-core/src/site-styles/joinTreatment.d.ts +132 -0
  90. package/dist/_dts/theme-core/src/site-styles/pageDesignEditorBoundaries.d.ts +31 -0
  91. package/dist/_dts/theme-core/src/site-styles/pageDesignEditorModel.d.ts +33 -29
  92. package/dist/_dts/theme-core/src/site-styles/pageDesignIntent.d.ts +4 -4
  93. package/dist/_dts/theme-core/src/site-styles/pageFlowPresets.d.ts +36 -0
  94. package/dist/_dts/theme-core/src/site-styles/previewCompiler.d.ts +4 -10
  95. package/dist/_dts/theme-core/src/site-styles/rawStyleFields.d.ts +17 -4
  96. package/dist/_dts/theme-core/src/site-styles/runtimeCompiler.d.ts +20 -74
  97. package/dist/_dts/theme-core/src/site-styles/sectionBoundaryComposition.d.ts +95 -0
  98. package/dist/_dts/theme-core/src/site-styles/sectionTransitions.d.ts +80 -518
  99. package/dist/_dts/theme-core/src/site-styles/siteStyleBlockPolicies.d.ts +9 -4
  100. package/dist/_dts/theme-core/src/site-styles/transitionCatalogue.d.ts +320 -0
  101. package/dist/_dts/theme-core/src/site-styles/types.d.ts +3 -18
  102. package/dist/client/{BookingConsentAgreement-DoAILrkN.mjs → BookingConsentAgreement-DlVOmpW4.mjs} +2 -2
  103. package/dist/client/{DiscountCodeDisclosure-X528hUTf.mjs → DiscountCodeDisclosure-T9q623PQ.mjs} +1 -1
  104. package/dist/client/{EventCombined.client-DSBVwq5m.mjs → EventCombined.client-DnsUeONl.mjs} +6 -6
  105. package/dist/client/{EventListing.client-DmFAX7Vb.mjs → EventListing.client-CNBFqJS4.mjs} +2 -2
  106. package/dist/client/{LeafletStaticMap-BAqXdfhq.mjs → LeafletStaticMap-C7higg52.mjs} +1 -1
  107. package/dist/client/{ThemedButton-BwNFVwi4.mjs → ThemedButton-LAJTNrS8.mjs} +1 -1
  108. package/dist/client/{accordion-DRhMdkbd.mjs → accordion-BcNF9TjX.mjs} +1 -1
  109. package/dist/client/{bookingForm-iJ_nCsNF.mjs → bookingForm-BUaQ3S03.mjs} +142 -50
  110. package/dist/client/bookings.mjs +191 -64
  111. package/dist/client/{carousel-D8zuffZr.mjs → carousel-CTdF6e0V.mjs} +1 -1
  112. package/dist/client/{cart-DeMGJViN.mjs → cart-pGtyf_XU.mjs} +3 -3
  113. package/dist/client/{checkout-DXc06Km2.mjs → checkout-Da9WSn7Y.mjs} +3 -3
  114. package/dist/client/client.mjs +1630 -816
  115. package/dist/client/{context-CDLCfDep.mjs → context-BFeY_Wbm.mjs} +1 -1
  116. package/dist/client/{dates-ClFx7Epy.mjs → dates-BhwVSxDg.mjs} +2 -2
  117. package/dist/client/{eventCalendar-BaGpnOGN.mjs → eventCalendar-BAtdnR4s.mjs} +9 -9
  118. package/dist/client/{eventCombined-ywONOx2m.mjs → eventCombined-RksA3tRC.mjs} +4 -4
  119. package/dist/client/{eventDetails-B2LlOTYY.mjs → eventDetails-BB9hB4wR.mjs} +4 -4
  120. package/dist/client/{eventListing-CMgxWpqP.mjs → eventListing-BpJBkviM.mjs} +4 -4
  121. package/dist/client/{eventRegistration-BarLDNHR.mjs → eventRegistration-B18jFq_o.mjs} +8 -8
  122. package/dist/client/{form-BjqKaBJ7.mjs → form-Dodt8Y8t.mjs} +3 -3
  123. package/dist/client/{headerSection-CP4XDwz1.mjs → headerSection-B0qj9ttg.mjs} +3 -3
  124. package/dist/client/hooks.mjs +550 -99
  125. package/dist/client/{locationMap-C5gW-d-w.mjs → locationMap-gn-iMk7a.mjs} +3 -3
  126. package/dist/client/{newsletterForm-afXlVSA0.mjs → newsletterForm-oByLdFkr.mjs} +26 -5
  127. package/dist/client/{pricing-Bl1CAl28.mjs → pricing-BOU0_Hai.mjs} +1 -1
  128. package/dist/client/{productDetail-CvQ3jWQe.mjs → productDetail-D9v1zH2j.mjs} +3 -3
  129. package/dist/client/{productList-U874PGO7.mjs → productList-D-mItx1n.mjs} +3 -3
  130. package/dist/client/{propsDecoder-DPXtCZWP.mjs → propsDecoder-C3TP_z4x.mjs} +72 -33
  131. package/dist/client/rendering/client.mjs +900 -266
  132. package/dist/client/rendering/islands.mjs +17 -17
  133. package/dist/client/rendering.mjs +1637 -788
  134. package/dist/client/{routeIslandApiConfig-NGYiUWXu.mjs → routeIslandApiConfig-DzN1W0sq.mjs} +1 -1
  135. package/dist/client/{scrollToBlock-0-C3DVhK.mjs → scrollToBlock-CWs8EIdo.mjs} +1 -1
  136. package/dist/client/{shop-BXjXhM9P.mjs → shop-Dufw7N7o.mjs} +7 -7
  137. package/dist/client/{shop-commerce-BZ6UlWJ7.mjs → shop-commerce-gklw_hLF.mjs} +6 -6
  138. package/dist/client/{shop-commerce-store-DlSBXb3D.mjs → shop-commerce-store-Sf1eyTaZ.mjs} +1 -1
  139. package/dist/client/{shopShared-kkEOiLPA.mjs → shopShared-B5nyA41S.mjs} +4 -4
  140. package/dist/client/{useEventFilters-zvnnE1ro.mjs → useEventFilters-CLL829vy.mjs} +6 -6
  141. package/dist/preview-next/before-render.mjs +147 -77
  142. package/dist/preview-next/client/runtime.mjs +4 -4
  143. package/dist/preview-next/keepAlive.mjs +147 -77
  144. package/dist/preview-next/middleware.mjs +147 -77
  145. package/dist/{previewAuthStore-JA6-I_sL.mjs → previewAuthStore-BxAFlu-j.mjs} +147 -77
  146. package/dist/{sdk-runtime-DFJlQt3q.mjs → sdk-runtime-D0uZFev7.mjs} +2 -2
  147. package/dist/{separator-o8GHb1xh.mjs → separator-EvdCAn4V.mjs} +1 -1
  148. package/dist/server/components.mjs +1727 -991
  149. package/dist/server/config-validation.mjs +537 -97
  150. package/dist/server/config.mjs +537 -97
  151. package/dist/server/data.mjs +549 -98
  152. package/dist/server/index.mjs +159 -81
  153. package/dist/server/next.mjs +1460 -748
  154. package/dist/server/page-converter.mjs +384 -54
  155. package/dist/server/prebuild.mjs +1 -1
  156. package/dist/server/rendering/server.mjs +1712 -973
  157. package/dist/server/rendering.mjs +1748 -1001
  158. package/dist/server/routing.mjs +624 -131
  159. package/dist/server/server.mjs +554 -138
  160. package/dist/server/theme-bridge.mjs +1192 -27
  161. package/dist/server/theme.mjs +6 -4
  162. package/package.json +2 -1
@@ -6705,6 +6705,15 @@ function asSiteStyleId(value) {
6705
6705
  function asDesignSystemTemplateId(value) {
6706
6706
  return brandNonEmptyString(value, "DesignSystemTemplateId");
6707
6707
  }
6708
+ function toNonEmptyReadonlyArray(values) {
6709
+ const [first, ...rest] = values;
6710
+ return first === void 0 ? null : [first, ...rest];
6711
+ }
6712
+ function requireNonEmptyReadonlyArray(values, message = "Expected a non-empty array.") {
6713
+ const result = toNonEmptyReadonlyArray(values);
6714
+ if (!result) throw new Error(message);
6715
+ return result;
6716
+ }
6708
6717
  function makeBoundaryId(previousBlockId, nextBlockId) {
6709
6718
  return asDesignBoundaryId(`boundary:${encodeURIComponent(previousBlockId)}:${encodeURIComponent(nextBlockId)}`);
6710
6719
  }
@@ -6907,16 +6916,18 @@ const themeV2RuntimeStyleFieldNames = [
6907
6916
  "_frameStyles",
6908
6917
  "_sectionStyles",
6909
6918
  "_containerStyles",
6910
- "_cardStyles",
6911
- "_transitionStyles",
6912
- "styleGroup"
6919
+ "_cardStyles"
6913
6920
  ];
6914
6921
  const themeV2BlockSpecificRawStyleFieldNames = [
6915
6922
  "_contentCardStyles",
6916
6923
  "_heroLayoutStyles",
6917
6924
  "_textCardStyles"
6918
6925
  ];
6919
- const themeV2NormalEditorRawStyleFieldNames = [...themeV2RuntimeStyleFieldNames, ...themeV2BlockSpecificRawStyleFieldNames];
6926
+ const themeV2NormalEditorRawStyleFieldNames = [
6927
+ ...themeV2RuntimeStyleFieldNames,
6928
+ ...themeV2BlockSpecificRawStyleFieldNames,
6929
+ "styleGroup"
6930
+ ];
6920
6931
  new Set(themeV2NormalEditorRawStyleFieldNames);
6921
6932
  [...themeV2RuntimeStyleFieldNames, ...themeV2BlockSpecificRawStyleFieldNames];
6922
6933
  const pageDesignEditorBackgroundOverrideOwner = "page-design-editor";
@@ -8550,6 +8561,75 @@ const calendarWindowPageSchema = z.discriminatedUnion("kind", [z.object({
8550
8561
  nextCursor: calendarSourceCursorSchema
8551
8562
  })]);
8552
8563
  //#endregion
8564
+ //#region ../api/src/defineEndpointDefinitions.ts
8565
+ /**
8566
+ * Validates extracted endpoint descriptors while preserving each literal path,
8567
+ * method, and parameter contract for the typed URL builders.
8568
+ */
8569
+ function defineEndpointDefinitions(definitions) {
8570
+ return definitions;
8571
+ }
8572
+ //#endregion
8573
+ //#region ../api/src/publicNewsletterEndpointDefinitions.ts
8574
+ const PUBLIC_NEWSLETTER_ENDPOINT_DEFINITIONS = defineEndpointDefinitions({
8575
+ subscribeNewsletter: {
8576
+ path: "/public/sites/{siteId}/newsletter/subscribe",
8577
+ method: "POST",
8578
+ tags: ["public-newsletter-{siteId}"],
8579
+ auth: "public",
8580
+ responseKind: "json"
8581
+ },
8582
+ confirmNewsletter: {
8583
+ path: "/public/sites/{siteId}/newsletter/confirm/{token}",
8584
+ method: "GET",
8585
+ tags: ["public-newsletter-{siteId}"],
8586
+ auth: "public",
8587
+ responseKind: "text"
8588
+ },
8589
+ unsubscribeNewsletter: {
8590
+ path: "/public/sites/{siteId}/newsletter/unsubscribe/{token}",
8591
+ method: "GET",
8592
+ tags: ["public-newsletter-{siteId}"],
8593
+ auth: "public",
8594
+ responseKind: "text"
8595
+ },
8596
+ unsubscribeNewsletterPost: {
8597
+ path: "/public/sites/{siteId}/newsletter/unsubscribe/{token}",
8598
+ method: "POST",
8599
+ tags: ["public-newsletter-{siteId}"],
8600
+ auth: "public",
8601
+ responseKind: "text"
8602
+ },
8603
+ confirmNewsletterPost: {
8604
+ path: "/public/sites/{siteId}/newsletter/confirm/{token}",
8605
+ method: "POST",
8606
+ tags: ["public-newsletter-{siteId}"],
8607
+ auth: "public",
8608
+ responseKind: "text"
8609
+ },
8610
+ getNewsletterPreferences: {
8611
+ path: "/public/sites/{siteId}/newsletter/preferences/{token}",
8612
+ method: "GET",
8613
+ tags: ["public-newsletter-{siteId}"],
8614
+ auth: "public",
8615
+ responseKind: "text"
8616
+ },
8617
+ saveNewsletterPreferences: {
8618
+ path: "/public/sites/{siteId}/newsletter/preferences/{token}",
8619
+ method: "POST",
8620
+ tags: ["public-newsletter-{siteId}"],
8621
+ auth: "public",
8622
+ responseKind: "text"
8623
+ },
8624
+ getNewsletterArchive: {
8625
+ path: "/public/sites/{siteId}/newsletter/archive/{token}",
8626
+ method: "GET",
8627
+ tags: ["public-newsletter-{siteId}"],
8628
+ auth: "public",
8629
+ responseKind: "text"
8630
+ }
8631
+ });
8632
+ //#endregion
8553
8633
  //#region ../api/src/apiEndpointTypes.ts
8554
8634
  function allowedDemoMutationPolicy() {
8555
8635
  return {
@@ -8641,17 +8721,85 @@ const SDK_ENTRY_READ_ENDPOINTS = {
8641
8721
  }
8642
8722
  };
8643
8723
  //#endregion
8644
- //#region ../api/src/defineEndpointDefinitions.ts
8645
- /**
8646
- * Validates extracted endpoint descriptors while preserving each literal path,
8647
- * method, and parameter contract for the typed URL builders.
8648
- */
8649
- function defineEndpointDefinitions(definitions) {
8650
- return definitions;
8651
- }
8652
- //#endregion
8653
8724
  //#region ../api/src/appointmentEndpointDefinitions.ts
8654
8725
  const APPOINTMENT_ENDPOINT_DEFINITIONS = defineEndpointDefinitions({
8726
+ ...defineEndpointDefinitions({
8727
+ listGroupedAppointmentServices: {
8728
+ path: "/sites/{siteId}/bookings/services/grouped",
8729
+ method: "GET",
8730
+ auth: "user",
8731
+ responseKind: "json",
8732
+ errors: ["server:internal_error"]
8733
+ },
8734
+ reorderAppointmentServices: {
8735
+ path: "/sites/{siteId}/bookings/services/order",
8736
+ method: "PUT",
8737
+ auth: "user",
8738
+ responseKind: "json",
8739
+ errors: [
8740
+ "validation:invalid_input",
8741
+ "auth:forbidden",
8742
+ "resource:not_found",
8743
+ "resource:conflict",
8744
+ "server:internal_error"
8745
+ ]
8746
+ },
8747
+ listAppointmentServiceCategories: {
8748
+ path: "/sites/{siteId}/bookings/service-categories",
8749
+ method: "GET",
8750
+ auth: "user",
8751
+ responseKind: "json",
8752
+ errors: ["server:internal_error"]
8753
+ },
8754
+ createAppointmentServiceCategory: {
8755
+ path: "/sites/{siteId}/bookings/service-categories",
8756
+ method: "POST",
8757
+ auth: "user",
8758
+ responseKind: "json",
8759
+ errors: [
8760
+ "validation:invalid_input",
8761
+ "auth:forbidden",
8762
+ "resource:conflict",
8763
+ "server:internal_error"
8764
+ ]
8765
+ },
8766
+ updateAppointmentServiceCategory: {
8767
+ path: "/sites/{siteId}/bookings/service-categories/{categoryId}",
8768
+ method: "PUT",
8769
+ auth: "user",
8770
+ responseKind: "json",
8771
+ errors: [
8772
+ "validation:invalid_input",
8773
+ "auth:forbidden",
8774
+ "resource:not_found",
8775
+ "resource:conflict",
8776
+ "server:internal_error"
8777
+ ]
8778
+ },
8779
+ deleteAppointmentServiceCategory: {
8780
+ path: "/sites/{siteId}/bookings/service-categories/{categoryId}",
8781
+ method: "DELETE",
8782
+ auth: "user",
8783
+ responseKind: "json",
8784
+ errors: [
8785
+ "auth:forbidden",
8786
+ "resource:not_found",
8787
+ "server:internal_error"
8788
+ ]
8789
+ },
8790
+ reorderAppointmentServiceCategories: {
8791
+ path: "/sites/{siteId}/bookings/service-categories/order",
8792
+ method: "PUT",
8793
+ auth: "user",
8794
+ responseKind: "json",
8795
+ errors: [
8796
+ "validation:invalid_input",
8797
+ "auth:forbidden",
8798
+ "resource:conflict",
8799
+ "server:internal_error"
8800
+ ]
8801
+ }
8802
+ }),
8655
8803
  listAppointmentResources: {
8656
8804
  path: "/sites/{siteId}/bookings/resources",
8657
8805
  method: "GET",
@@ -9799,39 +9947,6 @@ const NEWSLETTER_ENDPOINT_DEFINITIONS = defineEndpointDefinitions({
9799
9947
  auth: "user",
9800
9948
  responseKind: "json",
9801
9949
  demoMutation: DEMO_MUTATION_BLOCKED_HIDDEN
9802
- },
9803
- listNewsletterSendJobs: {
9804
- path: "/sites/{siteId}/newsletter/jobs",
9805
- method: "GET",
9806
- tags: [TAG_TEMPLATES.site, TAG_TEMPLATES.siteNewsletter],
9807
- auth: "user",
9808
- responseKind: "json"
9809
- },
9810
- retryNewsletterSendJob: {
9811
- path: "/sites/{siteId}/newsletter/jobs/{jobId}/retry",
9812
- method: "POST",
9813
- errors: [
9814
- "validation:invalid_input",
9815
- "resource:not_found",
9816
- "auth:forbidden",
9817
- "server:internal_error"
9818
- ],
9819
- tags: [TAG_TEMPLATES.site, TAG_TEMPLATES.siteNewsletter],
9820
- auth: "user",
9821
- responseKind: "json"
9822
- },
9823
- cancelNewsletterSendJob: {
9824
- path: "/sites/{siteId}/newsletter/jobs/{jobId}/cancel",
9825
- method: "POST",
9826
- errors: [
9827
- "validation:invalid_input",
9828
- "resource:not_found",
9829
- "auth:forbidden",
9830
- "server:internal_error"
9831
- ],
9832
- tags: [TAG_TEMPLATES.site, TAG_TEMPLATES.siteNewsletter],
9833
- auth: "user",
9834
- responseKind: "json"
9835
9950
  }
9836
9951
  });
9837
9952
  //#endregion
@@ -10597,6 +10712,7 @@ const BILLING_ENDPOINT_DEFINITIONS = defineEndpointDefinitions({
10597
10712
  }
10598
10713
  });
10599
10714
  ({
10715
+ ...PUBLIC_NEWSLETTER_ENDPOINT_DEFINITIONS,
10600
10716
  ...ACCOUNT_ENDPOINT_DEFINITIONS,
10601
10717
  ...PUBLIC_ONBOARDING_ATTEMPT_ENDPOINT_DEFINITIONS,
10602
10718
  ...PUBLIC_EVENT_ENDPOINT_DEFINITIONS,
@@ -12957,11 +13073,260 @@ function cardRoleFromLegacyVocabulary(value) {
12957
13073
  */
12958
13074
  const cardRoleWithLegacyAliasSchema = z.preprocess((value) => cardRoleFromLegacyVocabulary(value) ?? value, cardRoleSchema);
12959
13075
  //#endregion
12960
- //#region ../theme-core/src/site-styles/compilationPlan.ts
12961
- const defaultHeaderBrandPreferences = {
12962
- brandDisplay: "auto",
12963
- logoSize: "auto"
12964
- };
13076
+ //#region ../theme-core/src/site-styles/transitionCatalogue.ts
13077
+ /**
13078
+ * Family order for pickers. Entries below are listed family by family in this
13079
+ * same order, so the flat option list and the grouped families agree.
13080
+ */
13081
+ const transitionCatalogueFamilies = [
13082
+ {
13083
+ id: "gradient",
13084
+ label: "Gradient"
13085
+ },
13086
+ {
13087
+ id: "wave",
13088
+ label: "Wave"
13089
+ },
13090
+ {
13091
+ id: "angle",
13092
+ label: "Angle"
13093
+ }
13094
+ ];
13095
+ const mediumHeight = "6rem + 2px";
13096
+ const compactHeight = "4.5rem + 2px";
13097
+ const largeHeight = "7rem + 2px";
13098
+ /**
13099
+ * The single source of transition vocabulary. Order is significant: it is the
13100
+ * order of `boundaryOptions` (after `none`) and of each family's variants,
13101
+ * which persisted pins, page-flow presets and the editor picker all rely on.
13102
+ *
13103
+ * Shapes match what `generateLayoutCss` draws today. Structured
13104
+ * amplitude/frequency treatments (issue 826) extend this list later.
13105
+ */
13106
+ const transitionCatalogueEntries = defineExactCatalog()([
13107
+ {
13108
+ intent: "soft-fade-short",
13109
+ optionId: asBoundaryOptionId("break:soft"),
13110
+ family: "gradient",
13111
+ variantId: "soft",
13112
+ label: "Soft",
13113
+ variantLabel: "Soft",
13114
+ treatment: {
13115
+ kind: "soft-fade",
13116
+ height: "medium",
13117
+ curve: "soft"
13118
+ },
13119
+ size: "medium",
13120
+ heightExpression: mediumHeight,
13121
+ shape: { kind: "fade" }
13122
+ },
13123
+ {
13124
+ intent: "soft-fade-long",
13125
+ optionId: asBoundaryOptionId("break:spacious"),
13126
+ family: "gradient",
13127
+ variantId: "spacious",
13128
+ label: "Spacious",
13129
+ variantLabel: "Spacious",
13130
+ treatment: {
13131
+ kind: "soft-fade",
13132
+ height: "large",
13133
+ curve: "spacious"
13134
+ },
13135
+ size: "spacious",
13136
+ heightExpression: "10rem",
13137
+ shape: { kind: "fade" }
13138
+ },
13139
+ {
13140
+ intent: "soft-fade-expansive",
13141
+ optionId: asBoundaryOptionId("break:expansive"),
13142
+ family: "gradient",
13143
+ variantId: "expansive",
13144
+ label: "Expansive",
13145
+ variantLabel: "Expansive",
13146
+ treatment: {
13147
+ kind: "soft-fade",
13148
+ height: "expansive",
13149
+ curve: "expansive"
13150
+ },
13151
+ size: "expansive",
13152
+ heightExpression: "14rem",
13153
+ shape: { kind: "fade" }
13154
+ },
13155
+ {
13156
+ intent: "wave-edge-balanced",
13157
+ optionId: asBoundaryOptionId("break:wave-balanced"),
13158
+ family: "wave",
13159
+ variantId: "balanced",
13160
+ label: "Balanced wave",
13161
+ variantLabel: "Balanced",
13162
+ treatment: {
13163
+ kind: "wave-edge",
13164
+ height: "medium",
13165
+ amplitude: "balanced",
13166
+ rhythm: "double",
13167
+ symmetry: "symmetrical"
13168
+ },
13169
+ size: "medium",
13170
+ heightExpression: mediumHeight,
13171
+ shape: {
13172
+ kind: "wave",
13173
+ mask: "balanced"
13174
+ }
13175
+ },
13176
+ {
13177
+ intent: "wave-edge",
13178
+ optionId: asBoundaryOptionId("break:wave"),
13179
+ family: "wave",
13180
+ variantId: "classic",
13181
+ label: "Classic wave",
13182
+ variantLabel: "Classic",
13183
+ treatment: {
13184
+ kind: "wave-edge",
13185
+ height: "medium",
13186
+ amplitude: "balanced",
13187
+ rhythm: "double",
13188
+ symmetry: "asymmetrical"
13189
+ },
13190
+ size: "medium",
13191
+ heightExpression: mediumHeight,
13192
+ shape: {
13193
+ kind: "wave",
13194
+ mask: "classic"
13195
+ }
13196
+ },
13197
+ {
13198
+ intent: "wave-edge-gentle",
13199
+ optionId: asBoundaryOptionId("break:wave-gentle"),
13200
+ family: "wave",
13201
+ variantId: "gentle",
13202
+ label: "Gentle wave",
13203
+ variantLabel: "Gentle",
13204
+ treatment: {
13205
+ kind: "wave-edge",
13206
+ height: "compact",
13207
+ amplitude: "subtle",
13208
+ rhythm: "single",
13209
+ symmetry: "symmetrical"
13210
+ },
13211
+ size: "compact",
13212
+ heightExpression: compactHeight,
13213
+ shape: {
13214
+ kind: "wave",
13215
+ mask: "gentle"
13216
+ }
13217
+ },
13218
+ {
13219
+ intent: "wave-edge-bold",
13220
+ optionId: asBoundaryOptionId("break:wave-bold"),
13221
+ family: "wave",
13222
+ variantId: "bold",
13223
+ label: "Bold wave",
13224
+ variantLabel: "Bold",
13225
+ treatment: {
13226
+ kind: "wave-edge",
13227
+ height: "large",
13228
+ amplitude: "bold",
13229
+ rhythm: "double",
13230
+ symmetry: "symmetrical"
13231
+ },
13232
+ size: "large",
13233
+ heightExpression: largeHeight,
13234
+ shape: {
13235
+ kind: "wave",
13236
+ mask: "bold"
13237
+ }
13238
+ },
13239
+ {
13240
+ intent: "wave-edge-drift",
13241
+ optionId: asBoundaryOptionId("break:wave-drift"),
13242
+ family: "wave",
13243
+ variantId: "drift",
13244
+ label: "Drift wave",
13245
+ variantLabel: "Drift",
13246
+ treatment: {
13247
+ kind: "wave-edge",
13248
+ height: "medium",
13249
+ amplitude: "balanced",
13250
+ rhythm: "double",
13251
+ symmetry: "drift"
13252
+ },
13253
+ size: "medium",
13254
+ heightExpression: mediumHeight,
13255
+ shape: {
13256
+ kind: "wave",
13257
+ mask: "drift"
13258
+ }
13259
+ },
13260
+ {
13261
+ intent: "angle-edge-subtle",
13262
+ optionId: asBoundaryOptionId("break:angle-subtle"),
13263
+ family: "angle",
13264
+ variantId: "subtle",
13265
+ label: "Subtle angle",
13266
+ variantLabel: "Subtle",
13267
+ treatment: {
13268
+ kind: "angle-edge",
13269
+ height: "compact",
13270
+ slope: "subtle",
13271
+ direction: "forward"
13272
+ },
13273
+ size: "compact",
13274
+ heightExpression: compactHeight,
13275
+ shape: {
13276
+ kind: "angle",
13277
+ polygon: {
13278
+ startTopPercent: 34,
13279
+ endTopPercent: 18
13280
+ }
13281
+ }
13282
+ },
13283
+ {
13284
+ intent: "angle-edge",
13285
+ optionId: asBoundaryOptionId("break:angle-balanced"),
13286
+ family: "angle",
13287
+ variantId: "balanced",
13288
+ label: "Balanced angle",
13289
+ variantLabel: "Balanced",
13290
+ treatment: {
13291
+ kind: "angle-edge",
13292
+ height: "medium",
13293
+ slope: "balanced",
13294
+ direction: "forward"
13295
+ },
13296
+ size: "medium",
13297
+ heightExpression: mediumHeight,
13298
+ shape: {
13299
+ kind: "angle",
13300
+ polygon: {
13301
+ startTopPercent: 42,
13302
+ endTopPercent: 8
13303
+ }
13304
+ }
13305
+ },
13306
+ {
13307
+ intent: "angle-edge-steep",
13308
+ optionId: asBoundaryOptionId("break:angle-steep"),
13309
+ family: "angle",
13310
+ variantId: "steep",
13311
+ label: "Steep angle",
13312
+ variantLabel: "Steep",
13313
+ treatment: {
13314
+ kind: "angle-edge",
13315
+ height: "large",
13316
+ slope: "steep",
13317
+ direction: "forward"
13318
+ },
13319
+ size: "large",
13320
+ heightExpression: largeHeight,
13321
+ shape: {
13322
+ kind: "angle",
13323
+ polygon: {
13324
+ startTopPercent: 54,
13325
+ endTopPercent: 0
13326
+ }
13327
+ }
13328
+ }
13329
+ ]);
12965
13330
  //#endregion
12966
13331
  //#region ../theme-core/src/site-styles/sectionTransitions.ts
12967
13332
  function boundaryRuntimeMetrics(family, size, heightExpression) {
@@ -12972,42 +13337,106 @@ function boundaryRuntimeMetrics(family, size, heightExpression) {
12972
13337
  reserveCss: `calc((${heightExpression}) / 2)`
12973
13338
  };
12974
13339
  }
12975
- boundaryRuntimeMetrics("gradient", "medium", "6rem + 2px"), boundaryRuntimeMetrics("gradient", "spacious", "10rem"), boundaryRuntimeMetrics("gradient", "expansive", "14rem"), boundaryRuntimeMetrics("wave", "medium", "6rem + 2px"), boundaryRuntimeMetrics("wave", "medium", "6rem + 2px"), boundaryRuntimeMetrics("wave", "compact", "4.5rem + 2px"), boundaryRuntimeMetrics("wave", "large", "7rem + 2px"), boundaryRuntimeMetrics("wave", "medium", "6rem + 2px"), boundaryRuntimeMetrics("angle", "medium", "6rem + 2px"), boundaryRuntimeMetrics("angle", "compact", "4.5rem + 2px"), boundaryRuntimeMetrics("angle", "large", "7rem + 2px");
13340
+ new Map(transitionCatalogueEntries.map((entry) => [entry.intent, entry]));
13341
+ new Map(transitionCatalogueEntries.map((entry) => [entry.intent, boundaryRuntimeMetrics(entry.family, entry.size, entry.heightExpression)]));
13342
+ /**
13343
+ * The catalogue's compile-time coverage check guarantees an entry per
13344
+ * decorative intent, so a miss here is a broken invariant, not bad input.
13345
+ */
13346
+ function requireCatalogueValue(values, intent) {
13347
+ const value = values.get(intent);
13348
+ if (value === void 0) throw new Error(`Transition catalogue has no entry for ${intent}`);
13349
+ return value;
13350
+ }
12976
13351
  const noneBoundaryOption = {
12977
13352
  id: asBoundaryOptionId("break:none"),
12978
13353
  label: "None",
12979
13354
  transitionAfter: "none",
12980
13355
  treatment: { kind: "none" }
12981
13356
  };
12982
- const softBoundaryOption = {
12983
- id: asBoundaryOptionId("break:soft"),
12984
- label: "Soft",
12985
- transitionAfter: "soft-fade-short",
12986
- treatment: {
12987
- kind: "soft-fade",
12988
- height: "medium",
12989
- curve: "soft"
12990
- }
13357
+ const boundaryOptionByIntent = new Map(transitionCatalogueEntries.map((entry) => [entry.intent, {
13358
+ id: entry.optionId,
13359
+ label: entry.label,
13360
+ transitionAfter: entry.intent,
13361
+ treatment: entry.treatment
13362
+ }]));
13363
+ function boundaryOptionForTransitionIntent(intent) {
13364
+ return requireCatalogueValue(boundaryOptionByIntent, intent);
13365
+ }
13366
+ const softBoundaryOption = boundaryOptionForTransitionIntent("soft-fade-short");
13367
+ const spaciousBoundaryOption = boundaryOptionForTransitionIntent("soft-fade-long");
13368
+ boundaryOptionForTransitionIntent("soft-fade-expansive");
13369
+ boundaryOptionForTransitionIntent("wave-edge");
13370
+ boundaryOptionForTransitionIntent("wave-edge-balanced");
13371
+ boundaryOptionForTransitionIntent("wave-edge-gentle");
13372
+ boundaryOptionForTransitionIntent("wave-edge-bold");
13373
+ boundaryOptionForTransitionIntent("wave-edge-drift");
13374
+ boundaryOptionForTransitionIntent("angle-edge-subtle");
13375
+ boundaryOptionForTransitionIntent("angle-edge");
13376
+ boundaryOptionForTransitionIntent("angle-edge-steep");
13377
+ /**
13378
+ * Must remain non-empty; downstream code indexes `[0]` as the documented default.
13379
+ */
13380
+ const boundaryOptions = [noneBoundaryOption, ...transitionCatalogueEntries.map((entry) => boundaryOptionForTransitionIntent(entry.intent))];
13381
+ const noneTransitionVariant = {
13382
+ familyId: "none",
13383
+ variantId: "none",
13384
+ label: "None",
13385
+ boundaryOption: noneBoundaryOption
12991
13386
  };
12992
- const spaciousBoundaryOption = {
12993
- id: asBoundaryOptionId("break:spacious"),
12994
- label: "Spacious",
12995
- transitionAfter: "soft-fade-long",
12996
- treatment: {
12997
- kind: "soft-fade",
12998
- height: "large",
12999
- curve: "spacious"
13000
- }
13387
+ function transitionVariantForEntry(entry) {
13388
+ return {
13389
+ familyId: entry.family,
13390
+ variantId: entry.variantId,
13391
+ label: entry.variantLabel,
13392
+ boundaryOption: boundaryOptionForTransitionIntent(entry.intent)
13393
+ };
13394
+ }
13395
+ const sectionTransitionFamilies = [{
13396
+ id: "none",
13397
+ label: "None",
13398
+ variants: [noneTransitionVariant]
13399
+ }, ...transitionCatalogueFamilies.map((family) => ({
13400
+ id: family.id,
13401
+ label: family.label,
13402
+ variants: requireNonEmptyReadonlyArray(transitionCatalogueEntries.filter((entry) => entry.family === family.id).map(transitionVariantForEntry), `Transition family ${family.id} has no catalogue entries.`)
13403
+ }))];
13404
+ new Map(boundaryOptions.map((option) => [option.id, option]));
13405
+ new Map(boundaryOptions.map((option) => [stableTreatmentKey(option.treatment), option]));
13406
+ new Map(sectionTransitionFamilies.flatMap((family) => family.variants.map((variant) => [variant.boundaryOption.id, variant])));
13407
+ new Map(sectionTransitionFamilies.map((family) => [family.id, family]));
13408
+ function stableTreatmentKey(treatment) {
13409
+ switch (treatment.kind) {
13410
+ case "none": return "none";
13411
+ case "soft-fade": return `${treatment.kind}:${treatment.height}:${treatment.curve}`;
13412
+ case "wave-edge": return [
13413
+ treatment.kind,
13414
+ treatment.height,
13415
+ treatment.amplitude,
13416
+ treatment.rhythm,
13417
+ treatment.symmetry
13418
+ ].join(":");
13419
+ case "angle-edge": return [
13420
+ treatment.kind,
13421
+ treatment.height,
13422
+ treatment.slope,
13423
+ treatment.direction
13424
+ ].join(":");
13425
+ case "legacy-unsupported": return `${treatment.kind}:${treatment.boundaryOptionId}`;
13426
+ }
13427
+ }
13428
+ requireThemeColorToken$1("background");
13429
+ function requireThemeColorToken$1(value) {
13430
+ const token = parseThemeColorToken(value);
13431
+ if (!token) throw new Error(`Expected a theme color token. Received: ${value}`);
13432
+ return token;
13433
+ }
13434
+ //#endregion
13435
+ //#region ../theme-core/src/site-styles/compilationPlan.ts
13436
+ const defaultHeaderBrandPreferences = {
13437
+ brandDisplay: "auto",
13438
+ logoSize: "auto"
13001
13439
  };
13002
- asBoundaryOptionId("break:expansive");
13003
- asBoundaryOptionId("break:wave");
13004
- asBoundaryOptionId("break:wave-balanced");
13005
- asBoundaryOptionId("break:wave-gentle");
13006
- asBoundaryOptionId("break:wave-bold");
13007
- asBoundaryOptionId("break:wave-drift");
13008
- asBoundaryOptionId("break:angle-subtle");
13009
- asBoundaryOptionId("break:angle-balanced");
13010
- asBoundaryOptionId("break:angle-steep");
13011
13440
  asBoundaryOptionId("break:unknown");
13012
13441
  const pageDesignUserPinnedAppearanceChoiceSchema = z.object({
13013
13442
  kind: z.literal("user-pinned"),
@@ -13134,14 +13563,11 @@ function validateUniquePageDesignPins(intent, ctx) {
13134
13563
  label: "block Look pin"
13135
13564
  });
13136
13565
  addDuplicateStringIssues(ctx, {
13137
- values: intent.boundaryPins.map((pin) => boundaryKey(pin.previousBlockId, pin.nextBlockId)),
13566
+ values: intent.boundaryPins.map((pin) => makeBoundaryId(pin.previousBlockId, pin.nextBlockId)),
13138
13567
  path: ["boundaryPins"],
13139
13568
  label: "boundary pin"
13140
13569
  });
13141
13570
  }
13142
- function boundaryKey(previousBlockId, nextBlockId) {
13143
- return makeBoundaryId(previousBlockId, nextBlockId);
13144
- }
13145
13571
  //#endregion
13146
13572
  //#region ../theme-core/src/accordions/siteStyleDefaults.ts
13147
13573
  /**
@@ -14769,6 +15195,13 @@ z.object({
14769
15195
  fields: nonEmptyRuntimeStyleFieldNamesSchema,
14770
15196
  authority: styleAuthoritySchema
14771
15197
  }).strict();
15198
+ asPageFlowPresetId("flow:quiet"), noneBoundaryOption.id, asPageFlowPresetId("flow:balanced"), softBoundaryOption.id, asPageFlowPresetId("flow:expressive"), spaciousBoundaryOption.id;
15199
+ asPageFlowPresetId("generated-default");
15200
+ asSiteStyleId("site-style:south-west-twerk-school");
15201
+ asAppearancePresetId("hero-brand-scrim-fixed-frame");
15202
+ asLayoutVariantKey("classic");
15203
+ asLayoutVariantKey("micro");
15204
+ asBoundaryOptionId("break:wave");
14772
15205
  //#endregion
14773
15206
  //#region ../theme-core/src/site-styles/runtimeCompiler.ts
14774
15207
  function defineSectionForegroundRuntimeTokens(input) {
@@ -14792,7 +15225,7 @@ function defineComponentRuntimeRules(rules) {
14792
15225
  }
14793
15226
  /**
14794
15227
  * Default design rules translate semantic page-level choices into the current
14795
- * runtime's section background and transition style-group vocabulary.
15228
+ * runtime's section background vocabulary.
14796
15229
  */
14797
15230
  const defaultDesignRuntimeRules = defineDesignRuntimeRules({
14798
15231
  sectionSurfaces: {
@@ -14827,8 +15260,7 @@ const defaultDesignRuntimeRules = defineDesignRuntimeRules({
14827
15260
  color: "surface",
14828
15261
  opacity: .88
14829
15262
  }
14830
- },
14831
- transitionClassName: (transition, fromSurface, toSurface) => transition === "none" ? null : `site-style-transition-${transition}-from-${fromSurface}-to-${toSurface}`
15263
+ }
14832
15264
  });
14833
15265
  /**
14834
15266
  * Default component rules translate frame and item-surface semantics into the
@@ -16563,19 +16995,11 @@ const curatedSiteStyles = [
16563
16995
  })
16564
16996
  ];
16565
16997
  new Map(curatedSiteStyles.map((style) => [style.id, style]));
16566
- asPageFlowPresetId("generated-default");
16567
- asSiteStyleId("site-style:south-west-twerk-school");
16568
- asAppearancePresetId("hero-brand-scrim-fixed-frame");
16569
- asLayoutVariantKey("classic");
16570
- asLayoutVariantKey("micro");
16571
- asBoundaryOptionId("break:wave");
16572
- asPageFlowPresetId("flow:quiet"), noneBoundaryOption.id, asPageFlowPresetId("flow:balanced"), softBoundaryOption.id, asPageFlowPresetId("flow:expressive"), spaciousBoundaryOption.id;
16573
16998
  //#endregion
16574
16999
  //#region ../theme-core/src/site-styles/resolver.ts
16575
17000
  const blockDesignFallback = {
16576
17001
  sectionSurface: "base",
16577
17002
  contentFrame: plainFrame,
16578
- transitionAfter: "none",
16579
17003
  sectionHeight: "default",
16580
17004
  heroLegibility: "none",
16581
17005
  imageSurfaceTreatment: { kind: "none" },
@@ -16586,7 +17010,7 @@ const blockDesignFallback = {
16586
17010
  accordionIconTreatment: null,
16587
17011
  composition: null
16588
17012
  };
16589
- blockDesignFallback.sectionSurface, blockDesignFallback.contentFrame, blockDesignFallback.transitionAfter, blockDesignFallback.sectionHeight, blockDesignFallback.heroLegibility, blockDesignFallback.imageSurfaceTreatment, blockDesignFallback.imageSurfaceMotion, blockDesignFallback.tileTreatment, blockDesignFallback.eventListTreatment, blockDesignFallback.eyebrowTreatment, blockDesignFallback.accordionIconTreatment, blockDesignFallback.composition;
17013
+ blockDesignFallback.sectionSurface, blockDesignFallback.contentFrame, blockDesignFallback.sectionHeight, blockDesignFallback.heroLegibility, blockDesignFallback.imageSurfaceTreatment, blockDesignFallback.imageSurfaceMotion, blockDesignFallback.tileTreatment, blockDesignFallback.eventListTreatment, blockDesignFallback.eyebrowTreatment, blockDesignFallback.accordionIconTreatment, blockDesignFallback.composition;
16590
17014
  //#endregion
16591
17015
  //#region ../theme-core/src/site-styles/siteChromeBackgrounds.ts
16592
17016
  const siteChromeBackgroundColorTokens = toSiteChromeBackgroundColorTokens(backgroundAppearanceColorTokenNames);
@@ -17179,7 +17603,8 @@ const siteOptionSources = [
17179
17603
  "eventCategories",
17180
17604
  "eventSeries",
17181
17605
  "venues",
17182
- "staffMembers"
17606
+ "staffMembers",
17607
+ "appointmentServiceCategories"
17183
17608
  ];
17184
17609
  const mediaDeliverySchema = z.object({
17185
17610
  sizes: z.string().optional(),
@@ -29873,6 +30298,15 @@ const appointmentServicesBlockDefinition = {
29873
30298
  required: false,
29874
30299
  ui: { intent: "content" }
29875
30300
  },
30301
+ createSiteOptionSelectField({
30302
+ id: "categoryId",
30303
+ label: "Category",
30304
+ description: "Show one category (with its heading and intro), or leave it on All categories to show everything grouped.",
30305
+ required: false,
30306
+ multiple: false,
30307
+ optionSource: "appointmentServiceCategories",
30308
+ ui: { intent: "content" }
30309
+ }),
29876
30310
  sectionStylesField({
29877
30311
  id: "_sectionStyles",
29878
30312
  label: "Section styles",
@@ -29907,6 +30341,7 @@ const appointmentServicesBlockDefinition = {
29907
30341
  richText({ className: "rb-prose rb-max-w-none" }, bind("content.description"), when("content.description")),
29908
30342
  el("appointment-services", {
29909
30343
  sectionHeading: { $bind: { from: "content.heading" } },
30344
+ categoryId: { $bind: { from: "content.categoryId" } },
29910
30345
  services: { $bind: { from: "data.services" } },
29911
30346
  pathname: { $bind: { from: "$root.pathname" } },
29912
30347
  servicePathPrefix: { $bind: { from: "$root.appointmentServicePathPrefix" } }
@@ -40379,6 +40814,17 @@ function coerceToString(value) {
40379
40814
  return "";
40380
40815
  }
40381
40816
  /**
40817
+ * The appointment-services catalogue (issue 1403) pairs the services with the
40818
+ * site's ordered categories. Both are needed to group them, so that response
40819
+ * is passed through whole; any other `{ services }` wrapper is unwrapped.
40820
+ */
40821
+ function coerceServicesPayload(record) {
40822
+ return Array.isArray(record.services) && Array.isArray(record.categories) ? {
40823
+ services: record.services,
40824
+ categories: record.categories
40825
+ } : record.services;
40826
+ }
40827
+ /**
40382
40828
  * Extract data from API response.
40383
40829
  * Unwraps common response wrappers: { data }, { form }, { entries }, { services }, { teamMembers }
40384
40830
  *
@@ -40393,7 +40839,7 @@ function coercePayload(payload) {
40393
40839
  if ("data" in record && typeof record.data !== "function") return record.data;
40394
40840
  if ("form" in record && typeof record.form !== "function") return record.form;
40395
40841
  if ("entries" in record && typeof record.entries !== "function") return record.entries;
40396
- if ("services" in record && typeof record.services !== "function") return record.services;
40842
+ if ("services" in record && typeof record.services !== "function") return coerceServicesPayload(record);
40397
40843
  if ("teamMembers" in record && typeof record.teamMembers !== "function") return record.teamMembers;
40398
40844
  }
40399
40845
  return payload;
@@ -41295,7 +41741,12 @@ const appointmentSetupServiceDraftSchema = z.object({
41295
41741
  venue: appointmentSetupVenueChoiceSchema,
41296
41742
  timezone: z.string().trim().min(1).nullable(),
41297
41743
  payment: appointmentSetupPaymentDraftSchema,
41298
- assignment: appointmentSetupServiceAssignmentDraftSchema
41744
+ assignment: appointmentSetupServiceAssignmentDraftSchema,
41745
+ /**
41746
+ * The service's category, or null for "Other" (issue 1403). Omitted leaves
41747
+ * an existing service's category alone and puts a new one in "Other".
41748
+ */
41749
+ categoryId: z.string().uuid().nullable().optional()
41299
41750
  }).superRefine((service, ctx) => {
41300
41751
  if (service.payment.kind !== "free" && (service.priceAmount === null || service.priceAmount <= 0)) ctx.addIssue({
41301
41752
  code: "custom",
@@ -42231,7 +42682,7 @@ function usePage(params) {
42231
42682
  loading: false,
42232
42683
  error: null,
42233
42684
  page: pageOutline,
42234
- runtimeBoundaries: pageData.runtimeBoundaries,
42685
+ runtimeJoins: pageData.runtimeJoins,
42235
42686
  theme: requireSdkTheme(site.theme, siteId),
42236
42687
  siteId,
42237
42688
  resolvedData,