@wix/agent-skills 1.21.0 → 1.22.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 (258) hide show
  1. package/package.json +1 -1
  2. package/skills/wix-app/SKILL.md +60 -4
  3. package/skills/wix-app/references/DASHBOARD_PAGE.md +11 -25
  4. package/skills/wix-app/references/DATA_COLLECTION.md +16 -219
  5. package/skills/wix-app/references/dashboard-page/DATA_SOURCES.md +182 -0
  6. package/skills/wix-app/references/dashboard-page/DRAFT_TEMPLATE.md +97 -0
  7. package/skills/wix-app/references/dashboard-page/DRAFT_TEMPLATE_COLLECTION.md +184 -0
  8. package/skills/wix-app/references/dashboard-page/DRAFT_TEMPLATE_ROUTER.md +203 -0
  9. package/skills/wix-app/references/dashboard-page/DRAFT_TEMPLATE_SETTINGS.md +44 -0
  10. package/skills/wix-app/references/dashboard-page/QUERY_AND_PAGING.md +182 -0
  11. package/skills/wix-app/references/dashboard-page/TABLE_STATE.md +133 -0
  12. package/skills/wix-app/references/dashboard-page/UX_SUCCESS_MODEL.md +10 -5
  13. package/skills/wix-app/references/data-collection/LIFECYCLE.md +68 -0
  14. package/skills/wix-app/references/data-collection/PERMISSIONS.md +47 -0
  15. package/skills/wix-app/references/data-collection/SCHEMA.md +181 -0
  16. package/skills/wix-app/references/data-collection/WIX_DATA.md +38 -66
  17. package/skills/wix-headless-fast/SKILL.md +61 -223
  18. package/skills/wix-headless-fast/cold-start/bootstrap.mjs +156 -0
  19. package/skills/wix-headless-fast/{entry/skill.md → cold-start/cold-start.md} +11 -12
  20. package/skills/wix-headless-fast/guides/existing-site.md +76 -0
  21. package/skills/wix-headless-fast/guides/reference-mode.md +97 -0
  22. package/skills/wix-headless-fast/install/AGENTS.md +6 -3
  23. package/skills/wix-headless-fast/install/attach.mjs +15 -47
  24. package/skills/wix-headless-fast/install/deploy.mjs +21 -60
  25. package/skills/wix-headless-fast/install/lock.mjs +55 -0
  26. package/skills/wix-headless-fast/install/setup.mjs +32 -12
  27. package/skills/wix-headless-fast/install/templates.mjs +168 -0
  28. package/skills/wix-manage/references/google-ads/google-ads-dashboard-navigation.md +27 -0
  29. package/skills/wix-manage/references/google-ads/manage-campaign-success-guide.md +83 -37
  30. package/skills/wix-headless-fast/references/blog/INSTRUCTIONS.md +0 -303
  31. package/skills/wix-headless-fast/references/blog/app/components/blog/BlogFeedView.tsx +0 -136
  32. package/skills/wix-headless-fast/references/blog/app/components/blog/PostView.tsx +0 -112
  33. package/skills/wix-headless-fast/references/blog/app/components/blog/RichContent.tsx +0 -42
  34. package/skills/wix-headless-fast/references/blog/app/hooks/blog/useBlogFeed.ts +0 -31
  35. package/skills/wix-headless-fast/references/blog/app/hooks/blog/usePost.ts +0 -22
  36. package/skills/wix-headless-fast/references/blog/app/wix/blog/blog-feed-store.ts +0 -137
  37. package/skills/wix-headless-fast/references/blog/app/wix/blog/post-store.ts +0 -78
  38. package/skills/wix-headless-fast/references/blog/app/wix/blog/posts-core.ts +0 -117
  39. package/skills/wix-headless-fast/references/blog/app/wix/blog/posts.ts +0 -52
  40. package/skills/wix-headless-fast/references/blog/app/wix/blog/taxonomy-core.ts +0 -47
  41. package/skills/wix-headless-fast/references/blog/app/wix/blog/taxonomy.ts +0 -58
  42. package/skills/wix-headless-fast/references/blog/app/wix/blog/types.ts +0 -62
  43. package/skills/wix-headless-fast/references/blog/app-astro/layouts/SiteLayout.astro +0 -40
  44. package/skills/wix-headless-fast/references/blog/app-astro/pages/blog/[...slug].astro +0 -97
  45. package/skills/wix-headless-fast/references/blog/app-astro/pages/blog.astro +0 -24
  46. package/skills/wix-headless-fast/references/blog/lock/astro/package-lock.json +0 -16156
  47. package/skills/wix-headless-fast/references/blog/rest/posts.ts +0 -42
  48. package/skills/wix-headless-fast/references/blog/rest/taxonomy.ts +0 -62
  49. package/skills/wix-headless-fast/references/blog/seed/SEED.md +0 -81
  50. package/skills/wix-headless-fast/references/blog/seed/read-site.mjs +0 -22
  51. package/skills/wix-headless-fast/references/blog/seed/seed-blog.mjs +0 -287
  52. package/skills/wix-headless-fast/references/bookings/INSTRUCTIONS.md +0 -277
  53. package/skills/wix-headless-fast/references/bookings/app/components/bookings/ServiceBookingView.tsx +0 -144
  54. package/skills/wix-headless-fast/references/bookings/app/components/bookings/ServicesView.tsx +0 -119
  55. package/skills/wix-headless-fast/references/bookings/app/hooks/bookings/useBookingFlow.ts +0 -32
  56. package/skills/wix-headless-fast/references/bookings/app/hooks/bookings/useServices.ts +0 -23
  57. package/skills/wix-headless-fast/references/bookings/app/wix/bookings/booking-core.ts +0 -218
  58. package/skills/wix-headless-fast/references/bookings/app/wix/bookings/booking-flow-store.ts +0 -169
  59. package/skills/wix-headless-fast/references/bookings/app/wix/bookings/booking.ts +0 -121
  60. package/skills/wix-headless-fast/references/bookings/app/wix/bookings/services-core.ts +0 -92
  61. package/skills/wix-headless-fast/references/bookings/app/wix/bookings/services-store.ts +0 -90
  62. package/skills/wix-headless-fast/references/bookings/app/wix/bookings/services.ts +0 -57
  63. package/skills/wix-headless-fast/references/bookings/app/wix/bookings/types.ts +0 -72
  64. package/skills/wix-headless-fast/references/bookings/app-astro/layouts/SiteLayout.astro +0 -40
  65. package/skills/wix-headless-fast/references/bookings/app-astro/pages/services/[slug].astro +0 -76
  66. package/skills/wix-headless-fast/references/bookings/app-astro/pages/services.astro +0 -22
  67. package/skills/wix-headless-fast/references/bookings/lock/astro/package-lock.json +0 -11962
  68. package/skills/wix-headless-fast/references/bookings/rest/booking.ts +0 -113
  69. package/skills/wix-headless-fast/references/bookings/rest/services.ts +0 -55
  70. package/skills/wix-headless-fast/references/bookings/seed/SEED.md +0 -71
  71. package/skills/wix-headless-fast/references/bookings/seed/read-site.mjs +0 -28
  72. package/skills/wix-headless-fast/references/bookings/seed/seed-bookings.mjs +0 -302
  73. package/skills/wix-headless-fast/references/cms/INSTRUCTIONS.md +0 -355
  74. package/skills/wix-headless-fast/references/cms/app/hooks/cms/useCollection.ts +0 -50
  75. package/skills/wix-headless-fast/references/cms/app/hooks/cms/useItem.ts +0 -37
  76. package/skills/wix-headless-fast/references/cms/app/wix/cms/collection-store.ts +0 -158
  77. package/skills/wix-headless-fast/references/cms/app/wix/cms/item-store.ts +0 -93
  78. package/skills/wix-headless-fast/references/cms/app/wix/cms/items-core.ts +0 -177
  79. package/skills/wix-headless-fast/references/cms/app/wix/cms/items.ts +0 -123
  80. package/skills/wix-headless-fast/references/cms/app/wix/cms/types.ts +0 -75
  81. package/skills/wix-headless-fast/references/cms/app-astro/layouts/SiteLayout.astro +0 -41
  82. package/skills/wix-headless-fast/references/cms/lock/astro/package-lock.json +0 -11262
  83. package/skills/wix-headless-fast/references/cms/rest/items.ts +0 -125
  84. package/skills/wix-headless-fast/references/cms/seed/SEED.md +0 -112
  85. package/skills/wix-headless-fast/references/cms/seed/read-site.mjs +0 -20
  86. package/skills/wix-headless-fast/references/cms/seed/seed-cms.mjs +0 -324
  87. package/skills/wix-headless-fast/references/events/INSTRUCTIONS.md +0 -307
  88. package/skills/wix-headless-fast/references/events/app/components/events/EventConfirmationView.tsx +0 -66
  89. package/skills/wix-headless-fast/references/events/app/components/events/EventRegistrationView.tsx +0 -178
  90. package/skills/wix-headless-fast/references/events/app/components/events/EventsView.tsx +0 -118
  91. package/skills/wix-headless-fast/references/events/app/hooks/events/useEventRegistration.ts +0 -35
  92. package/skills/wix-headless-fast/references/events/app/hooks/events/useEvents.ts +0 -24
  93. package/skills/wix-headless-fast/references/events/app/wix/events/events-core.ts +0 -130
  94. package/skills/wix-headless-fast/references/events/app/wix/events/events-store.ts +0 -97
  95. package/skills/wix-headless-fast/references/events/app/wix/events/events.ts +0 -55
  96. package/skills/wix-headless-fast/references/events/app/wix/events/registration-core.ts +0 -113
  97. package/skills/wix-headless-fast/references/events/app/wix/events/registration-store.ts +0 -156
  98. package/skills/wix-headless-fast/references/events/app/wix/events/registration.ts +0 -97
  99. package/skills/wix-headless-fast/references/events/app/wix/events/types.ts +0 -61
  100. package/skills/wix-headless-fast/references/events/app-astro/layouts/SiteLayout.astro +0 -40
  101. package/skills/wix-headless-fast/references/events/app-astro/pages/event-confirmation.astro +0 -12
  102. package/skills/wix-headless-fast/references/events/app-astro/pages/events/[slug].astro +0 -80
  103. package/skills/wix-headless-fast/references/events/app-astro/pages/events.astro +0 -21
  104. package/skills/wix-headless-fast/references/events/lock/astro/package-lock.json +0 -11884
  105. package/skills/wix-headless-fast/references/events/rest/events.ts +0 -57
  106. package/skills/wix-headless-fast/references/events/rest/registration.ts +0 -83
  107. package/skills/wix-headless-fast/references/events/seed/SEED.md +0 -95
  108. package/skills/wix-headless-fast/references/events/seed/read-site.mjs +0 -26
  109. package/skills/wix-headless-fast/references/events/seed/seed-events.mjs +0 -276
  110. package/skills/wix-headless-fast/references/forms/INSTRUCTIONS.md +0 -340
  111. package/skills/wix-headless-fast/references/forms/app/hooks/forms/useWixForm.ts +0 -85
  112. package/skills/wix-headless-fast/references/forms/app/wix/forms/form-store.ts +0 -332
  113. package/skills/wix-headless-fast/references/forms/app/wix/forms/forms-core.ts +0 -238
  114. package/skills/wix-headless-fast/references/forms/app/wix/forms/forms.ts +0 -54
  115. package/skills/wix-headless-fast/references/forms/app/wix/forms/submissions-core.ts +0 -216
  116. package/skills/wix-headless-fast/references/forms/app/wix/forms/submissions.ts +0 -59
  117. package/skills/wix-headless-fast/references/forms/app/wix/forms/types.ts +0 -135
  118. package/skills/wix-headless-fast/references/forms/lock/astro/package-lock.json +0 -10593
  119. package/skills/wix-headless-fast/references/forms/rest/forms.ts +0 -34
  120. package/skills/wix-headless-fast/references/forms/rest/submissions.ts +0 -56
  121. package/skills/wix-headless-fast/references/forms/seed/SEED.md +0 -116
  122. package/skills/wix-headless-fast/references/forms/seed/read-site.mjs +0 -20
  123. package/skills/wix-headless-fast/references/forms/seed/seed-forms.mjs +0 -327
  124. package/skills/wix-headless-fast/references/members/INSTRUCTIONS.md +0 -316
  125. package/skills/wix-headless-fast/references/members/app/components/members/AccountView.tsx +0 -60
  126. package/skills/wix-headless-fast/references/members/app/components/members/LoginForm.tsx +0 -155
  127. package/skills/wix-headless-fast/references/members/app/components/members/MemberMenu.tsx +0 -78
  128. package/skills/wix-headless-fast/references/members/app/components/members/RequireAuth.tsx +0 -47
  129. package/skills/wix-headless-fast/references/members/app/hooks/members/useMember.ts +0 -66
  130. package/skills/wix-headless-fast/references/members/app/wix/members/auth-core.ts +0 -105
  131. package/skills/wix-headless-fast/references/members/app/wix/members/auth.ts +0 -59
  132. package/skills/wix-headless-fast/references/members/app/wix/members/client.ts +0 -53
  133. package/skills/wix-headless-fast/references/members/app/wix/members/member-store.ts +0 -122
  134. package/skills/wix-headless-fast/references/members/app/wix/members/members-core.ts +0 -43
  135. package/skills/wix-headless-fast/references/members/app/wix/members/members.ts +0 -29
  136. package/skills/wix-headless-fast/references/members/app/wix/members/types.ts +0 -21
  137. package/skills/wix-headless-fast/references/members/app-astro/layouts/SiteLayout.astro +0 -42
  138. package/skills/wix-headless-fast/references/members/app-astro/pages/account.astro +0 -10
  139. package/skills/wix-headless-fast/references/members/app-astro/pages/login.astro +0 -11
  140. package/skills/wix-headless-fast/references/members/lock/astro/package-lock.json +0 -10329
  141. package/skills/wix-headless-fast/references/members/rest/auth.ts +0 -215
  142. package/skills/wix-headless-fast/references/members/rest/members.ts +0 -26
  143. package/skills/wix-headless-fast/references/members/seed/SEED.md +0 -39
  144. package/skills/wix-headless-fast/references/members/seed/read-site.mjs +0 -15
  145. package/skills/wix-headless-fast/references/members/seed/seed-members.mjs +0 -94
  146. package/skills/wix-headless-fast/references/portfolio/INSTRUCTIONS.md +0 -315
  147. package/skills/wix-headless-fast/references/portfolio/app/components/portfolio/CollectionProjectsView.tsx +0 -110
  148. package/skills/wix-headless-fast/references/portfolio/app/components/portfolio/CollectionsView.tsx +0 -90
  149. package/skills/wix-headless-fast/references/portfolio/app/components/portfolio/GalleryMedia.tsx +0 -35
  150. package/skills/wix-headless-fast/references/portfolio/app/components/portfolio/ProjectDetailView.tsx +0 -85
  151. package/skills/wix-headless-fast/references/portfolio/app/hooks/portfolio/useCollectionProjects.ts +0 -32
  152. package/skills/wix-headless-fast/references/portfolio/app/hooks/portfolio/useCollections.ts +0 -21
  153. package/skills/wix-headless-fast/references/portfolio/app/hooks/portfolio/useProjectDetail.ts +0 -31
  154. package/skills/wix-headless-fast/references/portfolio/app/wix/portfolio/collection-projects-store.ts +0 -82
  155. package/skills/wix-headless-fast/references/portfolio/app/wix/portfolio/collections-store.ts +0 -58
  156. package/skills/wix-headless-fast/references/portfolio/app/wix/portfolio/portfolio-core.ts +0 -177
  157. package/skills/wix-headless-fast/references/portfolio/app/wix/portfolio/portfolio.ts +0 -78
  158. package/skills/wix-headless-fast/references/portfolio/app/wix/portfolio/project-detail-store.ts +0 -81
  159. package/skills/wix-headless-fast/references/portfolio/app/wix/portfolio/types.ts +0 -55
  160. package/skills/wix-headless-fast/references/portfolio/app-astro/layouts/SiteLayout.astro +0 -40
  161. package/skills/wix-headless-fast/references/portfolio/app-astro/pages/portfolio/[slug].astro +0 -30
  162. package/skills/wix-headless-fast/references/portfolio/app-astro/pages/portfolio.astro +0 -21
  163. package/skills/wix-headless-fast/references/portfolio/app-astro/pages/projects/[slug].astro +0 -29
  164. package/skills/wix-headless-fast/references/portfolio/lock/astro/package-lock.json +0 -10197
  165. package/skills/wix-headless-fast/references/portfolio/rest/portfolio.ts +0 -75
  166. package/skills/wix-headless-fast/references/portfolio/seed/SEED.md +0 -86
  167. package/skills/wix-headless-fast/references/portfolio/seed/read-site.mjs +0 -20
  168. package/skills/wix-headless-fast/references/portfolio/seed/seed-portfolio.mjs +0 -256
  169. package/skills/wix-headless-fast/references/pricing-plans/INSTRUCTIONS.md +0 -296
  170. package/skills/wix-headless-fast/references/pricing-plans/app/components/pricing-plans/PlanDetailView.tsx +0 -47
  171. package/skills/wix-headless-fast/references/pricing-plans/app/components/pricing-plans/PlansView.tsx +0 -101
  172. package/skills/wix-headless-fast/references/pricing-plans/app/components/pricing-plans/SubscribeButton.tsx +0 -41
  173. package/skills/wix-headless-fast/references/pricing-plans/app/hooks/pricing-plans/usePlanPurchase.ts +0 -16
  174. package/skills/wix-headless-fast/references/pricing-plans/app/hooks/pricing-plans/usePlans.ts +0 -22
  175. package/skills/wix-headless-fast/references/pricing-plans/app/wix/pricing-plans/plan-purchase-store.ts +0 -54
  176. package/skills/wix-headless-fast/references/pricing-plans/app/wix/pricing-plans/plans-core.ts +0 -106
  177. package/skills/wix-headless-fast/references/pricing-plans/app/wix/pricing-plans/plans-store.ts +0 -64
  178. package/skills/wix-headless-fast/references/pricing-plans/app/wix/pricing-plans/plans.ts +0 -27
  179. package/skills/wix-headless-fast/references/pricing-plans/app/wix/pricing-plans/purchase-core.ts +0 -43
  180. package/skills/wix-headless-fast/references/pricing-plans/app/wix/pricing-plans/purchase.ts +0 -22
  181. package/skills/wix-headless-fast/references/pricing-plans/app/wix/pricing-plans/types.ts +0 -30
  182. package/skills/wix-headless-fast/references/pricing-plans/app-astro/layouts/SiteLayout.astro +0 -41
  183. package/skills/wix-headless-fast/references/pricing-plans/app-astro/pages/plans/[slug].astro +0 -40
  184. package/skills/wix-headless-fast/references/pricing-plans/app-astro/pages/plans.astro +0 -21
  185. package/skills/wix-headless-fast/references/pricing-plans/lock/astro/package-lock.json +0 -11226
  186. package/skills/wix-headless-fast/references/pricing-plans/rest/plans.ts +0 -31
  187. package/skills/wix-headless-fast/references/pricing-plans/rest/purchase.ts +0 -20
  188. package/skills/wix-headless-fast/references/pricing-plans/seed/SEED.md +0 -79
  189. package/skills/wix-headless-fast/references/pricing-plans/seed/read-site.mjs +0 -21
  190. package/skills/wix-headless-fast/references/pricing-plans/seed/seed-pricing-plans.mjs +0 -279
  191. package/skills/wix-headless-fast/references/restaurants/INSTRUCTIONS.md +0 -360
  192. package/skills/wix-headless-fast/references/restaurants/app/components/restaurants/MenuView.tsx +0 -142
  193. package/skills/wix-headless-fast/references/restaurants/app/components/restaurants/OrderCartButton.tsx +0 -26
  194. package/skills/wix-headless-fast/references/restaurants/app/components/restaurants/OrderCartDrawer.tsx +0 -121
  195. package/skills/wix-headless-fast/references/restaurants/app/components/restaurants/ReservationView.tsx +0 -155
  196. package/skills/wix-headless-fast/references/restaurants/app/hooks/restaurants/useMenus.ts +0 -34
  197. package/skills/wix-headless-fast/references/restaurants/app/hooks/restaurants/useOrderCart.ts +0 -43
  198. package/skills/wix-headless-fast/references/restaurants/app/hooks/restaurants/useReservation.ts +0 -34
  199. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/menu-core.ts +0 -155
  200. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/menu-store.ts +0 -89
  201. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/menu.ts +0 -71
  202. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/order-store.ts +0 -103
  203. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/ordering-core.ts +0 -124
  204. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/ordering.ts +0 -185
  205. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/reservation-store.ts +0 -193
  206. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/reservations-core.ts +0 -94
  207. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/reservations.ts +0 -74
  208. package/skills/wix-headless-fast/references/restaurants/app/wix/restaurants/types.ts +0 -168
  209. package/skills/wix-headless-fast/references/restaurants/app-astro/layouts/SiteLayout.astro +0 -47
  210. package/skills/wix-headless-fast/references/restaurants/app-astro/pages/menu.astro +0 -22
  211. package/skills/wix-headless-fast/references/restaurants/app-astro/pages/reservations.astro +0 -12
  212. package/skills/wix-headless-fast/references/restaurants/lock/astro/package-lock.json +0 -12560
  213. package/skills/wix-headless-fast/references/restaurants/rest/menu.ts +0 -60
  214. package/skills/wix-headless-fast/references/restaurants/rest/ordering.ts +0 -169
  215. package/skills/wix-headless-fast/references/restaurants/rest/reservations.ts +0 -68
  216. package/skills/wix-headless-fast/references/restaurants/seed/SEED.md +0 -89
  217. package/skills/wix-headless-fast/references/restaurants/seed/read-site.mjs +0 -25
  218. package/skills/wix-headless-fast/references/restaurants/seed/seed-restaurants.mjs +0 -499
  219. package/skills/wix-headless-fast/references/shared/CONTENT.md +0 -22
  220. package/skills/wix-headless-fast/references/shared/CUSTOM_OPERATIONS.md +0 -73
  221. package/skills/wix-headless-fast/references/shared/DESIGN.md +0 -26
  222. package/skills/wix-headless-fast/references/shared/SUPPLIED-CONTENT.md +0 -23
  223. package/skills/wix-headless-fast/references/shared/app/styles/global.css +0 -52
  224. package/skills/wix-headless-fast/references/shared/app/wix/config.ts +0 -15
  225. package/skills/wix-headless-fast/references/shared/app/wix/media.ts +0 -81
  226. package/skills/wix-headless-fast/references/shared/app/wix/money.ts +0 -24
  227. package/skills/wix-headless-fast/references/shared/app/wix/sdk.ts +0 -89
  228. package/skills/wix-headless-fast/references/shared/capabilities/media-upload/app/wix/media-upload/client.ts +0 -46
  229. package/skills/wix-headless-fast/references/shared/capabilities/media-upload/app-astro/pages/api/wix/media-upload.ts +0 -46
  230. package/skills/wix-headless-fast/references/shared/rest/client.ts +0 -155
  231. package/skills/wix-headless-fast/references/shared/rest/config.ts +0 -3
  232. package/skills/wix-headless-fast/references/shared/rest/media.ts +0 -65
  233. package/skills/wix-headless-fast/references/shared/seed/images.mjs +0 -145
  234. package/skills/wix-headless-fast/references/shared/seed/read-site.mjs +0 -99
  235. package/skills/wix-headless-fast/references/storefront/INSTRUCTIONS.md +0 -612
  236. package/skills/wix-headless-fast/references/storefront/app/components/storefront/CartButton.tsx +0 -26
  237. package/skills/wix-headless-fast/references/storefront/app/components/storefront/CartDrawer.tsx +0 -155
  238. package/skills/wix-headless-fast/references/storefront/app/components/storefront/FilterPanel.tsx +0 -266
  239. package/skills/wix-headless-fast/references/storefront/app/components/storefront/OptionPicker.tsx +0 -95
  240. package/skills/wix-headless-fast/references/storefront/app/components/storefront/QuickAdd.tsx +0 -136
  241. package/skills/wix-headless-fast/references/storefront/app/hooks/storefront/useCart.ts +0 -48
  242. package/skills/wix-headless-fast/references/storefront/app/hooks/storefront/useProductDetail.ts +0 -39
  243. package/skills/wix-headless-fast/references/storefront/app/hooks/storefront/useShop.ts +0 -34
  244. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/cart-core.ts +0 -121
  245. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/cart-store.ts +0 -107
  246. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/cart.ts +0 -138
  247. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/catalog-core.ts +0 -314
  248. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/catalog.ts +0 -133
  249. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/product-detail-store.ts +0 -147
  250. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/shop-store.ts +0 -289
  251. package/skills/wix-headless-fast/references/storefront/app/wix/storefront/types.ts +0 -169
  252. package/skills/wix-headless-fast/references/storefront/app-astro/layouts/SiteLayout.astro +0 -65
  253. package/skills/wix-headless-fast/references/storefront/lock/astro/package-lock.json +0 -12247
  254. package/skills/wix-headless-fast/references/storefront/rest/cart.ts +0 -132
  255. package/skills/wix-headless-fast/references/storefront/rest/catalog.ts +0 -123
  256. package/skills/wix-headless-fast/references/storefront/seed/SEED.md +0 -130
  257. package/skills/wix-headless-fast/references/storefront/seed/read-site.mjs +0 -38
  258. package/skills/wix-headless-fast/references/storefront/seed/seed-store.mjs +0 -561
