@wix/auto-patterns 1.36.0 → 1.38.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 (172) hide show
  1. package/dist/cjs/components/AutoPatternsApp/AutoPatternsApp.js +1 -1
  2. package/dist/cjs/components/AutoPatternsCollectionComponent/AutoPatternsCollectionComponent.js +1 -1
  3. package/dist/cjs/components/AutoPatternsCollectionPage/AutoPatternsCollectionPage.js +1 -1
  4. package/dist/cjs/components/AutoPatternsCollectionPageContent/AutoPatternsCollectionPageContent.js +1 -1
  5. package/dist/cjs/components/AutoPatternsCollectionPageContent/SkeletonCollection.js +1 -1
  6. package/dist/cjs/components/AutoPatternsCollectionPageFooter/AutoPatternsCollectionPageFooter.js +1 -1
  7. package/dist/cjs/components/AutoPatternsEntityPage/AutoPatternsEntityPage.js +1 -1
  8. package/dist/cjs/components/AutoPatternsEntityPage/EditModeEntityPage.js +13 -9
  9. package/dist/cjs/components/AutoPatternsEntityPage/EditModeEntityPage.js.map +1 -1
  10. package/dist/cjs/components/AutoPatternsEntityPage/Fields/Checkbox.js +1 -1
  11. package/dist/cjs/components/AutoPatternsEntityPage/Fields/DateInput.js +1 -1
  12. package/dist/cjs/components/AutoPatternsEntityPage/Fields/DateTime.js +1 -1
  13. package/dist/cjs/components/AutoPatternsEntityPage/Fields/FormFieldInput.js +1 -1
  14. package/dist/cjs/components/AutoPatternsEntityPage/Fields/ImageInput.js +1 -1
  15. package/dist/cjs/components/AutoPatternsEntityPage/Fields/LongText.js +1 -1
  16. package/dist/cjs/components/AutoPatternsEntityPage/Fields/Number.js +1 -1
  17. package/dist/cjs/components/AutoPatternsEntityPage/Fields/ShortText.js +1 -1
  18. package/dist/cjs/components/AutoPatternsEntityPage/Fields/Url.js +1 -1
  19. package/dist/cjs/components/AutoPatternsEntityPage/RenderLayout/RenderLayoutCard.js +1 -1
  20. package/dist/cjs/components/AutoPatternsEntityPage/RenderLayout/RenderLayoutContent.js +1 -1
  21. package/dist/cjs/components/AutoPatternsEntityPage/RenderLayout/RenderViewField.js +1 -1
  22. package/dist/cjs/components/AutoPatternsEntityPage/SkeletonEntity.js +1 -1
  23. package/dist/cjs/components/AutoPatternsEntityPage/ViewEntityPage/RenderViewLayoutCard.js +1 -1
  24. package/dist/cjs/components/AutoPatternsEntityPage/ViewEntityPage/RenderViewLayoutContent.js +1 -1
  25. package/dist/cjs/components/AutoPatternsEntityPage/ViewModeEntityPage.js +1 -1
  26. package/dist/cjs/components/AutoPatternsGrid/AutoPatternsGrid.js +9 -6
  27. package/dist/cjs/components/AutoPatternsGrid/AutoPatternsGrid.js.map +1 -1
  28. package/dist/cjs/components/AutoPatternsRoute/AutoPatternsPage.js +1 -1
  29. package/dist/cjs/components/AutoPatternsRoute/AutoPatternsRoutes.js +1 -1
  30. package/dist/cjs/components/AutoPatternsTable/AutoPatternsTable.js +11 -6
  31. package/dist/cjs/components/AutoPatternsTable/AutoPatternsTable.js.map +1 -1
  32. package/dist/cjs/components/AutoPatternsTableGridSwitch/AutoPatternsTableGridSwitch.js +1 -1
  33. package/dist/cjs/components/DynamicIcon.js +1 -1
  34. package/dist/cjs/components/ModalRenderer.js +1 -1
  35. package/dist/cjs/components/filters/DynamicCollectionFilter.js +1 -1
  36. package/dist/cjs/components/filters/StaticCollectionFilter.js +1 -1
  37. package/dist/cjs/components/modals/actions/BulkDeleteModal.js +32 -14
  38. package/dist/cjs/components/modals/actions/BulkDeleteModal.js.map +1 -1
  39. package/dist/cjs/components/modals/actions/CreateModal.js +1 -1
  40. package/dist/cjs/components/modals/actions/EditModal.js +1 -1
  41. package/dist/cjs/counter.js +1 -1
  42. package/dist/cjs/dataSourceAdapters/cms/filterUtils.js +3 -2
  43. package/dist/cjs/dataSourceAdapters/cms/filterUtils.js.map +1 -1
  44. package/dist/cjs/dataSourceAdapters/cms/sortUtils.js +2 -1
  45. package/dist/cjs/dataSourceAdapters/cms/sortUtils.js.map +1 -1
  46. package/dist/cjs/hooks/useBaseTableFeatures.js +6 -3
  47. package/dist/cjs/hooks/useBaseTableFeatures.js.map +1 -1
  48. package/dist/cjs/hooks/useBulkActionToolbar.js +1 -1
  49. package/dist/cjs/hooks/useCollectionPageActions.js +1 -1
  50. package/dist/cjs/hooks/useColumns.js +6 -1
  51. package/dist/cjs/hooks/useColumns.js.map +1 -1
  52. package/dist/cjs/hooks/useCommonCollectionFeatures.js +1 -1
  53. package/dist/cjs/hooks/useDataExtensionProps.js +30 -0
  54. package/dist/cjs/hooks/useDataExtensionProps.js.map +1 -0
  55. package/dist/cjs/hooks/useDragAndDropBaseProps.js +30 -0
  56. package/dist/cjs/hooks/useDragAndDropBaseProps.js.map +1 -0
  57. package/dist/cjs/hooks/useEmptyStates.js +1 -1
  58. package/dist/cjs/hooks/useEntityPageActions.js +1 -1
  59. package/dist/cjs/hooks/useFilters.js +1 -1
  60. package/dist/cjs/hooks/useGridDragAndDrop.js +17 -0
  61. package/dist/cjs/hooks/useGridDragAndDrop.js.map +1 -0
  62. package/dist/cjs/hooks/useGridFeatures.js +4 -1
  63. package/dist/cjs/hooks/useGridFeatures.js.map +1 -1
  64. package/dist/cjs/hooks/useTableDragAndDrop.js +17 -0
  65. package/dist/cjs/hooks/useTableDragAndDrop.js.map +1 -0
  66. package/dist/cjs/hooks/useTableFeatures.js +7 -2
  67. package/dist/cjs/hooks/useTableFeatures.js.map +1 -1
  68. package/dist/cjs/hooks/useTableGridSwitchDragAndDrop.js +17 -0
  69. package/dist/cjs/hooks/useTableGridSwitchDragAndDrop.js.map +1 -0
  70. package/dist/cjs/hooks/useTableGridSwitchFeatures.js +7 -2
  71. package/dist/cjs/hooks/useTableGridSwitchFeatures.js.map +1 -1
  72. package/dist/cjs/providers/AppConfigContext.js +1 -1
  73. package/dist/cjs/providers/AppContext.js +1 -1
  74. package/dist/cjs/providers/AppContextData.js +1 -1
  75. package/dist/cjs/providers/AutoPatternsOverridesContext.js +2 -2
  76. package/dist/cjs/providers/AutoPatternsOverridesContext.js.map +1 -1
  77. package/dist/cjs/providers/ErrorContext.js +1 -1
  78. package/dist/cjs/providers/ItemsContext.js +1 -1
  79. package/dist/cjs/providers/ModalContext.js +1 -1
  80. package/dist/cjs/providers/OptimisticActionsContext.js +1 -1
  81. package/dist/cjs/providers/RootAppProvider.js +1 -1
  82. package/dist/cjs/providers/SchemaContext.js +1 -1
  83. package/dist/cjs/providers/SchemaRegistryContext.js +1 -1
  84. package/dist/cjs/types/CollectionPageConfig.js.map +1 -1
  85. package/dist/cjs/types/DeepPartial.js +4 -0
  86. package/dist/cjs/types/DeepPartial.js.map +1 -0
  87. package/dist/cjs/types/actions/base.js.map +1 -1
  88. package/dist/cjs/types/types.js.map +1 -1
  89. package/dist/cjs/utils/actions/bulkDeleteAction.js +1 -1
  90. package/dist/cjs/utils/actions/createAction.js +1 -1
  91. package/dist/cjs/utils/actions/deleteAction.js +1 -1
  92. package/dist/cjs/utils/actions/updateAction.js +1 -1
  93. package/dist/esm/components/AutoPatternsEntityPage/EditModeEntityPage.js +4 -0
  94. package/dist/esm/components/AutoPatternsEntityPage/EditModeEntityPage.js.map +1 -1
  95. package/dist/esm/components/AutoPatternsGrid/AutoPatternsGrid.js +7 -4
  96. package/dist/esm/components/AutoPatternsGrid/AutoPatternsGrid.js.map +1 -1
  97. package/dist/esm/components/AutoPatternsTable/AutoPatternsTable.js +9 -4
  98. package/dist/esm/components/AutoPatternsTable/AutoPatternsTable.js.map +1 -1
  99. package/dist/esm/components/modals/actions/BulkDeleteModal.js +25 -8
  100. package/dist/esm/components/modals/actions/BulkDeleteModal.js.map +1 -1
  101. package/dist/esm/dataSourceAdapters/cms/filterUtils.js +3 -2
  102. package/dist/esm/dataSourceAdapters/cms/filterUtils.js.map +1 -1
  103. package/dist/esm/dataSourceAdapters/cms/sortUtils.js +2 -1
  104. package/dist/esm/dataSourceAdapters/cms/sortUtils.js.map +1 -1
  105. package/dist/esm/hooks/useBaseTableFeatures.js +4 -1
  106. package/dist/esm/hooks/useBaseTableFeatures.js.map +1 -1
  107. package/dist/esm/hooks/useColumns.js +5 -0
  108. package/dist/esm/hooks/useColumns.js.map +1 -1
  109. package/dist/esm/hooks/useDataExtensionProps.js +18 -0
  110. package/dist/esm/hooks/useDataExtensionProps.js.map +1 -0
  111. package/dist/esm/hooks/useDragAndDropBaseProps.js +27 -0
  112. package/dist/esm/hooks/useDragAndDropBaseProps.js.map +1 -0
  113. package/dist/esm/hooks/useGridDragAndDrop.js +13 -0
  114. package/dist/esm/hooks/useGridDragAndDrop.js.map +1 -0
  115. package/dist/esm/hooks/useGridFeatures.js +4 -1
  116. package/dist/esm/hooks/useGridFeatures.js.map +1 -1
  117. package/dist/esm/hooks/useTableDragAndDrop.js +13 -0
  118. package/dist/esm/hooks/useTableDragAndDrop.js.map +1 -0
  119. package/dist/esm/hooks/useTableFeatures.js +7 -2
  120. package/dist/esm/hooks/useTableFeatures.js.map +1 -1
  121. package/dist/esm/hooks/useTableGridSwitchDragAndDrop.js +13 -0
  122. package/dist/esm/hooks/useTableGridSwitchDragAndDrop.js.map +1 -0
  123. package/dist/esm/hooks/useTableGridSwitchFeatures.js +7 -2
  124. package/dist/esm/hooks/useTableGridSwitchFeatures.js.map +1 -1
  125. package/dist/esm/providers/AutoPatternsOverridesContext.js.map +1 -1
  126. package/dist/esm/types/CollectionPageConfig.js.map +1 -1
  127. package/dist/esm/types/DeepPartial.js +2 -0
  128. package/dist/esm/types/DeepPartial.js.map +1 -0
  129. package/dist/esm/types/actions/base.js.map +1 -1
  130. package/dist/esm/types/types.js.map +1 -1
  131. package/dist/types/components/AutoPatternsEntityPage/EditModeEntityPage.d.ts.map +1 -1
  132. package/dist/types/components/AutoPatternsGrid/AutoPatternsGrid.d.ts.map +1 -1
  133. package/dist/types/components/AutoPatternsTable/AutoPatternsTable.d.ts.map +1 -1
  134. package/dist/types/components/modals/actions/BulkDeleteModal.d.ts.map +1 -1
  135. package/dist/types/hooks/useBaseTableFeatures.d.ts +10 -0
  136. package/dist/types/hooks/useBaseTableFeatures.d.ts.map +1 -1
  137. package/dist/types/hooks/useColumns.d.ts.map +1 -1
  138. package/dist/types/hooks/useDataExtensionProps.d.ts +8 -0
  139. package/dist/types/hooks/useDataExtensionProps.d.ts.map +1 -0
  140. package/dist/types/hooks/useDragAndDropBaseProps.d.ts +4 -0
  141. package/dist/types/hooks/useDragAndDropBaseProps.d.ts.map +1 -0
  142. package/dist/types/hooks/useGridDragAndDrop.d.ts +24 -0
  143. package/dist/types/hooks/useGridDragAndDrop.d.ts.map +1 -0
  144. package/dist/types/hooks/useGridFeatures.d.ts +22 -0
  145. package/dist/types/hooks/useGridFeatures.d.ts.map +1 -1
  146. package/dist/types/hooks/useTableDragAndDrop.d.ts +3 -0
  147. package/dist/types/hooks/useTableDragAndDrop.d.ts.map +1 -0
  148. package/dist/types/hooks/useTableFeatures.d.ts +2 -0
  149. package/dist/types/hooks/useTableFeatures.d.ts.map +1 -1
  150. package/dist/types/hooks/useTableGridSwitchDragAndDrop.d.ts +27 -0
  151. package/dist/types/hooks/useTableGridSwitchDragAndDrop.d.ts.map +1 -0
  152. package/dist/types/hooks/useTableGridSwitchFeatures.d.ts +24 -0
  153. package/dist/types/hooks/useTableGridSwitchFeatures.d.ts.map +1 -1
  154. package/dist/types/providers/AutoPatternsOverridesContext.d.ts +6 -0
  155. package/dist/types/providers/AutoPatternsOverridesContext.d.ts.map +1 -1
  156. package/dist/types/types/CollectionPageConfig.d.ts +19 -0
  157. package/dist/types/types/CollectionPageConfig.d.ts.map +1 -1
  158. package/dist/types/types/DeepPartial.d.ts +4 -0
  159. package/dist/types/types/DeepPartial.d.ts.map +1 -0
  160. package/dist/types/types/actions/base.d.ts +5 -0
  161. package/dist/types/types/actions/base.d.ts.map +1 -1
  162. package/dist/types/types/types.d.ts +24 -1
  163. package/dist/types/types/types.d.ts.map +1 -1
  164. package/docs/GETTING_STARTED.md +99 -2
  165. package/mcp-docs/app_config_structure.md +15 -1
  166. package/mcp-docs/auto-patterns-guide.md +317 -80
  167. package/mcp-docs/bulk_actions.md +60 -0
  168. package/mcp-docs/collection_page.md +34 -0
  169. package/mcp-docs/custom_overrides.md +134 -54
  170. package/mcp-docs/schema_config.md +74 -25
  171. package/mcp-docs/wix_fqdn_custom_data_source.md +66 -11
  172. package/package.json +12 -12