@@ -0,0 +1,203 @@
1
+ # Draft Template — Cases A, B and D (router-wired)
2
+
3
+ **Applies to [DRAFT_TEMPLATE.md](DRAFT_TEMPLATE.md)'s Cases A, B and D.** All three need `PatternsReactRouter`, because in all three a row opens a page of its own — a panel is not the drill-in ([UX_SUCCESS_MODEL.md](UX_SUCCESS_MODEL.md)). Case A's detail route is read-only (§4); B and D route to a full `EntityPage`. The collection and settings components live in [DRAFT_TEMPLATE.md](DRAFT_TEMPLATE.md); this file covers only what a router adds — the entry file, the app shell, and the detail/entity page.
4
+
5
+ Every snippet below is copied from the installed `dist/docs/*.md` this session read, not from memory.
6
+
7
+ ## 1. Entry — `location` is manual in a Wix CLI app, and only because the router needs it
8
+
9
+ `PatternsReactRouter` reads the page location through `container.usePageLocation()`, which only `withDashboard`'s `location` prop feeds — nothing supplies it automatically in a Wix CLI app the way Yoshi BM flow does:
10
+
11
+ ```tsx
12
+ // {feature}.tsx — Case A, B or D
13
+ import { useEffect, useState, type FC } from 'react';
14
+ import { dashboard } from '@wix/dashboard';
15
+ import { WixDesignSystemProvider } from '@wix/design-system';
16
+ import '@wix/design-system/styles.global.css';
17
+ import { {Feature}App } from './{Feature}App';
18
+
19
+ type PageLocation = Parameters<Parameters<typeof dashboard.observeState>[0]>[1]['pageLocation'];
20
+
21
+ const Page: FC = () => {
22
+ const [location, setLocation] = useState<PageLocation | undefined>();
23
+
24
+ useEffect(() => {
25
+ const subscription = dashboard.observeState((_pageParams, environment) => {
26
+ setLocation(environment.pageLocation);
27
+ });
28
+ return () => subscription.disconnect();
29
+ }, []);
30
+
31
+ return (
32
+ <WixDesignSystemProvider>
33
+ {location ? <{Feature}App location={location} /> : null}
34
+ </WixDesignSystemProvider>
35
+ );
36
+ };
37
+
38
+ export default Page;
39
+ ```
40
+
41
+ **Skipping this is a runtime-only failure.** Per `PatternsReactRouter`'s own docs: "Nothing catches this before runtime — type checking and bundling both pass, because neither renders the page." `tsc` and `wix build` will not catch a missing `location` — only opening the page in a browser will. This is exactly why [Step 5's Preview](../../SKILL.md#validation) is not optional for Case B/D.
42
+
43
+ ## 2. App shell — provider, router, routes
44
+
45
+ ```tsx
46
+ // {Feature}App.tsx — Case A, B or D
47
+ import { withDashboard } from '@wix/patterns';
48
+ import { WixPatternsProvider } from '@wix/patterns/provider';
49
+ import { PatternsReactRouter, PatternsReactRoute } from '@wix/patterns/router';
50
+ import { {Feature}CollectionPage } from './{Feature}CollectionPage';
51
+ import { {Feature}EntityPage } from './{Feature}EntityPage';
52
+ // Case D only:
53
+ import { {Feature}SettingsPage } from './{Feature}SettingsPage';
54
+
55
+ export const {Feature}App = withDashboard(() => (
56
+ <WixPatternsProvider>
57
+ <PatternsReactRouter>
58
+ <PatternsReactRoute type="collection" path="/" element={<{Feature}CollectionPage />} />
59
+ {/* Case B/D — editable record. Case A registers this ONE route instead, with
60
+ {Feature}DetailPage as the element and no /new route (§4). Either way the
61
+ type is `editEntity`: it wires back-navigation to the collection. */}
62
+ <PatternsReactRoute type="editEntity" path="/:id" element={<{Feature}EntityPage />} />
63
+ {/* Case B/D only — Case A has nothing to create: */}
64
+ <PatternsReactRoute type="createEntity" path="/new" element={<{Feature}EntityPage />} />
65
+ {/* Case D only: */}
66
+ <PatternsReactRoute type="other" path="/settings" element={<{Feature}SettingsPage />} />
67
+ </PatternsReactRouter>
68
+ </WixPatternsProvider>
69
+ ));
70
+ ```
71
+
72
+ `PatternsReactRoute`'s `type` is one of exactly `"collection" | "createEntity" | "editEntity" | "other"` — no dedicated settings value, so a settings route is `"other"`. Case B: delete the `/settings` route and the import above it — nothing else changes.
73
+
74
+ `{Feature}CollectionPage` is [DRAFT_TEMPLATE_COLLECTION.md](DRAFT_TEMPLATE_COLLECTION.md)'s component, unchanged; `{Feature}SettingsPage` (Case D) is [DRAFT_TEMPLATE_SETTINGS.md](DRAFT_TEMPLATE_SETTINGS.md).
75
+
76
+ ## 2b. The collection side of the handoff
77
+
78
+ The router file above registers `/new`; something has to navigate there. All three of these live on
79
+ the collection page, and `usePatternsNavigate` comes from **`@wix/patterns/router`** — not the root
80
+ export, which is where it is easy to reach for it:
81
+
82
+ ```tsx
83
+ import { PrimaryPageButton } from '@wix/patterns';
84
+ import { usePatternsNavigate } from '@wix/patterns/router';
85
+
86
+ const { navigateToEntityPage } = usePatternsNavigate<{Entity}>();
87
+ const openNew = () => navigateToEntityPage({ path: '/new' }); // no record yet — omit `entity`
88
+
89
+ // CollectionPage.Header — primaryAction takes an ELEMENT, not a { text, onClick } config:
90
+ <CollectionPage.Header
91
+ title={{ text: '{Page Title}' }}
92
+ primaryAction={<PrimaryPageButton text="Add {entity}" onClick={openNew} />}
93
+ />
94
+
95
+ // the empty state should offer the same action, and this one IS a config object:
96
+ <CollectionEmptyState title="No {feature} yet" addNewCta={{ text: 'Add {entity}', onClick: openNew }} />
97
+
98
+ // and a row opens the edit route:
99
+ onRowClick={(item) => navigateToEntityPage({ path: `/${item.id}`, entity: item })}
100
+ ```
101
+
102
+ The two shapes differ on purpose — `primaryAction` is an element, `addNewCta` is `{ text, onClick }`.
103
+ Guessing either costs a compile round.
104
+
105
+ ## 3. Entity page — one component for both `/new` and `/:id`
106
+
107
+ Full call details (both generics, what `onSave` receives, the `UseEntityPageParams` pick list) are in `<pkgRoot>/dist/docs/useEntityPage.md` — read it before filling in fields. The part specific to this router-based shape:
108
+
109
+ ```tsx
110
+ // {Feature}EntityPage.tsx — Case B or D (sketch — see dist/docs/useEntityPage.md for the full call)
111
+ import { useParams } from 'react-router-dom'; // NOT @wix/patterns/router — PatternsReactRoute wraps react-router-dom's Route, but only exports PatternsReactRoute/PatternsReactRouter/usePatternsNavigate itself
112
+ import { useEntityPage, EntityPage } from '@wix/patterns';
113
+ import { useForm } from '@wix/patterns/form';
114
+ import { fetch{Entity}, save{Entity}, type {Entity} } from './{feature}-api';
115
+
116
+ // The form's shape is yours to declare, and need not match the saved entity type.
117
+ type {Entity}FormFields = { name: string };
118
+
119
+ export const {Feature}EntityPage = () => {
120
+ const { id } = useParams<{ id?: string }>();
121
+ const form = useForm<{Entity}FormFields>();
122
+
123
+ const state = useEntityPage<{Entity}, {Entity}FormFields>({
124
+ parentPath: '/', // NOT parentPageId — this shape always uses Patterns Router
125
+ isNewEntity: () => !id, // a getter: the route can change (/new -> /:id after save) while this stays mounted
126
+ form,
127
+ fetch: () => (id ? fetch{Entity}(id).then((entity) => ({ entity })) : Promise.resolve({ entity: undefined })),
128
+ onSave: ({ widgetsFormData }) =>
129
+ save{Entity}({ id, ...form.getValues(), ...widgetsFormData }).then((updatedEntity) => ({ updatedEntity })),
130
+ });
131
+
132
+ return (
133
+ <EntityPage state={state}>
134
+ <EntityPage.Header title={{ text: id ? 'Edit {Entity}' : 'New {Entity}' }} />
135
+ <EntityPage.Content>
136
+ <EntityPage.MainContent>{/* form cards — see dist/docs/EntityPage.md */}</EntityPage.MainContent>
137
+ </EntityPage.Content>
138
+ </EntityPage>
139
+ );
140
+ };
141
+ ```
142
+
143
+ `useEntityPage`'s own docs are explicit about both details above: `parentPath` "Must be passed if using Patterns Router" (`parentPageId` is the non-router alternative — irrelevant here, since Case B/D always uses the router), and `isNewEntity` should be "a getter when the route can change while the page stays mounted" — exactly this component's case, since a successful create typically navigates `/new` → `/:newId`.
144
+
145
+ **`UseEntityPageParams` is a `Pick<>`, so a param missing from it is a compile error, not an ignored prop.** `isNewEntity` is in that list at 1.470.0 and absent before ~1.46x. If it doesn't compile, read the pick list in your installed `dist/types/hooks/useEntityPage.d.ts` and upgrade — deleting the line makes a create route behave as an edit.
146
+
147
+ ## 4. Read-only detail route — Case A
148
+
149
+ A display-only collection still routes its rows to a page — but not an `EntityPage`, which has no
150
+ read-only mode and still has none at **1.471.0**: `fetch` and `onSave` are both required, and
151
+ `actionsBarConfig` (`saveCta.text`, `cancelCta`) can retext Save but not remove it. It would ship
152
+ two buttons that either do nothing or save a form nobody was offered.
153
+
154
+ Use a WDS `Page` — what Cairo does itself: `example-bm`'s `DataExtensionEntityViewPage` and
155
+ auto-patterns' `ViewModeEntityPage` are both plain WDS `Page`s, the latter unexported.
156
+
157
+ ```tsx
158
+ // {Feature}DetailPage.tsx — Case A
159
+ import { useEffect, useState } from 'react';
160
+ import { useParams } from 'react-router-dom';
161
+ import { Card, Loader, Page, Text } from '@wix/design-system';
162
+ import { usePatternsNavigate } from '@wix/patterns/router';
163
+ import { fetch{Entity}, type {Entity} } from './{feature}-api';
164
+
165
+ export const {Feature}DetailPage = () => {
166
+ const { id } = useParams<{ id: string }>();
167
+ const { navigateToCollectionPage } = usePatternsNavigate();
168
+ const [entity, setEntity] = useState<{Entity} | undefined>();
169
+
170
+ useEffect(() => {
171
+ if (id) {
172
+ fetch{Entity}(id).then(setEntity);
173
+ }
174
+ }, [id]);
175
+
176
+ return (
177
+ <Page>
178
+ {/* The way back is the header's back button — a read-only page has no Cancel. */}
179
+ <Page.Header
180
+ title={entity?.name ?? '{Entity}'}
181
+ showBackButton
182
+ onBackClicked={() => navigateToCollectionPage({ path: '/' })}
183
+ />
184
+ <Page.Content>
185
+ {entity ? (
186
+ <Card>
187
+ <Card.Header title="Details" />
188
+ <Card.Divider />
189
+ <Card.Content>
190
+ <Text>{entity.name}</Text>
191
+ </Card.Content>
192
+ </Card>
193
+ ) : (
194
+ <Loader />
195
+ )}
196
+ </Page.Content>
197
+ </Page>
198
+ );
199
+ };
200
+ ```
201
+
202
+ If the request later grows an edit form this becomes §3's `EntityPage`, route type and `onRowClick`
203
+ unchanged — which is why Case A registers `editEntity`, not `other`.
@@ -0,0 +1,44 @@
1
+ # Draft Template — Settings page (Cases C and D)
2
+
3
+ > Pick your case in [DRAFT_TEMPLATE.md](DRAFT_TEMPLATE.md) first; this page covers Case C or D.
4
+
5
+ ## The settings page
6
+
7
+ No dedicated toolkit file exists for this yet (unlike Entity/Collection) — the shape, verified against `useSettingsPage.md`:
8
+
9
+ ```tsx
10
+ // {Feature}SettingsPage.tsx — Case C or D
11
+ import { SettingsPage, useSettingsPage, useSettings } from '@wix/patterns';
12
+ import { useForm } from '@wix/patterns/form';
13
+ import { fetch{Feature}Settings, save{Feature}Settings, type {Feature}Settings } from './{feature}-api';
14
+
15
+ // The form's shape is yours to declare, and need not match the saved settings type —
16
+ // one field per control on the page.
17
+ type {Feature}SettingsFormFields = { reminderHours: number; notifyStaff: boolean };
18
+
19
+ export const {Feature}SettingsPage = () => {
20
+ const form = useForm<{Feature}SettingsFormFields>();
21
+
22
+ const state = useSettingsPage<{Feature}Settings, {Feature}SettingsFormFields>({
23
+ form,
24
+ fetch: () => fetch{Feature}Settings().then((settings) => ({ settings })),
25
+ onSave: () => save{Feature}Settings(form.getValues()),
26
+ onCancel: async () => form.reset(),
27
+ saveSuccessToast: 'Settings saved',
28
+ saveErrorToast: (err, { retry }) => ({ message: 'Failed to save settings', action: { text: 'Retry', onClick: retry } }),
29
+ });
30
+
31
+ const settings = useSettings<{Feature}Settings, {Feature}SettingsFormFields>(state);
32
+
33
+ return (
34
+ <SettingsPage state={state}>
35
+ <SettingsPage.Header title={{ text: '{Settings Page Title}' }} />
36
+ <SettingsPage.Content>
37
+ <SettingsPage.MainContent>{/* form cards — same field-controller patterns as EntityPage */}</SettingsPage.MainContent>
38
+ </SettingsPage.Content>
39
+ </SettingsPage>
40
+ );
41
+ };
42
+ ```
43
+
44
+ `useSettingsPage`'s params are all required except `saveSuccessToast`/`saveErrorToast`: `form`, `fetch`, `onSave`, `onCancel`. There is no `parentPath`/`parentPageId` — a settings page isn't reached by drilling into a row, so it carries no back-navigation contract, and Case C needs no router at all to reach it (Section 1's entry renders it directly).
@@ -0,0 +1,182 @@
1
+ # Querying and paging a Wix API from a collection page
2
+
3
+ > [DATA_SOURCES.md](DATA_SOURCES.md) covers finding the method and its fields; this page is about
4
+ > calling it.
5
+
6
+ Filters are written in **WQL**, which is shared across the platform — the rules below come from
7
+ [About the Wix API Query Language][wql], not from one endpoint's behaviour, so they hold for
8
+ `@wix/ecom`, `@wix/stores`, `@wix/bookings` and the rest alike.
9
+
10
+ ## The filterable fields are a closed list, published per endpoint
11
+
12
+ > "This endpoint declares which fields it can filter and sort by, and with which operators; that
13
+ > list is closed and covers this endpoint only. Anything else errors or silently returns the wrong
14
+ > rows." — [WQL][wql]
15
+
16
+ So a field path is never inferable from the entity shape, and the endpoint's own prose is not
17
+ authoritative either. **Most query endpoints publish a "Supported Filters and Sorting" page**, and
18
+ the SDK typedoc for the query's `filter` field links to it — Contacts, Orders, Products V3,
19
+ Pipelines and Bookings all do. Find the link before you guess:
20
+
21
+ ```bash
22
+ grep -rho "https://[^)]*supported-filters[^)]*" node_modules/@wix/<pkg>/build/es/*.d.mts | sort -u
23
+ ```
24
+
25
+ **Read the page, don't just find it.** It is a table of field → operators, and it routinely lists
26
+ more than the endpoint's prose implies — Query Extended Bookings' prose mentions filtering courses
27
+ "by `scheduleId`", while its table also declares `serviceId` and the staff `resource.id` on both
28
+ `bookedEntity` branches, and `contactDetails.contactId` / `.email`. Those are the difference between
29
+ a page with two working filters and one with five.
30
+
31
+ **Honour the *Filter Performance* note.** Many pages carry one, naming fields to include in every
32
+ request — Query Extended Bookings "strongly recommends" `startDate` in all of them. Don't satisfy it
33
+ by hiding a clause in `fetchData`: a filter the user cannot see or clear makes rows go missing for no
34
+ visible reason. Seed the visible filter instead, so the default is applied, labelled and adjustable:
35
+
36
+ ```ts
37
+ const dateFilter = dateRangeFilter({
38
+ name: 'Date',
39
+ initialValue: { from: startOfDay(subDays(new Date(), 30)), to: null },
40
+ });
41
+ ```
42
+
43
+ `initialValue` is on every filter factory (`FilterStateBaseParams`), so the same trick seeds a status
44
+ or category default. Pick a window that matches the page's job — a booking review wants recent and
45
+ upcoming, an audit log wants the last 24 hours.
46
+
47
+ **A seeded default must not defeat search.** Search is a "find this anywhere" gesture, so a window
48
+ the user never chose silently hiding matches from it reads as broken search — a measured run shipped
49
+ exactly that, and the report was "search doesn't work", not "the date filter is too narrow". Bypass
50
+ the range while it is still the seeded value, and keep it once the user has set their own:
51
+
52
+ ```ts
53
+ const DEFAULT_FROM = startOfDayDaysAgo(30);
54
+ const isUntouchedDefault = (r?: { from?: Date; to?: Date }) =>
55
+ !r?.to && r?.from?.getTime() === DEFAULT_FROM.getTime();
56
+ // in fetchData AND fetchTotal:
57
+ dateRange: search?.trim() && isUntouchedDefault(range) ? undefined : range,
58
+ ```
59
+
60
+ Whatever a filter or a permission removes from the result, **say so in `noResultsState`** — "no
61
+ matches" and "no matches because a default you didn't set, or a scope you don't hold, excluded them"
62
+ look identical, and only the second is actionable.
63
+
64
+ Two traps the list resolves, both of which look like a working filter:
65
+
66
+ **Nested paths.** A field that reads as top-level on the entity is often only filterable at its full
67
+ path. Query Extended Bookings describes itself as filtering "by `scheduleId` of the relevant
68
+ service", and a bare `scheduleId` is rejected outright — the accepted paths are nested under
69
+ `bookedEntity`. The error names the offending path exactly, so one call settles it:
70
+
71
+ ```json
72
+ { "code": "INVALID_FILTER", "data": { "unknownField": { "fieldPath": "scheduleId" } } }
73
+ ```
74
+
75
+ **Oneof branches.** When the entity has a oneof, one path covers only one branch, and a filter over
76
+ just that branch silently drops every row of the other kind — exactly as the row mapper has to
77
+ handle both. Cover them with `$or`, and check each branch separately before wiring it into a page:
78
+
79
+ ```ts
80
+ $or: [
81
+ { 'bookedEntity.item.slot.scheduleId': { $in: scheduleIds } },
82
+ { 'bookedEntity.item.schedule.scheduleId': { $in: scheduleIds } },
83
+ ]
84
+ ```
85
+
86
+ ## One operator per field
87
+
88
+ > "The filter is written in WQL, where each field takes a single operator, so conditions are
89
+ > combined with the logical operators instead: `$and` and `$or` take an array of expressions,
90
+ > `$not` takes one, and they can nest. They are WQL syntax, not field capabilities." — [WQL][wql]
91
+
92
+ A date range written the obvious way therefore fails, and the error quotes the whole object back as
93
+ the offending "operator", which reads like a parser bug and is actually the rule:
94
+
95
+ ```ts
96
+ { startDate: { $gte: from, $lte: to } } // INVALID_FILTER — unknownOperator
97
+ ```
98
+
99
+ Ranges are two clauses under `$and`; `$or` nests inside it:
100
+
101
+ ```ts
102
+ { $and: [
103
+ { status: { $in: statuses } },
104
+ { startDate: { $gte: from } },
105
+ { startDate: { $lte: to } },
106
+ { $or: [ /* the oneof branches */ ] },
107
+ ] }
108
+ ```
109
+
110
+ Build the filter as a list of clauses and wrap it at the end — return the bare clause when there is
111
+ only one, `{}` when there are none — rather than mutating one object and hoping the operators do not
112
+ collide. A page with several filters hits this the moment two of them apply at once, which is
113
+ usually after the single-filter case has already been called working. The full operator set —
114
+ including `$not`, `$nin`, `$exists`, `$isEmpty`, `$hasAll`, `$hasSome` — is in the [WQL article][wql].
115
+
116
+ ## A follow-up cursor page carries the cursor alone
117
+
118
+ The cursor already encodes the filter and sort of the query that produced it, so re-sending them is
119
+ rejected. This is not one API's quirk: it is stated on the `cursorPaging.cursor` field of every
120
+ generated Wix SDK that offers cursor paging — 46 of the 179 `auto_sdk_*` packages in one install —
121
+ in a standard sentence you can read before making a request:
122
+
123
+ > "Cursor token pointing to a page of results. Not used in the first request. Following requests use
124
+ > the cursor token and not `filter` or `sort`."
125
+
126
+ Build the first request and the follow-ups differently:
127
+
128
+ ```ts
129
+ const response = await ns.query(
130
+ query.cursor
131
+ ? { cursorPaging: { limit: query.limit, cursor: query.cursor } }
132
+ : { filter, sort, cursorPaging: { limit: query.limit } },
133
+ );
134
+ ```
135
+
136
+ Sending them together answers `"Invalid cursor. Sort or filter can not be specified together with
137
+ cursor"` — and because the collection retries, that renders as a spinner under the last row, which
138
+ reads as "still loading". What you return on the **last** page is the collection's own contract, and
139
+ has its own trap: [TABLE_STATE.md](TABLE_STATE.md#query-and-result-shapes).
140
+
141
+ Cursor mode also takes a separate `fetchTotal`, since a cursor-paged response carries no total.
142
+ Build its filter exactly as the page's, or the count disagrees with the rows it counts.
143
+
144
+ ## What `fetchTotal` is allowed to call
145
+
146
+ `fetchTotal: (query) => Promise<number>`. It has to resolve **a number from something that
147
+ counts** — and the obvious-looking source is not one. A cursor-paged response carries no total,
148
+ so `pagingMetadata.total` is `undefined` — and `undefined` reaches the collection as `0`.
149
+ `@wix/data` spells the rule out on `PagingMetadataV2.total`: "Returned if offset paging is used,
150
+ `returnTotalCount` is `true` in the request, and `tooManyToCount` is false." Read the field's own
151
+ doc comment in the SDK you are calling rather than assuming it is populated. That is the whole of the
152
+ "`SummaryBar` reads 0 while the table under it is full of rows" bug, and it survives review
153
+ because nothing throws and nothing fails to compile.
154
+
155
+ Use a real count, in this order:
156
+
157
+ ```ts
158
+ // 1. A CMS collection: `items.query(id)` returns a builder whose `.count()` is
159
+ // `Promise<number>` and honours the filter you put on it. Apply the page's
160
+ // filter with the same function fetchData uses, so the two cannot drift.
161
+ // (The standalone `items.count(id)` is marked @internal and takes no filter.)
162
+ const count{Feature} = (q: {Feature}Query): Promise<number> =>
163
+ apply{Feature}Filter(items.query(COLLECTION_ID), q).count();
164
+
165
+ // 2. A vertical SDK with its own count endpoint: call that — it already returns a number.
166
+
167
+ // 3. Offset paging only — ask for the count, then read it back:
168
+ const { pagingMetadata } = await ns.query({ paging: { limit, offset }, returnTotalCount: true });
169
+ return pagingMetadata?.total ?? 0; // `?? 0` is honest HERE: you asked for the count
170
+ ```
171
+
172
+ **If the API offers no count at all, omit `fetchTotal`.** `collection.total` then falls back to the
173
+ rows loaded so far, which is a real number you can label ("50 shown") instead of a confident `0`.
174
+ Never paper over the gap with `?? 0` on a field that is simply absent.
175
+
176
+ ## When a table will not settle
177
+
178
+ An extension runs in a cross-origin iframe whose console you cannot read, but its own `SummaryBar`
179
+ will happily display `state.collection.status.status`, a fetch counter and the last rejection
180
+ message. That is what turns "it spins" into a named error in one reload.
181
+
182
+ [wql]: https://dev.wix.com/docs/api-reference/articles/work-with-wix-apis/data-retrieval/about-the-wix-api-query-language
@@ -0,0 +1,133 @@
1
+ # Reading the state object `useTableCollection` hands you
2
+
3
+ > **Scope.** The [Component Docs Gate](../../SKILL.md) covers component *names and props*, and the
4
+ > package's own `TableState` declaration is the member list. This file covers only what that
5
+ > declaration cannot tell you: the plausible members that are absent from it, and the behaviour
6
+ > behind the ones that are there.
7
+
8
+ ## Why guessing here always fails
9
+
10
+ `useTableCollection()` returns a `TableState`. For the members themselves, read the declaration the
11
+ index names — `Read <pkgRoot>/dist/dts-bundle/index.json`, then its `file`. Reading them is not the
12
+ hard part; the hard part is that several plausible members don't exist at all, and one that does
13
+ means something other than its name suggests (see
14
+ [Four that bite in practice](#four-that-bite-in-practice)).
15
+
16
+ **One thing not to conclude from the docs bundle.** `dist/dts-bundle/` publishes `CollectionState`
17
+ as a stub:
18
+
19
+ ```ts
20
+ declare class CollectionState<T = any, F = any> { [key: string]: unknown }
21
+ ```
22
+
23
+ That is a documentation abridgement, not the declaration your code compiles against. `tsc` resolves
24
+ `dist/types/index.d.ts`, which re-exports the **fully typed** `CollectionState` from
25
+ `@wix/bex-core` — no index signature. So `state.collection.…` is properly typed, a wrong member is a
26
+ compile error at the access, and reading `state.collection.status.status` to debug a stuck table is
27
+ sound. See [WIX_PATTERNS_DOCS.md § 5](../WIX_PATTERNS_DOCS.md#5--traps-that-make-a-read-wrong).
28
+
29
+ Prefer a typed member on `TableState` itself anyway — it is the object the hook hands you, and the
30
+ table's own view of the collection.
31
+
32
+ ## Four that bite in practice
33
+
34
+ **`state.filters` does not exist.** Filter state lives on the filter objects you created with
35
+ `stringsArrayFilter()` / `dateRangeFilter()` and passed into `filters`. Keep those in module-level
36
+ consts and reference the const in both the hook config and the JSX — that is also what
37
+ `MultiSelectCheckboxFilter`'s `filter` prop wants.
38
+
39
+ **`showLoadingState` is not "the query is running".** It stays `true` when the query resolves with
40
+ zero rows, so binding `SummaryBar`'s `status` to it leaves the bar on skeleton pills permanently on
41
+ an empty collection — which reads as a hung network rather than an empty result. Use
42
+ `state.showErrorState ? 'error' : 'success'`.
43
+
44
+ **`collection.isLoading` and `collection.refresh()` are not members.** They look plausible, they
45
+ compile against the index signature, and neither exists at runtime.
46
+
47
+ ### A `fetchTotal` that resolves undefined shows 0, not the rows
48
+
49
+ This is the "`SummaryBar` says 0 while the table under it is full" report, and it is worth tracing
50
+ once because every step is silent. `FetchTotalState` wraps your function in a second, one-item
51
+ collection whose page is literally `{ items: [], total: await fetchTotal(query) }`. That page then
52
+ goes through `CollectionState.updateResult`, which computes
53
+ `lastPage.total ?? lastPage.items.length` — so a `total` of `undefined` becomes `0`, because the
54
+ synthetic page has no items to fall back on. And `QueryResultState.total` reads
55
+ `fetchTotal ? fetchTotal.total : this._totals.processed`: **the moment `fetchTotal` exists it wins,
56
+ and the loaded-rows fallback is gone.**
57
+
58
+ Two consequences worth keeping in mind:
59
+
60
+ - **A wrong `fetchTotal` is worse than no `fetchTotal`.** Omit it and `total` degrades to the rows
61
+ you have; wire it to something that resolves `undefined` and a page with 4,000 matching rows
62
+ reports `0`. Nothing throws, nothing fails `tsc`, and the table beside it is correct.
63
+ - **`pagingMetadata.total` is not a count.** A cursor-paged response carries no total, and
64
+ `@wix/data` documents the field as returned only under *offset* paging with
65
+ `returnTotalCount: true`. Under the cursor paging these pages default to, expect `undefined`.
66
+ Call something that counts —
67
+ [QUERY_AND_PAGING.md](QUERY_AND_PAGING.md#what-fetchtotal-is-allowed-to-call).
68
+
69
+ To tell the two apart in a running page, show `state.collection.totalStatus` next to the number:
70
+ it is the totals collection's own status, so a `success` beside a `0` means your function resolved
71
+ nothing, not that the query failed.
72
+
73
+ ## Reading state outside the table: it is MobX
74
+
75
+ `@wix/patterns` depends on `mobx` and `mobx-react-lite`, so the state object is observable and a
76
+ plain React component does not track it. Anything you derive from `state` in your own component —
77
+ a `SummaryBar` count, a badge total, a header figure — is computed once on first render, when the
78
+ collection is still empty, and never recomputed. The table itself updates because it observes
79
+ internally; your derived numbers sit at zero next to a table full of rows, which reads as a bug in
80
+ the query rather than in the wiring.
81
+
82
+ `useSelector` from `@wix/patterns` subscribes:
83
+
84
+ ```tsx
85
+ const loadedCount = useSelector(() => state.keyedItems.length);
86
+ const rows = useMemo(() => state.keyedItems.map((k) => k.item), [loadedCount]);
87
+ ```
88
+
89
+ **Select a primitive.** Returning a fresh array or object from the selector gives it a new identity
90
+ on every evaluation. Select a length, a total or an id, then derive the rest once it fires.
91
+
92
+ ## Query and result shapes
93
+
94
+ `fetchData(query)` receives a `ComputedQuery<F>`: `limit`, `offset`, `page`, `search`, `rawSearch`,
95
+ `cursor`, `filters`, `rawFilters`, `sort`.
96
+
97
+ **Read the return type from `@wix/bex-core`, not from `@wix/patterns`.** The name
98
+ `CursorQueryResult` exists in both packages and they are different types. The one your `fetchData`
99
+ must satisfy is the generic in `node_modules/@wix/bex-core/dist/types/hooks/paginationModeConfig.d.ts`:
100
+
101
+ ```ts
102
+ interface DataResultRaw<T> {
103
+ items: T[];
104
+ total?: number | null;
105
+ available?: number; // total BEFORE filters
106
+ cursor?: string | undefined | null;
107
+ hasNext?: boolean | null;
108
+ }
109
+ type OffsetQueryResult<T> = Omit<DataResultRaw<T>, 'cursor'>;
110
+ type CursorQueryResult<T> = Omit<DataResultRaw<T>, 'cursor'> & { cursor: string | undefined | null };
111
+ ```
112
+
113
+ Three consequences, each of which has shipped as a bug:
114
+
115
+ **In cursor mode the `cursor` key is required; its value may be `undefined`.** The intersection
116
+ re-declares `cursor` without `?`, so `return { items }` does not compile — but
117
+ `{ items, cursor: undefined }` does. "Required" is about the key, not the value.
118
+
119
+ **On the last page return `undefined`, never `''`.** An empty string is still a cursor to the
120
+ collection: it requests the next page forever and appends the same rows each pass, a table that
121
+ grows without end while the API is perfectly happy, rendering as a spinner under the last row that
122
+ reads as "still loading". Derive it so the empty case collapses:
123
+
124
+ ```ts
125
+ cursor: response.pagingMetadata?.cursors?.next || undefined,
126
+ ```
127
+
128
+ **`hasNext` and `total` exist in both modes** — they are on `DataResultRaw`, which both aliases
129
+ extend. Cursor mode also accepts a separate `fetchTotal`, since a cursor-paged response carries no
130
+ total; build its filter exactly as the page's or the count disagrees with the rows it counts.
131
+
132
+ Look any of these up yourself with `Read <pkgRoot>/dist/dts-bundle/index.json` and the `file` path it
133
+ gives; the index is the single source of truth, and it moves between versions.
@@ -124,12 +124,17 @@ Choose the smallest interface that gives users enough context and room to comple
124
124
 
125
125
  | Interface | Use when… | Success looks like… |
126
126
  |---|---|---|
127
- | **Side panel** | The user should review or update one item while keeping the dashboard visible. | Context is preserved while deeper work remains focused. |
128
- | **Modal** | The user needs to complete a focused, bounded task or decision. | Attention stays on one task and the user can return cleanly. |
129
- | **Entity page** | The task involves complex details, multi-section editing, history, or related information. | The user has enough space and structure to complete deeper work. |
130
- | **Inline or expanded row** | The user needs a quick inspection or simple action. | Detail appears without creating a separate workspace. |
127
+ | **Entity page** | The item is editable — the default for a business record. | Enough space and structure to complete deeper work. |
128
+ | **Read-only detail page** | The collection is display-only. | Fully readable, linkable, one back-click from the list. |
129
+ | **Modal** | A focused, bounded task that is not "open this record". | Attention stays on one task; the user returns cleanly. |
130
+ | **Inline or expanded row** | A quick look *alongside* the drill-in, not instead of it. | Detail appears without a separate workspace. |
131
131
 
132
- Which Wix primitive builds each of these — and which components serve the summaries, filters and empty states named above — is in the installed package's `Collection Toolkit.md` guide — reached through [The Discovery Chain](../WIX_PATTERNS_DOCS.md#the-discovery-chain). Patterns has no side panel; that one is WDS.
132
+ Opening an item is a **route**, editable or not — a constraint, not a preference, and it outranks
133
+ "smallest interface". A side panel is not one of the choices: in Cairo it hosts a page's own
134
+ panels. A display-only record still routes, just to a WDS `Page`, since `EntityPage` has no view
135
+ mode.
136
+
137
+ Which Wix primitive builds each of these — and which components serve the summaries, filters and empty states named above — is in the installed package's `Collection Toolkit.md` guide — reached through [The Discovery Chain](../WIX_PATTERNS_DOCS.md#the-discovery-chain).
133
138
 
134
139
 
135
140
  ## Data Success
@@ -0,0 +1,68 @@
1
+ # Data Collection — getting it onto the site
2
+
3
+ > Declaring a collection is not the same as creating one. Releasing, updating the site, the CMS
4
+ > prerequisite, and what access the extension actually grants.
5
+
6
+ ## Item access and collection management are different scopes
7
+
8
+ The data-collections extension gives your app read/write access to the **items** in its own
9
+ collections — `items.query/insert/update` work with no extra scope. It does **not** grant the
10
+ collection-*management* API: `collections.listDataCollections()` and friends answer 403 unless the
11
+ app holds a Data Collections management scope.
12
+
13
+ That asymmetry is worth knowing before you debug: a page whose table loads rows has proved its
14
+ collection exists, because Wix Data errors on a missing collection rather than returning empty. If
15
+ that same page cannot list collections, the app is missing a management scope — a separate fact
16
+ about tooling, not evidence about the collection.
17
+
18
+ ## Reading the collection from a dashboard page
19
+
20
+ A page over a CMS collection is an ordinary collection page: the template is
21
+ [DRAFT_TEMPLATE_COLLECTION.md](../dashboard-page/DRAFT_TEMPLATE_COLLECTION.md), and its `fetchData`
22
+ calls `@wix/data` `items.query()` — see [WIX_DATA.md](WIX_DATA.md) for the query, result and paging
23
+ shapes. You write the filters and the columns yourself, exactly as for a vertical SDK.
24
+
25
+ ## The site must have CMS, or nothing is created at all
26
+
27
+ **The installing site needs the CMS (Content Manager) app.** Per the extension's own docs:
28
+ "Without it, collections added by the extension won't appear after installation." Nothing warns
29
+ you — the release succeeds, the update succeeds, and the collection silently never exists. Bundle
30
+ CMS as an [app dependency](https://dev.wix.com/docs/build-apps/launch-your-app/market-listing/add-app-dependencies)
31
+ so installing your app brings it, and list "add CMS to the site" under
32
+ [Manual Steps Required](../../SKILL.md#-manual-steps-required) for any site that may not have it.
33
+
34
+ This is the first thing to check when a collection is missing after a correct release and update.
35
+
36
+ ## The extension does not create the collection
37
+
38
+ Scaffolding the extension, compiling, and even releasing all leave the site's CMS unchanged.
39
+ A collection appears only when the app is **installed or updated on the site** with a version that
40
+ contains the extension — and any change under `data-collections/` needs a **major** version:
41
+
42
+ ```bash
43
+ npx wix release --version-type major -c "<what changed>"
44
+ ```
45
+
46
+ Releasing is only half of it. **Report both remaining browser steps under
47
+ [Manual Steps Required](../../SKILL.md#-manual-steps-required)** — they are the difference between a
48
+ page that works and one that shows an empty table:
49
+
50
+ 1. Update the app on the site to the new version.
51
+ 2. Wait up to 5 minutes for propagation.
52
+
53
+ A dev server running a version override does not create collections either, so "I ran `wix dev` and
54
+ the collection isn't in the CMS" is this step, not a bug.
55
+
56
+ ## App Version Updates
57
+
58
+ Changes to your data collections extension require releasing a new major version of your app. When a user updates to the new major version, their collections are updated as follows:
59
+
60
+ - **Adding a new collection:** The new collection is created on the site.
61
+ - **Removing a collection:** If the old app version defined a collection and the new version doesn't, the collection is removed from the site.
62
+ - **Modifying a collection schema:** Field additions, removals, and type changes are applied to the collection. Existing data is preserved.
63
+
64
+ **Important notes:**
65
+
66
+ - Collection changes only affect users who update to the new major version. Users who don't update retain their current collections.
67
+ - Collection changes take up to 5 minutes to propagate after an update.
68
+ - **Initial data is only imported when a collection is first created.** If a collection already contains data, `initialData` is ignored during updates.