@@ -311,7 +311,8 @@ export interface AppConfig {
311
311
  mode: 'modal'; // Currently only 'modal' is supported
312
312
  modal: {
313
313
  title?: {
314
- text: string; // Modal title
314
+ text?: string; // Static modal title
315
+ id?: string; // Dynamic title resolver ID
315
316
  };
316
317
  description?: {
317
318
  text: string; // Modal description
@@ -367,6 +368,15 @@ export interface AppConfig {
367
368
  id?: string; // Custom CTA ID
368
369
  };
369
370
  };
371
+ /**
372
+ * Drag and drop configuration.
373
+ */
374
+ dragAndDrop?: {
375
+ /**
376
+ * Whether drag and drop is enabled. When enabled, the [schema](./schema_config.md) must support a "move" action.
377
+ */
378
+ enabled: boolean;
379
+ };
370
380
  layout: [ // Array of layout items that define what components to render
371
381
  {
372
382
  type: 'Table'; // Layout item type for table rendering
@@ -382,10 +392,14 @@ export interface AppConfig {
382
392
  hideable?: boolean; // Whether column can be hidden
383
393
  defaultHidden?: boolean; // Whether column is hidden by default
384
394
  hiddenFromCustomColumnsSelection?: boolean; // Whether column is hidden from custom columns selection
395
+ tooltipContent?: string; // Tooltip content to display when hovering over the info icon in the column header
385
396
  }[];
386
397
  customColumns?: {
387
398
  enabled: boolean; // Enable user customization (hide/reorder columns)
388
399
  };
400
+ dataExtension?: {
401
+ enabled: boolean; // Enable data extension
402
+ };
389
403
  stickyColumns?: number; // Number of columns to make sticky from the start. Sticky columns remain visible when horizontally scrolling.
390
404
  showTitleBar?: boolean; // Whether to show the table column headers. Default: true
391
405
  };
@@ -771,6 +785,40 @@ The `layout` array contains the rendering components for the collection. Each la
771
785
  * If the user does not specify, **select the most relevant fields automatically**.
772
786
  * For grid components, it is strongly recommended to implement a primary action cell with an `update` action that navigates to the entity page. This provides users with an intuitive way to access detailed information and edit individual entities directly from the grid view.
773
787
 
788
+ ## Column Tooltips
789
+
790
+ Add tooltips to column headers using the `tooltipContent` property. When provided, an info icon appears next to the column header that users can hover over to see the tooltip content.
791
+
792
+ Use tooltips to provide:
793
+ - **Explanations** - Help users understand what the column represents
794
+ - **Tools** - Provide guidance on how to use or interpret the column data
795
+ - **Additional information** - Offer context about the column's purpose, data format, or usage
796
+
797
+ ```json
798
+ {
799
+ "columns": [
800
+ {
801
+ "id": "name",
802
+ "name": "Name",
803
+ "width": "200px",
804
+ "tooltipContent": "The name of the pet"
805
+ },
806
+ {
807
+ "id": "age",
808
+ "name": "Age",
809
+ "width": "100px",
810
+ "tooltipContent": "Age in years. Use this to filter pets by age range."
811
+ },
812
+ {
813
+ "id": "lastVisit",
814
+ "name": "Last Visit",
815
+ "width": "150px",
816
+ "tooltipContent": "Date of the pet's last veterinary visit. Click to sort by most recent visits."
817
+ }
818
+ ]
819
+ }
820
+ ```
821
+
774
822
  ---
775
823
 
776
824
  # Collection Page Actions
@@ -1350,19 +1398,47 @@ export interface SchemaConfig {
1350
1398
  | { items: any[]; cursor?: string | null; total?: number | null }
1351
1399
  | { items: any[]; hasNext?: boolean; total?: number | null }
1352
1400
  >;
1401
+ /**
1402
+ * Reorder an entity within the collection.
1403
+ * @param id The ID of the entity to move.
1404
+ * @param params.moveAfterId The ID of the entity that should precede the moved entity, or null/undefined to move to start.
1405
+ */
1406
+ move?: (
1407
+ id: string,
1408
+ params: {
1409
+ moveAfterId: string | null | undefined;
1410
+ },
1411
+ ) => Promise<void>;
1353
1412
  };
1413
+ /**
1414
+ * Whether the entity supports data extensions
1415
+ * Maps to `info.extensible` in the collection schema - map only properties that are relevant or `null` if not extensible
1416
+ */
1417
+ extensible: {
1418
+ /**
1419
+ * Whether the entity supports filtering on data extensions
1420
+ * Maps to `info.extensible.filterable` in the collection schema
1421
+ */
1422
+ filterable?: boolean;
1423
+ } | null;
1424
+ /**
1425
+ * Whether the schema contains personally identifiable information (PII).
1426
+ * Maps to `info.containsPii` in the collection schema
1427
+ */
1428
+ containsPii: boolean;
1354
1429
  }
1355
1430
 
1356
1431
  export interface Query {
1357
- limit: number; // Maximum number of items to return per request (controls page size)
1358
- offset?: number; // Number of items to skip from the beginning (for pagination)
1359
- page: number; // Current page number (1-based, works with limit for pagination)
1360
- search?: string; // Text search query applied to searchable fields
1361
- cursor?: string | null; // Cursor-based pagination token (alternative to offset-based pagination)
1362
- filters: Record<string, any>; // Field-specific filter conditions (keys = field IDs, values = filter criteria)
1363
- sort?: { // Sorting configuration for result ordering
1364
- fieldName: string; // Field ID to sort by (must be sortable per field capabilities)
1365
- order: 'asc' | 'desc'; // Sort direction
1432
+ limit: number; // Maximum number of items to return per request (controls page size)
1433
+ offset?: number; // Number of items to skip from the beginning (for pagination)
1434
+ page: number; // Current page number (1-based, works with limit for pagination)
1435
+ search?: string; // Text search query applied to searchable fields
1436
+ cursor?: string | null; // Cursor-based pagination token (alternative to offset-based pagination)
1437
+ filters: Record<string, any>; // Field-specific filter conditions (keys = field IDs, values = filter criteria)
1438
+ sort?: {
1439
+ // Sorting configuration for result ordering
1440
+ fieldName: string; // Field ID to sort by (must be sortable per field capabilities)
1441
+ order: 'asc' | 'desc'; // Sort direction
1366
1442
  }[];
1367
1443
  }
1368
1444
  ```
@@ -1413,43 +1489,63 @@ export type Field = ReferenceField | NonReferenceField;
1413
1489
  ### Key Properties
1414
1490
 
1415
1491
  • **id** - `string`
1416
- - Collection identifier (e.g., "WixPets")
1417
- - Example: `schema.id === "WixPets"`
1492
+
1493
+ - Collection identifier (e.g., "WixPets")
1494
+ - Example: `schema.id === "WixPets"`
1418
1495
 
1419
1496
  • **idField** - `string`
1420
- - Primary key field name (usually "_id")
1421
- - Required for all update/delete operations
1422
- - Example: `const id = item[schema.idField]`
1497
+
1498
+ - Primary key field name (usually "\_id")
1499
+ - Required for all update/delete operations
1500
+ - Example: `const id = item[schema.idField]`
1423
1501
 
1424
1502
  • **displayField** - `string`
1425
- - Main field for displaying items (name, title, etc.)
1426
- - Used in UI components for item identification
1427
- - Example: `const label = item[schema.displayField]`
1503
+
1504
+ - Main field for displaying items (name, title, etc.)
1505
+ - Used in UI components for item identification
1506
+ - Example: `const label = item[schema.displayField]`
1428
1507
 
1429
1508
  • **fields** - `Record<string, Field | undefined>`
1430
- - Complete field definitions with types and metadata
1431
- - Useful for dynamic form generation or validation
1432
- - Each field contains type information, validation rules, and capabilities
1433
- - Example: `schema.fields.name.type === 'SHORT_TEXT'`
1509
+
1510
+ - Complete field definitions with types and metadata
1511
+ - Useful for dynamic form generation or validation
1512
+ - Each field contains type information, validation rules, and capabilities
1513
+ - Example: `schema.fields.name.type === 'SHORT_TEXT'`
1434
1514
 
1435
1515
  • **actions** - Server operation functions
1436
- - Pre-configured API calls for CRUD operations
1437
- - Use with optimistic actions for best UX
1438
- - All actions return Promises and handle server communication
1439
- - Example: `await schema.actions.update(item)`
1516
+
1517
+ - Pre-configured API calls for CRUD operations
1518
+ - Use with optimistic actions for best UX
1519
+ - All actions return Promises and handle server communication
1520
+ - Example: `await schema.actions.update(item)`
1521
+
1522
+ • **extensible** - `object | null`
1523
+
1524
+ - Indicates if the entity supports data extensions
1525
+
1526
+ • **extensible.filterable** - `boolean | undefined`
1527
+
1528
+ - Indicates if filtering on data extensions is supported
1529
+
1530
+ • **containsPii** - `boolean`
1531
+
1532
+ - Indicates if the schema contains personally identifiable information (PII)
1440
1533
 
1441
1534
  ### Available Schema Actions
1442
1535
 
1443
1536
  #### Individual Entity Operations
1537
+
1444
1538
  - **schema.actions.get(entityId)** - Retrieve a single entity by ID
1445
1539
  - **schema.actions.create(newEntity)** - Create a new entity
1446
1540
  - **schema.actions.update(updatedEntity)** - Update an existing entity
1447
1541
  - **schema.actions.delete(entityId)** - Delete a single entity by ID
1448
1542
 
1449
1543
  #### Bulk Operations
1544
+
1450
1545
  - **schema.actions.bulkDelete(entityIds)** - Delete multiple entities by their IDs
1451
1546
 
1452
1547
  #### Query Operations
1548
+
1453
1549
  - **schema.actions.find(query, options)** - Search and filter entities
1454
1550
  - `query`: Query object with pagination, filtering, sorting, and search criteria (see Query Interface section)
1455
1551
  - `options.searchableFieldIds`: Array of field IDs that support text search
@@ -1476,6 +1572,7 @@ Each field in the `fields` record contains:
1476
1572
  ### Reference Fields
1477
1573
 
1478
1574
  Reference fields have additional metadata:
1575
+
1479
1576
  - **referenceMetadata.referencedCollectionId**: ID of the collection being referenced
1480
1577
  - Used for establishing relationships between different collections
1481
1578
 
@@ -1877,6 +1974,66 @@ Bulk delete actions remove multiple entities with a confirmation modal.
1877
1974
  2. `bulkDelete.modal` object must exist
1878
1975
  3. The modal properties (title, description, actions, feedback) are all optional
1879
1976
 
1977
+ #### Dynamic Modal Titles
1978
+
1979
+ Bulk delete modal titles can be made dynamic to reflect the number and type of selected items.
1980
+
1981
+ **Configuration**
1982
+
1983
+ Use the `title.id` property to reference a dynamic title resolver:
1984
+
1985
+ ```typescript
1986
+ bulkActionToolbar: {
1987
+ primaryActions: [{
1988
+ type: 'action',
1989
+ action: {
1990
+ item: {
1991
+ id: 'bulkDelete',
1992
+ type: 'bulkDelete',
1993
+ bulkDelete: {
1994
+ mode: 'modal',
1995
+ modal: {
1996
+ title: {
1997
+ id: 'dynamicDeleteTitle' // References override function
1998
+ },
1999
+ // ... other modal config
2000
+ }
2001
+ }
2002
+ }
2003
+ }
2004
+ }]
2005
+ }
2006
+ ```
2007
+
2008
+ **Implementation**
2009
+
2010
+ Create a title resolver function in your overrides:
2011
+
2012
+ ```typescript
2013
+ const useBulkDeleteModalTitle = () => ({
2014
+ dynamicDeleteTitle: ({ selectedCount, selectedValues }) => ({
2015
+ text: `Delete ${selectedCount} ${selectedCount === 1 ? 'item' : 'items'}?`
2016
+ }),
2017
+ });
2018
+
2019
+ const bulkDeleteModalTitle = useBulkDeleteModalTitle();
2020
+ // In your page component
2021
+ <AutoPatternsOverridesProvider
2022
+ value={{
2023
+ bulkDeleteModalTitle,
2024
+ // ... other overrides
2025
+ }}
2026
+ >
2027
+ <AutoPatternsApp configuration={config} />
2028
+ </AutoPatternsOverridesProvider>
2029
+ ```
2030
+
2031
+ **Parameters**
2032
+
2033
+ The title resolver function receives:
2034
+ - `selectedCount: number` - Total number of selected items
2035
+ - `selectedValues: any[]` - Array of selected item objects
2036
+
1880
2037
  ### Custom Bulk Action Configuration
1881
2038
 
1882
2039
  Custom bulk actions execute JavaScript code that you define for bulk operations. These actions receive parameters that give them access to selected entities data and utilities. Here's how to implement a custom bulk action:
@@ -3342,7 +3499,19 @@ export default function YourPage() {
3342
3499
  const entityPageHeaderBadges = useEntityPageHeaderBadges();
3343
3500
 
3344
3501
  return (
3345
- <AutoPatternsOverridesProvider value={{ actions, columns, slots, sections, components, modals, customDataSources, entityPageHeaderSubtitle, entityPageHeaderBadges }}>
3502
+ <AutoPatternsOverridesProvider
3503
+ value={{
3504
+ actions,
3505
+ columns,
3506
+ slots,
3507
+ sections,
3508
+ components,
3509
+ modals,
3510
+ customDataSources,
3511
+ entityPageHeaderSubtitle,
3512
+ entityPageHeaderBadges,
3513
+ }}
3514
+ >
3346
3515
  <AutoPatternsApp configuration={config} />
3347
3516
  </AutoPatternsOverridesProvider>
3348
3517
  );
@@ -3354,6 +3523,7 @@ export default function YourPage() {
3354
3523
  **When adding any new implementation (action, modal, column, slot, section or component), you MUST update the corresponding hook in the `index.tsx` file to include your new implementation.** The main page component uses these hooks, so they serve as the central export point for each type of override.
3355
3524
 
3356
3525
  For example:
3526
+
3357
3527
  - Adding a new action → Update `../components/actions/index.tsx` to include the new action in the `useActions` hook
3358
3528
  - Adding a new modal → Update `../components/modals/index.tsx` to include the new modal in the `useModals` hook
3359
3529
  - Adding a new column override → Update `../components/columns/index.tsx` to include the new column in the `useColumns` hook
@@ -3374,6 +3544,38 @@ Without updating the hook index files, your implementations won't be available t
3374
3544
  - Incorrect import paths or naming mismatches
3375
3545
  - Forgetting to import and use the hook in the main page component
3376
3546
 
3547
+ ## Bulk Delete Modal Titles
3548
+
3549
+ Dynamic title generation for bulk delete confirmation modals.
3550
+
3551
+ ```typescript
3552
+ bulkDeleteModalTitle?: Record<
3553
+ string,
3554
+ (params: { selectedCount: number; selectedValues: any[] }) => { text: string }
3555
+ >;
3556
+ ```
3557
+
3558
+ **Usage Example:**
3559
+ ```typescript
3560
+ const useBulkDeleteModalTitle = () => ({
3561
+ dynamicProductDelete: ({ selectedCount }) => ({
3562
+ text: `Delete ${selectedCount} ${selectedCount === 1 ? 'product' : 'products'}?`
3563
+ }),
3564
+ });
3565
+ ```
3566
+
3567
+ **Integration:**
3568
+ ```typescript
3569
+
3570
+ const bulkDeleteModalTitle = useBulkDeleteModalTitle();
3571
+
3572
+ <AutoPatternsOverridesProvider
3573
+ value={{
3574
+ bulkDeleteModalTitle,
3575
+ }}
3576
+ >
3577
+ ```
3578
+
3377
3579
  ## Columns
3378
3580
 
3379
3581
  Each column in the table has a default rendering based on its field type. You can override this rendering by providing a custom function for the `column.id`. This allows you to customize how specific columns are displayed.
@@ -3405,8 +3607,8 @@ import { Badge } from '@wix/design-system';
3405
3607
 
3406
3608
  /* The `IColumnValue<T>` interface provides type safety for column override functions: */
3407
3609
  interface IColumnValue<T> {
3408
- value: T; // The individual column value (strongly typed)
3409
- row: Record<string, any>; // The entire row object with all field values
3610
+ value: T; // The individual column value (strongly typed)
3611
+ row: Record<string, any>; // The entire row object with all field values
3410
3612
  }
3411
3613
 
3412
3614
  // For TEXT fields
@@ -3417,9 +3619,7 @@ export function petName({ value, row }: IColumnValue<string>) {
3417
3619
  // For NUMBER fields
3418
3620
  export function age({ value, row }: IColumnValue<number>) {
3419
3621
  return (
3420
- <Badge skin={value > 5 ? 'warning' : 'success'}>
3421
- {value} years old
3422
- </Badge>
3622
+ <Badge skin={value > 5 ? 'warning' : 'success'}>{value} years old</Badge>
3423
3623
  );
3424
3624
  }
3425
3625
 
@@ -3454,23 +3654,29 @@ export function hobbies({ value, row }: IColumnValue<string[]>) {
3454
3654
  **Important**: The `row` object contains all field values from the entity, where each property corresponds to a **field ID** from the collection schema. To access specific field values, use the exact field ID as defined in your collection schema.
3455
3655
 
3456
3656
  For example, if your collection schema has these fields:
3657
+
3457
3658
  ```json
3458
3659
  {
3459
3660
  "fields": [
3460
3661
  { "key": "name", "displayName": "Pet Name", "type": "TEXT" },
3461
3662
  { "key": "age", "displayName": "Age", "type": "NUMBER" },
3462
3663
  { "key": "isVaccinated", "displayName": "Vaccinated", "type": "BOOLEAN" },
3463
- { "key": "lastActivity", "displayName": "Last Activity", "type": "DATETIME" }
3664
+ {
3665
+ "key": "lastActivity",
3666
+ "displayName": "Last Activity",
3667
+ "type": "DATETIME"
3668
+ }
3464
3669
  ]
3465
3670
  }
3466
3671
  ```
3467
3672
 
3468
3673
  Then in your column override, you access these values using the field IDs:
3674
+
3469
3675
  ```typescript
3470
3676
  export function myColumn({ value, row }) {
3471
3677
  // Access field values using their schema field IDs
3472
- const petName = row.name; // "name" field ID
3473
- const petAge = row.age; // "age" field ID
3678
+ const petName = row.name; // "name" field ID
3679
+ const petAge = row.age; // "age" field ID
3474
3680
  const isVaccinated = row.isVaccinated; // "isVaccinated" field ID
3475
3681
  const lastActivity = row.lastActivity; // "lastActivity" field ID
3476
3682
 
@@ -3520,7 +3726,9 @@ export function petInfo({ value, row }: IColumnValue<string>) {
3520
3726
  {row.age} years old • {row.type}
3521
3727
  </Text>
3522
3728
  {row.isVaccinated && (
3523
- <Text size="tiny" skin="success">✓ Vaccinated</Text>
3729
+ <Text size="tiny" skin="success">
3730
+ ✓ Vaccinated
3731
+ </Text>
3524
3732
  )}
3525
3733
  </Box>
3526
3734
  );
@@ -3566,7 +3774,9 @@ import { IColumnValue } from '@wix/auto-patterns/types';
3566
3774
 
3567
3775
  export function date({ value, row }: IColumnValue<string>) {
3568
3776
  // Access to other row data for enhanced date formatting
3569
- const isRecent = row.lastActivity && new Date(row.lastActivity) > new Date(Date.now() - 7 * 24 * 60 * 60 * 1000);
3777
+ const isRecent =
3778
+ row.lastActivity &&
3779
+ new Date(row.lastActivity) > new Date(Date.now() - 7 * 24 * 60 * 60 * 1000);
3570
3780
 
3571
3781
  return (
3572
3782
  <span style={{ color: isRecent ? 'green' : 'inherit' }}>
@@ -3593,7 +3803,7 @@ export const useColumns = () => {
3593
3803
  petInfo,
3594
3804
  status,
3595
3805
  fullName,
3596
- date
3806
+ date,
3597
3807
  };
3598
3808
  };
3599
3809
  ```
@@ -3671,6 +3881,7 @@ These components can display custom UI elements like notifications, information
3671
3881
  ### 2. Field Rendering Overrides
3672
3882
 
3673
3883
  You can use custom components to override the default rendering of one or more fields. This allows you to:
3884
+
3674
3885
  - Apply custom validation logic
3675
3886
  - Create custom input components
3676
3887
  - Combine multiple fields into a single UI component
@@ -3685,6 +3896,7 @@ import { useController } from '@wix/auto-patterns/form'; // Always import from t
3685
3896
  ```
3686
3897
 
3687
3898
  The hook requires:
3899
+
3688
3900
  - **name**: The field name you want to edit (should match the schema field ID)
3689
3901
  - **control**: Retrieved from `form.control`
3690
3902
  - **defaultValue**: Set from `entity?.[fieldId]` when it exists
@@ -3728,7 +3940,6 @@ export const customNameField: FC<CustomComponentProps> = ({ form, entity }) => {
3728
3940
  };
3729
3941
  ```
3730
3942
 
3731
-
3732
3943
  ### Example: Standalone Component (Not Field-Specific)
3733
3944
 
3734
3945
  Custom components can also be used to add UI elements not tied to specific fields:
@@ -3745,8 +3956,8 @@ export const infoCard: FC<CustomComponentProps> = ({ entity }) => {
3745
3956
  <Box direction="vertical" gap={2}>
3746
3957
  <Text weight="bold">Important Information</Text>
3747
3958
  <Text>
3748
- This custom component can display additional information or functionality
3749
- that isn't directly tied to a specific field.
3959
+ This custom component can display additional information or
3960
+ functionality that isn't directly tied to a specific field.
3750
3961
  </Text>
3751
3962
  {entity?.isVaccinated ? (
3752
3963
  <Text skin="success">This pet is vaccinated</Text>
@@ -3772,7 +3983,7 @@ export const useComponents = () => {
3772
3983
  // You can access React context and other hooks here
3773
3984
  return {
3774
3985
  customNameField,
3775
- infoCard
3986
+ infoCard,
3776
3987
  };
3777
3988
  };
3778
3989
  ```
@@ -3837,9 +4048,7 @@ const CustomComponent: FC<CustomComponentProps> = ({ form, entity }) => {
3837
4048
  onChange={(e) => form.setValue('name', e.target.value)}
3838
4049
  />
3839
4050
 
3840
- {showSpecialMessage && (
3841
- <Text>Special message for special name!</Text>
3842
- )}
4051
+ {showSpecialMessage && <Text>Special message for special name!</Text>}
3843
4052
  </Box>
3844
4053
  );
3845
4054
  };
@@ -3859,18 +4068,16 @@ const CustomComponent: FC<CustomComponentProps> = ({ form, entity }) => {
3859
4068
  onChange={(e) => form.setValue('name', e.target.value)}
3860
4069
  />
3861
4070
 
3862
- {showSpecialMessage && (
3863
- <Text>Special message for special name!</Text>
3864
- )}
4071
+ {showSpecialMessage && <Text>Special message for special name!</Text>}
3865
4072
  </Box>
3866
4073
  );
3867
4074
  };
3868
4075
  ```
3869
4076
 
3870
-
3871
4077
  ##### When to Use the Entity Object
3872
4078
 
3873
4079
  The `entity` object is useful for:
4080
+
3874
4081
  - Setting initial values
3875
4082
  - Accessing read-only data that doesn't change
3876
4083
  - Comparing form state with original values (e.g., detecting if changes were made)
@@ -3883,7 +4090,7 @@ const CustomComponent: FC<CustomComponentProps> = ({ form, entity }) => {
3883
4090
  const controller = useController({
3884
4091
  name: 'name', // Field ID from the schema
3885
4092
  control: form.control,
3886
- defaultValue: entity?.name // Initialize from entity
4093
+ defaultValue: entity?.name, // Initialize from entity
3887
4094
  });
3888
4095
 
3889
4096
  // Use watch for reactive updates
@@ -3898,9 +4105,7 @@ const CustomComponent: FC<CustomComponentProps> = ({ form, entity }) => {
3898
4105
  onChange={(e) => controller.field.onChange(e.target.value)}
3899
4106
  />
3900
4107
  </FormField>
3901
- {hasChanges && (
3902
- <Text size="small">Original value: {entity?.name}</Text>
3903
- )}
4108
+ {hasChanges && <Text size="small">Original value: {entity?.name}</Text>}
3904
4109
  </Box>
3905
4110
  );
3906
4111
  };
@@ -3945,6 +4150,7 @@ When implementing a custom data source, you need to modify the `collection` conf
3945
4150
  }
3946
4151
  }
3947
4152
  ```
4153
+
3948
4154
  ## Sections
3949
4155
 
3950
4156
  Sections allow you to group table rows under section headers, making it easier to organize and navigate through large datasets. This feature is especially useful when you want to categorize entities by specific criteria.
@@ -3982,6 +4188,7 @@ To enable sections, add the `sections` configuration to your table configuration
3982
4188
  ```
3983
4189
 
3984
4190
  **Key Properties:**
4191
+
3985
4192
  - `entityTypeSource`: Must be set to `"custom"` instead of `"cms"`
3986
4193
  - `custom.id`: A unique identifier for your custom data source implementation
3987
4194
 
@@ -4008,6 +4215,7 @@ export default function YourPage() {
4008
4215
  #### Custom Data Source Function
4009
4216
 
4010
4217
  You must implement a custom data source function that:
4218
+
4011
4219
  - Takes `collectionId` and `context` parameters
4012
4220
  - Returns a Promise that resolves to a `SchemaConfig` object
4013
4221
  - The `SchemaConfig` object must include:
@@ -4023,8 +4231,12 @@ You must implement a custom data source function that:
4023
4231
  ### Example Implementation Structure
4024
4232
 
4025
4233
  ```tsx
4234
+ import { SchemaConfig } from '@wix/auto-patterns/types';
4026
4235
  // customDataSources/myCustomDataSource.ts
4027
- export const myCustomDataSource = async (collectionId: string, context: any) => {
4236
+ export const myCustomDataSource = async (
4237
+ collectionId: string,
4238
+ context: any,
4239
+ ): Promise<SchemaConfig> => {
4028
4240
  return {
4029
4241
  id: 'myCustomCollection',
4030
4242
  fields: {
@@ -4033,17 +4245,31 @@ export const myCustomDataSource = async (collectionId: string, context: any) =>
4033
4245
  displayField: 'name',
4034
4246
  idField: '_id',
4035
4247
  actions: {
4036
- get: async (entityId: string) => { /* Implementation */ },
4037
- create: async (newEntity: any) => { /* Implementation */ },
4038
- update: async (updatedEntity: any) => { /* Implementation */ },
4039
- delete: async (entityId: string) => { /* Implementation */ },
4040
- bulkDelete: async (entityIds: string[]) => { /* Implementation */ },
4041
- find: async (query: Query, options?: any) => { /* Implementation */ }
4042
- }
4248
+ get: async (entityId: string) => {
4249
+ /* Implementation */
4250
+ },
4251
+ create: async (newEntity: any) => {
4252
+ /* Implementation */
4253
+ },
4254
+ update: async (updatedEntity: any) => {
4255
+ /* Implementation */
4256
+ },
4257
+ delete: async (entityId: string) => {
4258
+ /* Implementation */
4259
+ },
4260
+ bulkDelete: async (entityIds: string[]) => {
4261
+ /* Implementation */
4262
+ },
4263
+ find: async (query: Query, options?: any) => {
4264
+ /* Implementation */
4265
+ },
4266
+ },
4043
4267
  };
4044
4268
  };
4045
4269
  ```
4046
4270
 
4271
+ > This is a simplified example of a custom data source implementation, do not use it as-is. You must implement the actual logic to connect to the FQDN schema.
4272
+
4047
4273
  ### Hook Implementation
4048
4274
 
4049
4275
  In `components/customDataSources/index.tsx`:
@@ -4054,7 +4280,7 @@ import { myCustomDataSource } from './myCustomDataSource';
4054
4280
  export const useCustomDataSources = () => {
4055
4281
  // You can access React context and other hooks here
4056
4282
  return {
4057
- myCustomDataSource
4283
+ myCustomDataSource,
4058
4284
  };
4059
4285
  };
4060
4286
  ```
@@ -4072,8 +4298,6 @@ When implementing custom data sources, you need to map your data source field ty
4072
4298
  - **Reference fields** → `'REFERENCE'`
4073
4299
  - **URL fields** → `'URL'`
4074
4300
 
4075
-
4076
-
4077
4301
  ### Validation Requirements
4078
4302
 
4079
4303
  - **Function Signature**: Custom data source must be a function with signature `(collectionId: string, context: any) => Promise<SchemaConfig>`
@@ -4130,7 +4354,7 @@ Section renderers are functions that determine how to group items and what infor
4130
4354
  #### Function Signature
4131
4355
 
4132
4356
  ```tsx
4133
- function sectionRenderer(item: any): Section
4357
+ function sectionRenderer(item: any): Section;
4134
4358
  ```
4135
4359
 
4136
4360
  Where `Section` is the interface from @wix/patterns (re-exported from auto-patterns):
@@ -4153,6 +4377,7 @@ interface Section {
4153
4377
  ```
4154
4378
 
4155
4379
  The section renderer receives an item and returns:
4380
+
4156
4381
  - **id**: A unique identifier for the section (items with the same id are grouped together)
4157
4382
  - **title**: The text displayed in the section header
4158
4383
  - **primaryAction** (optional): An action button displayed in the section header
@@ -4216,7 +4441,9 @@ export function groupByAgeAndVaccination(item: any): Section {
4216
4441
  badgeSkin = 'neutralLight';
4217
4442
  } else if (age >= 1 && age <= 5) {
4218
4443
  sectionId = isVaccinated ? 'young-vaccinated' : 'young-unvaccinated';
4219
- sectionTitle = `Young Adults (1-5 years) - ${isVaccinated ? 'Vaccinated' : 'Not Vaccinated'}`;
4444
+ sectionTitle = `Young Adults (1-5 years) - ${
4445
+ isVaccinated ? 'Vaccinated' : 'Not Vaccinated'
4446
+ }`;
4220
4447
  badgeSkin = isVaccinated ? 'light' : 'danger';
4221
4448
  } else {
4222
4449
  sectionId = 'seniors';
@@ -4227,13 +4454,16 @@ export function groupByAgeAndVaccination(item: any): Section {
4227
4454
  return {
4228
4455
  id: sectionId,
4229
4456
  title: sectionTitle,
4230
- primaryAction: age < 1 ? {
4231
- id: 'special-care',
4232
- label: 'Special Care Info',
4233
- onClick: () => {
4234
- // Show special care information for puppies
4235
- },
4236
- } : undefined,
4457
+ primaryAction:
4458
+ age < 1
4459
+ ? {
4460
+ id: 'special-care',
4461
+ label: 'Special Care Info',
4462
+ onClick: () => {
4463
+ // Show special care information for puppies
4464
+ },
4465
+ }
4466
+ : undefined,
4237
4467
  badge: {
4238
4468
  visible: true,
4239
4469
  skin: badgeSkin,
@@ -4253,7 +4483,7 @@ import * as actions from './components/actions';
4253
4483
 
4254
4484
  <AutoPatternsOverridesProvider value={{ sections, columns, actions }}>
4255
4485
  <AutoPatternsApp configuration={config} />
4256
- </AutoPatternsOverridesProvider>
4486
+ </AutoPatternsOverridesProvider>;
4257
4487
  ```
4258
4488
 
4259
4489
  ### Important Notes
@@ -4263,7 +4493,6 @@ import * as actions from './components/actions';
4263
4493
  - **Performance**: Section renderers are called for every item, so keep the logic lightweight.
4264
4494
  - **TableGridSwitch**: Sections work in both table and grid views when using TableGridSwitch.
4265
4495
 
4266
-
4267
4496
  By implementing sections, you can significantly improve the user experience when dealing with large datasets by providing logical groupings that make information easier to find and understand.
4268
4497
 
4269
4498
  ## Slots
@@ -4271,6 +4500,7 @@ By implementing sections, you can significantly improve the user experience when
4271
4500
  Slots allow you to inject custom React components into collection pages at specific points in the component hierarchy. Unlike other overrides that modify existing functionality, slots enable you to add entirely custom UI elements anywhere within the collection page components array.
4272
4501
 
4273
4502
  Slots are useful for:
4503
+
4274
4504
  - Adding custom banners or announcements above or below the table/grid
4275
4505
  - Inserting analytics widgets or dashboards
4276
4506
  - Adding custom promotional content
@@ -4288,6 +4518,7 @@ Slots are configured in the collection page configuration using the `CustomCompo
4288
4518
  ```
4289
4519
 
4290
4520
  **Key Properties:**
4521
+
4291
4522
  - `type`: Must be set to `"custom"` to identify this as a slot component
4292
4523
  - `id`: A unique identifier that maps to your slot component implementation
4293
4524
 
@@ -4321,6 +4552,7 @@ Slot components can be positioned anywhere within the `components` array of a co
4321
4552
  ```
4322
4553
 
4323
4554
  This configuration will render:
4555
+
4324
4556
  1. The custom `topBanner` component at the top
4325
4557
  2. The main collection component (table/grid) in the middle
4326
4558
  3. The custom `bottomStats` component at the bottom
@@ -4340,7 +4572,9 @@ export const TopBannerComponent: React.FC = () => {
4340
4572
  <Card>
4341
4573
  <Card.Content>
4342
4574
  <Box direction="vertical" gap={2}>
4343
- <Text size="large" weight="bold">Welcome to Pet Management</Text>
4575
+ <Text size="large" weight="bold">
4576
+ Welcome to Pet Management
4577
+ </Text>
4344
4578
  <Text>Manage all your pets from this central dashboard.</Text>
4345
4579
  <Button size="small">Get Started</Button>
4346
4580
  </Box>
@@ -4355,11 +4589,15 @@ export const BottomStatsComponent: React.FC = () => {
4355
4589
  <Card.Content>
4356
4590
  <Box direction="horizontal" gap={4}>
4357
4591
  <Box direction="vertical" gap={1}>
4358
- <Text size="large" weight="bold">47</Text>
4592
+ <Text size="large" weight="bold">
4593
+ 47
4594
+ </Text>
4359
4595
  <Text size="small">Total Pets</Text>
4360
4596
  </Box>
4361
4597
  <Box direction="vertical" gap={1}>
4362
- <Text size="large" weight="bold">12</Text>
4598
+ <Text size="large" weight="bold">
4599
+ 12
4600
+ </Text>
4363
4601
  <Text size="small">Available for Adoption</Text>
4364
4602
  </Box>
4365
4603
  </Box>
@@ -4381,7 +4619,7 @@ export const useSlots = () => {
4381
4619
  // You can access React context and other hooks here
4382
4620
  return {
4383
4621
  topBanner: TopBannerComponent,
4384
- bottomStats: BottomStatsComponent
4622
+ bottomStats: BottomStatsComponent,
4385
4623
  };
4386
4624
  };
4387
4625
  ```
@@ -4413,7 +4651,6 @@ export default function YourPage() {
4413
4651
  3. **Performance**: Slot components re-render with the page, so optimize for performance if needed
4414
4652
  4. **Styling**: Follow the design system patterns and responsive design principles
4415
4653
 
4416
-
4417
4654
  **Important:** Every time you create a new slot component, you must import it and add it to the `useSlots` hook return object in the `./components/slots/index.tsx` file. The key must match the `id` specified in your JSON configuration.
4418
4655
 
4419
4656
  Slots provide a powerful way to enhance collection pages with custom functionality while maintaining the structure and features of the AutoPatterns system.