@wix/auto-patterns 1.34.0 → 1.35.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/mcp-docs/action_cell.md +50 -2
- package/mcp-docs/auto-patterns-guide.md +611 -38
- package/mcp-docs/bulk_actions.md +78 -22
- package/mcp-docs/collection_page_actions.md +56 -2
- package/mcp-docs/custom_overrides.md +1 -0
- package/mcp-docs/entity_page_actions.md +78 -1
- package/mcp-docs/entity_page_view_actions.md +2 -0
- package/mcp-docs/error_handling.md +346 -11
- package/package.json +6 -6
|
@@ -870,7 +870,7 @@ Custom collection page actions execute JavaScript code that you define for colle
|
|
|
870
870
|
},
|
|
871
871
|
successToast: 'Collection exported successfully',
|
|
872
872
|
errorToast: (err, {retry}) => ({
|
|
873
|
-
|
|
873
|
+
text: 'Export failed',
|
|
874
874
|
action: { text: 'Retry', onClick: retry }
|
|
875
875
|
})
|
|
876
876
|
}
|
|
@@ -880,6 +880,60 @@ Custom collection page actions execute JavaScript code that you define for colle
|
|
|
880
880
|
};
|
|
881
881
|
```
|
|
882
882
|
|
|
883
|
+
**⚠️ CRITICAL: Error Handling for HTTP Requests**
|
|
884
|
+
|
|
885
|
+
The example above uses SDK methods which don't require error handling. However, if your custom collection action makes HTTP requests, you MUST follow the error handling patterns:
|
|
886
|
+
|
|
887
|
+
**For Wix HTTP requests (httpClient, wix/data, wix/stores):**
|
|
888
|
+
```typescript
|
|
889
|
+
import { errorHandler } from '@wix/essentials';
|
|
890
|
+
|
|
891
|
+
export const myCollectionAction: CustomActionCollectionPageActionResolver = (params) => {
|
|
892
|
+
const { actionParams, sdk } = params;
|
|
893
|
+
const { collectionId } = actionParams;
|
|
894
|
+
|
|
895
|
+
return {
|
|
896
|
+
label: 'My Collection Action',
|
|
897
|
+
icon: <MyIcon />,
|
|
898
|
+
onClick: () => {
|
|
899
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
900
|
+
errorHandler.withErrorHandler(
|
|
901
|
+
async () => {
|
|
902
|
+
const response = await httpClient.request(
|
|
903
|
+
myWixApiCall({ collectionId })
|
|
904
|
+
);
|
|
905
|
+
return response.data;
|
|
906
|
+
},
|
|
907
|
+
{}
|
|
908
|
+
);
|
|
909
|
+
},
|
|
910
|
+
biName: 'my-collection-action'
|
|
911
|
+
};
|
|
912
|
+
};
|
|
913
|
+
```
|
|
914
|
+
|
|
915
|
+
**For External API requests (fetch, axios, third-party):**
|
|
916
|
+
```typescript
|
|
917
|
+
export const myCollectionAction: CustomActionCollectionPageActionResolver = (params) => {
|
|
918
|
+
const { actionParams, sdk } = params;
|
|
919
|
+
const { collectionId } = actionParams;
|
|
920
|
+
|
|
921
|
+
return {
|
|
922
|
+
label: 'My Collection Action',
|
|
923
|
+
icon: <MyIcon />,
|
|
924
|
+
onClick: () => {
|
|
925
|
+
// ✅ CORRECT: External API call - NO errorHandler needed
|
|
926
|
+
fetch(`https://api.external-service.com/endpoint/${collectionId}`)
|
|
927
|
+
.then(response => response.json())
|
|
928
|
+
.then(data => console.log('External API response:', data));
|
|
929
|
+
},
|
|
930
|
+
biName: 'my-collection-action'
|
|
931
|
+
};
|
|
932
|
+
};
|
|
933
|
+
```
|
|
934
|
+
|
|
935
|
+
**Read the "Error Handling for HTTP Requests" section for complete guidance.**
|
|
936
|
+
|
|
883
937
|
3. Export your action in `actions/index.tsx`:
|
|
884
938
|
```typescript
|
|
885
939
|
import { exportCollection } from './exportCollection';
|
|
@@ -1096,7 +1150,7 @@ export const quickToggle: CustomActionCollectionPageActionOnRowClickResolver = (
|
|
|
1096
1150
|
},
|
|
1097
1151
|
successToast: `${item.name} toggled successfully`,
|
|
1098
1152
|
errorToast: (err, {retry}) => ({
|
|
1099
|
-
|
|
1153
|
+
text: 'Toggle failed',
|
|
1100
1154
|
action: { text: 'Retry', onClick: retry }
|
|
1101
1155
|
})
|
|
1102
1156
|
});
|
|
@@ -1492,6 +1546,7 @@ Both properties are optional, but at least one should be provided for the Action
|
|
|
1492
1546
|
- Browser interactions (alerts, downloads)
|
|
1493
1547
|
- Complex operations
|
|
1494
1548
|
- ⚠️ Requires implementation: Must register action in overrides
|
|
1549
|
+
- ⚠️ **CRITICAL: Error Handling Required** - When implementing custom actions that make HTTP requests, you MUST read the "Error Handling for HTTP Requests" section and apply the correct error handling patterns. Wix HTTP requests require `errorHandler.withErrorHandler`, while external API calls should NOT use errorHandler.
|
|
1495
1550
|
|
|
1496
1551
|
### Action Appearance: The `skin` Property
|
|
1497
1552
|
|
|
@@ -1591,7 +1646,7 @@ Custom actions execute JavaScript code that you define. These actions receive pa
|
|
|
1591
1646
|
},
|
|
1592
1647
|
successToast: 'Pet details downloaded',
|
|
1593
1648
|
errorToast: (err, {retry}) => ({
|
|
1594
|
-
|
|
1649
|
+
text: 'Download failed',
|
|
1595
1650
|
action: { text: 'Retry', onClick: retry }
|
|
1596
1651
|
})
|
|
1597
1652
|
});
|
|
@@ -1601,6 +1656,53 @@ Custom actions execute JavaScript code that you define. These actions receive pa
|
|
|
1601
1656
|
};
|
|
1602
1657
|
```
|
|
1603
1658
|
|
|
1659
|
+
**⚠️ CRITICAL: Error Handling for HTTP Requests**
|
|
1660
|
+
|
|
1661
|
+
The example above uses SDK methods which don't require error handling. However, if your custom action makes HTTP requests, you MUST follow the error handling patterns:
|
|
1662
|
+
|
|
1663
|
+
**For Wix HTTP requests (httpClient, wix/data, wix/stores):**
|
|
1664
|
+
```typescript
|
|
1665
|
+
import { errorHandler } from '@wix/essentials';
|
|
1666
|
+
|
|
1667
|
+
export const myAction: CustomActionCellSecondaryActionResolver = (params) => {
|
|
1668
|
+
return {
|
|
1669
|
+
label: 'My Action',
|
|
1670
|
+
icon: <MyIcon />,
|
|
1671
|
+
onClick: () => {
|
|
1672
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
1673
|
+
errorHandler.withErrorHandler(
|
|
1674
|
+
async () => {
|
|
1675
|
+
const response = await httpClient.request(
|
|
1676
|
+
myWixApiCall({ data: params.actionParams.item })
|
|
1677
|
+
);
|
|
1678
|
+
return response.data;
|
|
1679
|
+
},
|
|
1680
|
+
{}
|
|
1681
|
+
);
|
|
1682
|
+
},
|
|
1683
|
+
};
|
|
1684
|
+
};
|
|
1685
|
+
```
|
|
1686
|
+
|
|
1687
|
+
**For External API requests (fetch, axios, third-party):**
|
|
1688
|
+
```typescript
|
|
1689
|
+
export const myAction: CustomActionCellSecondaryActionResolver = (params) => {
|
|
1690
|
+
return {
|
|
1691
|
+
label: 'My Action',
|
|
1692
|
+
icon: <MyIcon />,
|
|
1693
|
+
onClick: () => {
|
|
1694
|
+
// ✅ CORRECT: External API call - NO errorHandler needed
|
|
1695
|
+
fetch('https://api.external-service.com/endpoint', {
|
|
1696
|
+
method: 'POST',
|
|
1697
|
+
body: JSON.stringify(params.actionParams.item)
|
|
1698
|
+
});
|
|
1699
|
+
},
|
|
1700
|
+
};
|
|
1701
|
+
};
|
|
1702
|
+
```
|
|
1703
|
+
|
|
1704
|
+
**Read the "Error Handling for HTTP Requests" section for complete guidance.**
|
|
1705
|
+
|
|
1604
1706
|
3. Export your action in `actions/index.tsx`:
|
|
1605
1707
|
```typescript
|
|
1606
1708
|
import { downloadPetDetails } from './downloadPetDetails';
|
|
@@ -1661,7 +1763,7 @@ Custom actions execute JavaScript code that you define. These actions receive pa
|
|
|
1661
1763
|
- Enable analytics tracking for user interactions
|
|
1662
1764
|
|
|
1663
1765
|
2. The implementation must return a `ResolvedAction` object with:
|
|
1664
|
-
- `label`: Text displayed for the action
|
|
1766
|
+
- `label`: Text displayed for the action
|
|
1665
1767
|
- `icon`: An Icon component from "@wix/wix-ui-icons-common"
|
|
1666
1768
|
- `onClick`: Handler function for the action
|
|
1667
1769
|
- `biName`: Business intelligence name for analytics tracking. Must match the `biName` in your action configuration (required)
|
|
@@ -1790,7 +1892,12 @@ Custom bulk actions execute JavaScript code that you define for bulk operations.
|
|
|
1790
1892
|
```
|
|
1791
1893
|
|
|
1792
1894
|
2. Create your bulk action handler in `bulkExportPets.tsx`:
|
|
1895
|
+
|
|
1896
|
+
**⚠️ CRITICAL: Before implementing, read the "Error Handling for HTTP Requests" section to understand when to use `errorHandler.withErrorHandler`.**
|
|
1897
|
+
|
|
1898
|
+
**Example 1: Bulk action with Wix API call (REQUIRES errorHandler)**
|
|
1793
1899
|
```typescript
|
|
1900
|
+
import { errorHandler } from '@wix/essentials';
|
|
1794
1901
|
import { CustomBulkActionsActionResolver } from '@wix/auto-patterns';
|
|
1795
1902
|
import { Download } from '@wix/wix-ui-icons-common';
|
|
1796
1903
|
import React from 'react';
|
|
@@ -1804,43 +1911,92 @@ Custom bulk actions execute JavaScript code that you define for bulk operations.
|
|
|
1804
1911
|
label: 'Export Selected',
|
|
1805
1912
|
icon: <Download />,
|
|
1806
1913
|
onClick: () => {
|
|
1807
|
-
//
|
|
1914
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
1915
|
+
errorHandler.withErrorHandler(
|
|
1916
|
+
async () => {
|
|
1917
|
+
const response = await httpClient.request(
|
|
1918
|
+
bulkExportPetsData({
|
|
1919
|
+
petIds: selectedValues.map(pet => pet.id),
|
|
1920
|
+
totalCount: total
|
|
1921
|
+
})
|
|
1922
|
+
);
|
|
1923
|
+
return response.data;
|
|
1924
|
+
},
|
|
1925
|
+
{}
|
|
1926
|
+
);
|
|
1927
|
+
},
|
|
1928
|
+
biName: 'bulk-export-pets-action' // MANDATORY: For analytics tracking
|
|
1929
|
+
};
|
|
1930
|
+
};
|
|
1931
|
+
```
|
|
1932
|
+
|
|
1933
|
+
**Example 2: Bulk action with External API call (NO errorHandler needed)**
|
|
1934
|
+
```typescript
|
|
1935
|
+
import { CustomBulkActionsActionResolver } from '@wix/auto-patterns';
|
|
1936
|
+
import { Download } from '@wix/wix-ui-icons-common';
|
|
1937
|
+
import React from 'react';
|
|
1938
|
+
|
|
1939
|
+
export const bulkExportPets: CustomBulkActionsActionResolver = (params) => {
|
|
1940
|
+
const { actionParams, sdk } = params;
|
|
1941
|
+
const { selectedValues, total } = actionParams;
|
|
1942
|
+
|
|
1943
|
+
return {
|
|
1944
|
+
label: 'Export Selected',
|
|
1945
|
+
icon: <Download />,
|
|
1946
|
+
onClick: () => {
|
|
1947
|
+
// ✅ CORRECT: External API call - NO errorHandler needed
|
|
1948
|
+
const exportData = selectedValues.map(pet => ({
|
|
1949
|
+
name: pet.name,
|
|
1950
|
+
age: pet.age,
|
|
1951
|
+
owner: pet.owner
|
|
1952
|
+
}));
|
|
1953
|
+
|
|
1954
|
+
// Create and download CSV
|
|
1955
|
+
const csv = exportData.map(row => Object.values(row).join(',')).join('\n');
|
|
1956
|
+
const blob = new Blob([csv], { type: 'text/csv' });
|
|
1957
|
+
const url = URL.createObjectURL(blob);
|
|
1958
|
+
const a = document.createElement('a');
|
|
1959
|
+
a.href = url;
|
|
1960
|
+
a.download = 'pets-export.csv';
|
|
1961
|
+
a.click();
|
|
1962
|
+
},
|
|
1963
|
+
biName: 'bulk-export-pets-action' // MANDATORY: For analytics tracking
|
|
1964
|
+
};
|
|
1965
|
+
};
|
|
1966
|
+
```
|
|
1967
|
+
|
|
1968
|
+
**Example 3: Bulk action using SDK methods (NO errorHandler needed)**
|
|
1969
|
+
```typescript
|
|
1970
|
+
import { CustomBulkActionsActionResolver } from '@wix/auto-patterns';
|
|
1971
|
+
import { Download } from '@wix/wix-ui-icons-common';
|
|
1972
|
+
import React from 'react';
|
|
1973
|
+
|
|
1974
|
+
export const bulkExportPets: CustomBulkActionsActionResolver = (params) => {
|
|
1975
|
+
const { actionParams, sdk } = params;
|
|
1976
|
+
const { selectedValues, total } = actionParams;
|
|
1977
|
+
|
|
1978
|
+
return {
|
|
1979
|
+
label: 'Export Selected',
|
|
1980
|
+
icon: <Download />,
|
|
1981
|
+
onClick: () => {
|
|
1982
|
+
// ✅ CORRECT: SDK methods - NO errorHandler needed
|
|
1808
1983
|
const optimisticActions = sdk.getOptimisticActions(sdk.collectionId);
|
|
1809
1984
|
const schema = sdk.getSchema(sdk.collectionId);
|
|
1810
1985
|
|
|
1811
|
-
// Example: Mark pets as exported
|
|
1812
1986
|
const updatedItems = selectedValues.map(item => ({
|
|
1813
1987
|
...item,
|
|
1814
1988
|
lastExported: new Date()
|
|
1815
1989
|
}));
|
|
1816
1990
|
optimisticActions.updateMany(updatedItems, {
|
|
1817
1991
|
submit: async (items) => {
|
|
1818
|
-
// Your export logic here + update server
|
|
1819
|
-
const exportData = items.map(pet => ({
|
|
1820
|
-
name: pet.name,
|
|
1821
|
-
age: pet.age,
|
|
1822
|
-
owner: pet.owner
|
|
1823
|
-
}));
|
|
1824
|
-
|
|
1825
|
-
// Create and download CSV
|
|
1826
|
-
const csv = exportData.map(row => Object.values(row).join(',')).join('\n');
|
|
1827
|
-
const blob = new Blob([csv], { type: 'text/csv' });
|
|
1828
|
-
const url = URL.createObjectURL(blob);
|
|
1829
|
-
const a = document.createElement('a');
|
|
1830
|
-
a.href = url;
|
|
1831
|
-
a.download = 'pets-export.csv';
|
|
1832
|
-
a.click();
|
|
1833
|
-
|
|
1834
|
-
// Update server with export timestamp
|
|
1835
|
-
// Handle potential undefined schema
|
|
1836
1992
|
if (schema) {
|
|
1837
1993
|
return await schema.actions.update(items);
|
|
1838
1994
|
}
|
|
1839
|
-
return items;
|
|
1995
|
+
return items;
|
|
1840
1996
|
},
|
|
1841
1997
|
successToast: `${selectedValues.length} pets exported`,
|
|
1842
1998
|
errorToast: (err, {retry}) => ({
|
|
1843
|
-
|
|
1999
|
+
text: 'Export failed',
|
|
1844
2000
|
action: { text: 'Retry', onClick: retry }
|
|
1845
2001
|
})
|
|
1846
2002
|
});
|
|
@@ -1850,6 +2006,8 @@ Custom bulk actions execute JavaScript code that you define for bulk operations.
|
|
|
1850
2006
|
};
|
|
1851
2007
|
```
|
|
1852
2008
|
|
|
2009
|
+
**Read the "Error Handling for HTTP Requests" section for complete guidance.**
|
|
2010
|
+
|
|
1853
2011
|
3. Export your action in `actions/index.tsx`:
|
|
1854
2012
|
```typescript
|
|
1855
2013
|
import { bulkExportPets } from './bulkExportPets';
|
|
@@ -2524,6 +2682,64 @@ The `CustomEntityPageActionResolver` type is used to implement custom actions fo
|
|
|
2524
2682
|
|
|
2525
2683
|
#### Function Signature
|
|
2526
2684
|
|
|
2685
|
+
**⚠️ CRITICAL: Before implementing, read the "Error Handling for HTTP Requests" section to understand when to use `errorHandler.withErrorHandler`.**
|
|
2686
|
+
|
|
2687
|
+
**Example 1: EntityPage action with Wix API call (REQUIRES errorHandler)**
|
|
2688
|
+
```typescript
|
|
2689
|
+
import { errorHandler } from '@wix/essentials';
|
|
2690
|
+
import { CustomEntityPageActionResolver } from '@wix/auto-patterns/types';
|
|
2691
|
+
|
|
2692
|
+
export const sendEmail: CustomEntityPageActionResolver = (params) => {
|
|
2693
|
+
const { actionParams: { entity, form } , sdk } = params;
|
|
2694
|
+
|
|
2695
|
+
return {
|
|
2696
|
+
label: 'Send Email',
|
|
2697
|
+
icon: <EmailIcon />, // required
|
|
2698
|
+
onClick: () => {
|
|
2699
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
2700
|
+
errorHandler.withErrorHandler(
|
|
2701
|
+
async () => {
|
|
2702
|
+
const response = await httpClient.request(
|
|
2703
|
+
sendEmailToEntity({ entityId: entity.id, email: entity.email })
|
|
2704
|
+
);
|
|
2705
|
+
return response.data;
|
|
2706
|
+
},
|
|
2707
|
+
{}
|
|
2708
|
+
);
|
|
2709
|
+
},
|
|
2710
|
+
biName: 'send-email-action' // MANDATORY: For analytics tracking
|
|
2711
|
+
};
|
|
2712
|
+
};
|
|
2713
|
+
```
|
|
2714
|
+
|
|
2715
|
+
**Example 2: EntityPage action with External API call (NO errorHandler needed)**
|
|
2716
|
+
```typescript
|
|
2717
|
+
import { CustomEntityPageActionResolver } from '@wix/auto-patterns/types';
|
|
2718
|
+
|
|
2719
|
+
export const exportData: CustomEntityPageActionResolver = (params) => {
|
|
2720
|
+
const { actionParams: { entity, form } , sdk } = params;
|
|
2721
|
+
|
|
2722
|
+
return {
|
|
2723
|
+
label: 'Export Data',
|
|
2724
|
+
icon: <ExportIcon />, // required
|
|
2725
|
+
onClick: () => {
|
|
2726
|
+
// ✅ CORRECT: External API call - NO errorHandler needed
|
|
2727
|
+
fetch(`https://api.external-service.com/export/${entity.id}`)
|
|
2728
|
+
.then(response => response.blob())
|
|
2729
|
+
.then(blob => {
|
|
2730
|
+
const url = URL.createObjectURL(blob);
|
|
2731
|
+
const a = document.createElement('a');
|
|
2732
|
+
a.href = url;
|
|
2733
|
+
a.download = `entity-${entity.id}.pdf`;
|
|
2734
|
+
a.click();
|
|
2735
|
+
});
|
|
2736
|
+
},
|
|
2737
|
+
biName: 'export-data-action' // MANDATORY: For analytics tracking
|
|
2738
|
+
};
|
|
2739
|
+
};
|
|
2740
|
+
```
|
|
2741
|
+
|
|
2742
|
+
**Example 3: EntityPage action using SDK methods (NO errorHandler needed)**
|
|
2527
2743
|
```typescript
|
|
2528
2744
|
import { CustomEntityPageActionResolver } from '@wix/auto-patterns/types';
|
|
2529
2745
|
|
|
@@ -2534,13 +2750,32 @@ export const myMoreAction: CustomEntityPageActionResolver = (params) => {
|
|
|
2534
2750
|
label: 'My More Action',
|
|
2535
2751
|
icon: <MyIcon />, // required
|
|
2536
2752
|
onClick: () => {
|
|
2537
|
-
//
|
|
2753
|
+
// ✅ CORRECT: SDK methods - NO errorHandler needed
|
|
2754
|
+
const optimisticActions = sdk.getOptimisticActions(sdk.collectionId);
|
|
2755
|
+
const schema = sdk.getSchema(sdk.collectionId);
|
|
2756
|
+
|
|
2757
|
+
const updatedEntity = { ...entity, lastAction: new Date() };
|
|
2758
|
+
optimisticActions.updateOne(updatedEntity, {
|
|
2759
|
+
submit: async (items) => {
|
|
2760
|
+
if (schema) {
|
|
2761
|
+
return await schema.actions.update(items[0]);
|
|
2762
|
+
}
|
|
2763
|
+
return items[0];
|
|
2764
|
+
},
|
|
2765
|
+
successToast: 'Action completed successfully',
|
|
2766
|
+
errorToast: (err, {retry}) => ({
|
|
2767
|
+
text: 'Action failed',
|
|
2768
|
+
action: { text: 'Retry', onClick: retry }
|
|
2769
|
+
})
|
|
2770
|
+
});
|
|
2538
2771
|
},
|
|
2539
2772
|
biName: 'my-more-action' // MANDATORY: For analytics tracking
|
|
2540
2773
|
};
|
|
2541
2774
|
};
|
|
2542
2775
|
```
|
|
2543
2776
|
|
|
2777
|
+
**Read the "Error Handling for HTTP Requests" section for complete guidance.**
|
|
2778
|
+
|
|
2544
2779
|
- **entity**: The current entity data (all field values). In actionParams.
|
|
2545
2780
|
- **form**: The react-hook-form instance for the entity page. In actionParams.
|
|
2546
2781
|
- **sdk**: The AutoPatterns SDK (see SDK Utilities section).
|
|
@@ -2580,6 +2815,8 @@ The `CustomEntityPageActionResolver` enables you to add custom, contextual actio
|
|
|
2580
2815
|
|
|
2581
2816
|
View mode supports the complete collection-style actions API, providing maximum flexibility for entity operations.
|
|
2582
2817
|
|
|
2818
|
+
**⚠️ CRITICAL: Error Handling for Custom Actions** - When implementing custom actions (type: "custom") in view mode, you MUST read the "Error Handling for HTTP Requests" section and apply the correct error handling patterns. Wix HTTP requests require `errorHandler.withErrorHandler`, while external API calls should NOT use errorHandler.
|
|
2819
|
+
|
|
2583
2820
|
## Supported Action Types
|
|
2584
2821
|
|
|
2585
2822
|
### Primary Actions
|
|
@@ -3027,6 +3264,7 @@ export const DataUpdateModal: React.FC = () => {
|
|
|
3027
3264
|
|
|
3028
3265
|
- **Custom overrides are restricted to the defined areas only** - attempting to override or modify any other aspect of `AutoPatternsApp` is prohibited and can cause unexpected behavior
|
|
3029
3266
|
- **Always verify override implementation** - when implementing custom overrides, you MUST ensure they are correctly imported and passed to the `AutoPatternsOverridesProvider`
|
|
3267
|
+
- **⚠️ CRITICAL: READ ERROR HANDLING DOCUMENTATION FIRST** - Before implementing ANY custom action (ActionCell, BulkActions, CollectionPage actions, EntityPage actions, or Custom Data Sources), you MUST read the "Error Handling for HTTP Requests" section and apply the correct error handling patterns. This is mandatory for all AI agents.
|
|
3030
3268
|
- **CRITICAL: Error handling for custom actions** - Custom actions that make external API calls (using `fetch()`, `axios`, etc.) should NOT use `errorHandler.withErrorHandler`. Only Wix HTTP requests (httpClient from @wix/essentials, Wix APIs like wix/data and wix/stores, and httpClient.fetchWithAuth()) require errorHandler wrapping. See the "Error Handling for HTTP Requests" section for details.
|
|
3031
3269
|
|
|
3032
3270
|
The `AutoPatternsOverridesProvider` allows you to inject custom code to override default behaviors or add additional functionality. Below are the areas where overrides can be applied:
|
|
@@ -4184,17 +4422,26 @@ Slots provide a powerful way to enhance collection pages with custom functionali
|
|
|
4184
4422
|
|
|
4185
4423
|
# Error Handling for HTTP Requests
|
|
4186
4424
|
|
|
4425
|
+
**⚠️ CRITICAL FOR AI AGENTS**: When creating or updating ANY custom actions (ActionCell, BulkActions, CollectionPage actions, EntityPage actions, or Custom Data Sources), you **MUST ALWAYS** read this error handling documentation first and apply the correct error handling patterns.
|
|
4426
|
+
|
|
4427
|
+
**⚠️ MANDATORY WORKFLOW FOR AI AGENTS:**
|
|
4428
|
+
1. **BEFORE** implementing any custom action, read this entire error handling documentation
|
|
4429
|
+
2. **IDENTIFY** what type of HTTP requests (if any) your action will make
|
|
4430
|
+
3. **APPLY** the correct error handling pattern based on the request type
|
|
4431
|
+
4. **VERIFY** your implementation follows the validation checklist below
|
|
4432
|
+
5. **NEVER** skip this process - it's critical for proper error handling
|
|
4433
|
+
|
|
4187
4434
|
**⚠️ CRITICAL**: When implementing custom data sources that make HTTP requests, you **MUST** wrap specific HTTP calls with proper error handling. This ensures consistent error management, prevents unhandled promise rejections, and provides better user experience.
|
|
4188
4435
|
|
|
4189
4436
|
## What Requires Error Handling
|
|
4190
4437
|
|
|
4191
|
-
**ONLY the following HTTP requests** in your custom data source actions must be wrapped with `errorHandler`:
|
|
4438
|
+
**ONLY the following HTTP requests** in your custom data source actions must be wrapped with `errorHandler.withErrorHandler`:
|
|
4192
4439
|
|
|
4193
4440
|
- **httpClient from @wix/essentials** (e.g., `httpClient.request(getDummyEntity(...))`)
|
|
4194
4441
|
- **Wix APIs** (e.g., `wix/data`, `wix/stores`, `items.get()`, `items.insert()`, `collections.getDataCollection()`)
|
|
4195
4442
|
- **httpClient.fetchWithAuth()** calls
|
|
4196
4443
|
|
|
4197
|
-
**DO NOT use errorHandler with:**
|
|
4444
|
+
**DO NOT use errorHandler.withErrorHandler with:**
|
|
4198
4445
|
|
|
4199
4446
|
- **External API calls** using `fetch()`, `axios.get()`, or other HTTP libraries
|
|
4200
4447
|
- **Custom HTTP clients** (e.g., any non-Wix HTTP request library)
|
|
@@ -4202,6 +4449,20 @@ Slots provide a powerful way to enhance collection pages with custom functionali
|
|
|
4202
4449
|
|
|
4203
4450
|
**EXCEPTION**: SDK actions that you get from the AutoPatterns SDK (e.g., `sdk.getOptimisticActions()`, `sdk.getSchema()`) do NOT need error handling as they are already handled internally.
|
|
4204
4451
|
|
|
4452
|
+
## ⚠️ CRITICAL: When to Apply Error Handling
|
|
4453
|
+
|
|
4454
|
+
**ALWAYS apply error handling when:**
|
|
4455
|
+
|
|
4456
|
+
1. **Creating Custom Data Sources** - All HTTP requests in data source actions must be wrapped
|
|
4457
|
+
2. **Implementing FQDN-based Custom Data Sources** - All Wix API calls must be wrapped
|
|
4458
|
+
3. **Making any Wix HTTP requests** in custom actions (ActionCell, BulkActions, etc.)
|
|
4459
|
+
|
|
4460
|
+
**NEVER apply error handling when:**
|
|
4461
|
+
|
|
4462
|
+
1. **Using external APIs** (fetch, axios, third-party libraries)
|
|
4463
|
+
2. **Using AutoPatterns SDK methods** (sdk.getOptimisticActions, sdk.getSchema, etc.)
|
|
4464
|
+
3. **Making non-HTTP operations** (local computations, form validations, etc.)
|
|
4465
|
+
|
|
4205
4466
|
## Why Error Handling is Required
|
|
4206
4467
|
|
|
4207
4468
|
Custom data sources often make HTTP requests to Wix APIs and services. Without proper error handling:
|
|
@@ -4225,7 +4486,7 @@ npm install @wix/essentials
|
|
|
4225
4486
|
|
|
4226
4487
|
### Basic Error Handling Pattern
|
|
4227
4488
|
|
|
4228
|
-
Wrap Wix HTTP requests in your custom data source actions with `errorHandler.withErrorHandler`:
|
|
4489
|
+
**⚠️ MANDATORY**: Wrap Wix HTTP requests in your custom data source actions with `errorHandler.withErrorHandler`:
|
|
4229
4490
|
|
|
4230
4491
|
```typescript
|
|
4231
4492
|
import { errorHandler } from '@wix/essentials';
|
|
@@ -4246,6 +4507,62 @@ actions: {
|
|
|
4246
4507
|
}
|
|
4247
4508
|
```
|
|
4248
4509
|
|
|
4510
|
+
### ⚠️ CRITICAL: Error Handling in Custom Actions
|
|
4511
|
+
|
|
4512
|
+
**When implementing ANY custom action (ActionCell, BulkActions, CollectionPage actions, EntityPage actions), you MUST:**
|
|
4513
|
+
|
|
4514
|
+
1. **Check if your action makes Wix HTTP requests**
|
|
4515
|
+
2. **If YES**: Wrap the HTTP request with `errorHandler.withErrorHandler`
|
|
4516
|
+
3. **If NO**: Do not use errorHandler (e.g., for external APIs, SDK methods, local operations)
|
|
4517
|
+
|
|
4518
|
+
**Example: Custom ActionCell with Wix API call**
|
|
4519
|
+
```typescript
|
|
4520
|
+
import { errorHandler } from '@wix/essentials';
|
|
4521
|
+
|
|
4522
|
+
export const myCustomAction: CustomActionCellActionResolver = (params) => {
|
|
4523
|
+
const { actionParams, sdk } = params;
|
|
4524
|
+
const { item } = actionParams;
|
|
4525
|
+
|
|
4526
|
+
return {
|
|
4527
|
+
label: 'Update Status',
|
|
4528
|
+
icon: <UpdateIcon />,
|
|
4529
|
+
onClick: () => {
|
|
4530
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
4531
|
+
errorHandler.withErrorHandler(
|
|
4532
|
+
async () => {
|
|
4533
|
+
const response = await httpClient.request(
|
|
4534
|
+
updateEntityStatus({ entityId: item.id, status: 'active' })
|
|
4535
|
+
);
|
|
4536
|
+
return response.data;
|
|
4537
|
+
},
|
|
4538
|
+
{}
|
|
4539
|
+
);
|
|
4540
|
+
},
|
|
4541
|
+
};
|
|
4542
|
+
};
|
|
4543
|
+
```
|
|
4544
|
+
|
|
4545
|
+
**Example: Custom ActionCell with External API call**
|
|
4546
|
+
```typescript
|
|
4547
|
+
export const myCustomAction: CustomActionCellActionResolver = (params) => {
|
|
4548
|
+
const { actionParams, sdk } = params;
|
|
4549
|
+
const { item } = actionParams;
|
|
4550
|
+
|
|
4551
|
+
return {
|
|
4552
|
+
label: 'Send to External Service',
|
|
4553
|
+
icon: <SendIcon />,
|
|
4554
|
+
onClick: () => {
|
|
4555
|
+
// ✅ CORRECT: External API call - NO errorHandler needed
|
|
4556
|
+
fetch('https://api.external-service.com/send', {
|
|
4557
|
+
method: 'POST',
|
|
4558
|
+
body: JSON.stringify({ data: item }),
|
|
4559
|
+
headers: { 'Content-Type': 'application/json' }
|
|
4560
|
+
});
|
|
4561
|
+
},
|
|
4562
|
+
};
|
|
4563
|
+
};
|
|
4564
|
+
```
|
|
4565
|
+
|
|
4249
4566
|
### Examples of HTTP Requests That Need Error Handling
|
|
4250
4567
|
|
|
4251
4568
|
**httpClient from @wix/essentials:**
|
|
@@ -4307,13 +4624,269 @@ The error handling in your custom data source integrates seamlessly with AutoPat
|
|
|
4307
4624
|
3. **Loading States**: Proper loading states during HTTP requests
|
|
4308
4625
|
4. **Error Boundaries**: Errors are caught and handled gracefully
|
|
4309
4626
|
|
|
4310
|
-
##
|
|
4627
|
+
## ⚠️ AI AGENT VALIDATION CHECKLIST
|
|
4628
|
+
|
|
4629
|
+
**BEFORE implementing ANY custom action or data source, AI agents MUST verify:**
|
|
4630
|
+
|
|
4631
|
+
### ✅ Error Handling Requirements
|
|
4632
|
+
- **httpClient from @wix/essentials** is wrapped with `errorHandler.withErrorHandler`
|
|
4633
|
+
- **Wix APIs (wix/data, wix/stores, etc)** are wrapped with `errorHandler.withErrorHandler`
|
|
4634
|
+
- **httpClient.fetchWithAuth()** calls are wrapped with `errorHandler.withErrorHandler`
|
|
4635
|
+
- **External API calls are NOT wrapped** with errorHandler (e.g., fetch(), axios, third-party HTTP clients)
|
|
4636
|
+
- **SDK actions are used directly** without error handling (e.g., `sdk.getOptimisticActions()`, `sdk.getSchema()`)
|
|
4637
|
+
- **@wix/essentials** is installed as a dependency
|
|
4638
|
+
|
|
4639
|
+
### ✅ Implementation Checklist
|
|
4640
|
+
- **Read this error handling documentation** before implementing any custom action
|
|
4641
|
+
- **Identify the type of HTTP request** being made (Wix vs External)
|
|
4642
|
+
- **Apply the correct error handling pattern** based on the request type
|
|
4643
|
+
- **Test error scenarios** to ensure proper error handling
|
|
4644
|
+
- **Verify error messages** are user-friendly and actionable
|
|
4645
|
+
|
|
4646
|
+
### ✅ Common Mistakes to Avoid
|
|
4647
|
+
- ❌ **NEVER** wrap external API calls (fetch, axios) with errorHandler
|
|
4648
|
+
- ❌ **NEVER** wrap SDK methods (sdk.getOptimisticActions) with errorHandler
|
|
4649
|
+
- ❌ **NEVER** forget to wrap Wix HTTP requests with errorHandler
|
|
4650
|
+
- ❌ **NEVER** implement custom actions without reading this documentation first
|
|
4651
|
+
|
|
4652
|
+
## Quick Decision Tree for AI Agents
|
|
4653
|
+
|
|
4654
|
+
**When implementing custom actions, ask:**
|
|
4655
|
+
|
|
4656
|
+
1. **Does this action make HTTP requests?**
|
|
4657
|
+
- **NO** → No error handling needed
|
|
4658
|
+
- **YES** → Go to step 2
|
|
4659
|
+
|
|
4660
|
+
2. **What type of HTTP request?**
|
|
4661
|
+
- **Wix APIs** (httpClient, wix/data, wix/stores) → **WRAP with errorHandler.withErrorHandler**
|
|
4662
|
+
- **External APIs** (fetch, axios, third-party) → **NO errorHandler needed**
|
|
4663
|
+
- **SDK methods** (sdk.getOptimisticActions, sdk.getSchema) → **NO errorHandler needed**
|
|
4664
|
+
|
|
4665
|
+
3. **Verify implementation:**
|
|
4666
|
+
- **Wix requests** are wrapped with `errorHandler.withErrorHandler`
|
|
4667
|
+
- **External requests** are NOT wrapped
|
|
4668
|
+
- **SDK methods** are used directly
|
|
4669
|
+
|
|
4670
|
+
## Complete Examples for All Custom Action Types
|
|
4311
4671
|
|
|
4312
|
-
|
|
4672
|
+
### ActionCell Custom Actions
|
|
4313
4673
|
|
|
4314
|
-
|
|
4315
|
-
|
|
4316
|
-
|
|
4317
|
-
|
|
4318
|
-
|
|
4319
|
-
|
|
4674
|
+
**Example 1: ActionCell with Wix API call (REQUIRES errorHandler)**
|
|
4675
|
+
```typescript
|
|
4676
|
+
import { errorHandler } from '@wix/essentials';
|
|
4677
|
+
import { CustomActionCellActionResolver } from '@wix/auto-patterns';
|
|
4678
|
+
|
|
4679
|
+
export const updateEntityStatus: CustomActionCellActionResolver = (params) => {
|
|
4680
|
+
const { actionParams, sdk } = params;
|
|
4681
|
+
const { item } = actionParams;
|
|
4682
|
+
|
|
4683
|
+
return {
|
|
4684
|
+
label: 'Update Status',
|
|
4685
|
+
icon: <UpdateIcon />,
|
|
4686
|
+
onClick: () => {
|
|
4687
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
4688
|
+
errorHandler.withErrorHandler(
|
|
4689
|
+
async () => {
|
|
4690
|
+
const response = await httpClient.request(
|
|
4691
|
+
updateEntityStatus({ entityId: item.id, status: 'active' })
|
|
4692
|
+
);
|
|
4693
|
+
return response.data;
|
|
4694
|
+
},
|
|
4695
|
+
{}
|
|
4696
|
+
);
|
|
4697
|
+
},
|
|
4698
|
+
};
|
|
4699
|
+
};
|
|
4700
|
+
```
|
|
4701
|
+
|
|
4702
|
+
**Example 2: ActionCell with External API call (NO errorHandler needed)**
|
|
4703
|
+
```typescript
|
|
4704
|
+
import { CustomActionCellActionResolver } from '@wix/auto-patterns';
|
|
4705
|
+
|
|
4706
|
+
export const sendToExternalService: CustomActionCellActionResolver = (params) => {
|
|
4707
|
+
const { actionParams, sdk } = params;
|
|
4708
|
+
const { item } = actionParams;
|
|
4709
|
+
|
|
4710
|
+
return {
|
|
4711
|
+
label: 'Send to External Service',
|
|
4712
|
+
icon: <SendIcon />,
|
|
4713
|
+
onClick: () => {
|
|
4714
|
+
// ✅ CORRECT: External API call - NO errorHandler needed
|
|
4715
|
+
fetch('https://api.external-service.com/send', {
|
|
4716
|
+
method: 'POST',
|
|
4717
|
+
body: JSON.stringify({ data: item }),
|
|
4718
|
+
headers: { 'Content-Type': 'application/json' }
|
|
4719
|
+
});
|
|
4720
|
+
},
|
|
4721
|
+
};
|
|
4722
|
+
};
|
|
4723
|
+
```
|
|
4724
|
+
|
|
4725
|
+
### BulkActions Custom Actions
|
|
4726
|
+
|
|
4727
|
+
**Example 3: BulkAction with Wix API call (REQUIRES errorHandler)**
|
|
4728
|
+
```typescript
|
|
4729
|
+
import { errorHandler } from '@wix/essentials';
|
|
4730
|
+
import { CustomBulkActionsActionResolver } from '@wix/auto-patterns';
|
|
4731
|
+
|
|
4732
|
+
export const bulkUpdateStatus: CustomBulkActionsActionResolver = (params) => {
|
|
4733
|
+
const { actionParams, sdk } = params;
|
|
4734
|
+
const { selectedValues } = actionParams;
|
|
4735
|
+
|
|
4736
|
+
return {
|
|
4737
|
+
label: 'Bulk Update Status',
|
|
4738
|
+
icon: <BulkUpdateIcon />,
|
|
4739
|
+
onClick: () => {
|
|
4740
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
4741
|
+
errorHandler.withErrorHandler(
|
|
4742
|
+
async () => {
|
|
4743
|
+
const response = await httpClient.request(
|
|
4744
|
+
bulkUpdateEntityStatus({
|
|
4745
|
+
entityIds: selectedValues.map(item => item.id),
|
|
4746
|
+
status: 'active'
|
|
4747
|
+
})
|
|
4748
|
+
);
|
|
4749
|
+
return response.data;
|
|
4750
|
+
},
|
|
4751
|
+
{}
|
|
4752
|
+
);
|
|
4753
|
+
},
|
|
4754
|
+
};
|
|
4755
|
+
};
|
|
4756
|
+
```
|
|
4757
|
+
|
|
4758
|
+
### CollectionPage Custom Actions
|
|
4759
|
+
|
|
4760
|
+
**Example 4: CollectionPage action with Wix API call (REQUIRES errorHandler)**
|
|
4761
|
+
```typescript
|
|
4762
|
+
import { errorHandler } from '@wix/essentials';
|
|
4763
|
+
import { CustomActionCollectionPageActionResolver } from '@wix/auto-patterns';
|
|
4764
|
+
|
|
4765
|
+
export const exportCollection: CustomActionCollectionPageActionResolver = (params) => {
|
|
4766
|
+
const { actionParams, sdk } = params;
|
|
4767
|
+
const { collectionId } = actionParams;
|
|
4768
|
+
|
|
4769
|
+
return {
|
|
4770
|
+
label: 'Export Collection',
|
|
4771
|
+
icon: <ExportIcon />,
|
|
4772
|
+
onClick: () => {
|
|
4773
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
4774
|
+
errorHandler.withErrorHandler(
|
|
4775
|
+
async () => {
|
|
4776
|
+
const response = await httpClient.request(
|
|
4777
|
+
exportCollectionData({ collectionId })
|
|
4778
|
+
);
|
|
4779
|
+
return response.data;
|
|
4780
|
+
},
|
|
4781
|
+
{}
|
|
4782
|
+
);
|
|
4783
|
+
},
|
|
4784
|
+
};
|
|
4785
|
+
};
|
|
4786
|
+
```
|
|
4787
|
+
|
|
4788
|
+
### EntityPage Custom Actions
|
|
4789
|
+
|
|
4790
|
+
**Example 5: EntityPage action with Wix API call (REQUIRES errorHandler)**
|
|
4791
|
+
```typescript
|
|
4792
|
+
import { errorHandler } from '@wix/essentials';
|
|
4793
|
+
import { CustomEntityPageMoreActionsActionResolver } from '@wix/auto-patterns';
|
|
4794
|
+
|
|
4795
|
+
export const sendEmail: CustomEntityPageMoreActionsActionResolver = (params) => {
|
|
4796
|
+
const { actionParams, sdk } = params;
|
|
4797
|
+
const { entity } = actionParams;
|
|
4798
|
+
|
|
4799
|
+
return {
|
|
4800
|
+
label: 'Send Email',
|
|
4801
|
+
icon: <EmailIcon />,
|
|
4802
|
+
onClick: () => {
|
|
4803
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
4804
|
+
errorHandler.withErrorHandler(
|
|
4805
|
+
async () => {
|
|
4806
|
+
const response = await httpClient.request(
|
|
4807
|
+
sendEmailToEntity({ entityId: entity.id, email: entity.email })
|
|
4808
|
+
);
|
|
4809
|
+
return response.data;
|
|
4810
|
+
},
|
|
4811
|
+
{}
|
|
4812
|
+
);
|
|
4813
|
+
},
|
|
4814
|
+
};
|
|
4815
|
+
};
|
|
4816
|
+
```
|
|
4817
|
+
|
|
4818
|
+
### Custom Data Sources
|
|
4819
|
+
|
|
4820
|
+
**Example 6: Custom Data Source with Wix API calls (REQUIRES errorHandler)**
|
|
4821
|
+
```typescript
|
|
4822
|
+
import { errorHandler } from '@wix/essentials';
|
|
4823
|
+
|
|
4824
|
+
export const myCustomDataSource = async (collectionId: string, context: any) => {
|
|
4825
|
+
return {
|
|
4826
|
+
id: 'myCustomCollection',
|
|
4827
|
+
fields: {
|
|
4828
|
+
// ... field definitions
|
|
4829
|
+
},
|
|
4830
|
+
idField: 'id',
|
|
4831
|
+
actions: {
|
|
4832
|
+
get: async (entityId: string) => {
|
|
4833
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
4834
|
+
return errorHandler.withErrorHandler(
|
|
4835
|
+
async () => {
|
|
4836
|
+
const response = await httpClient.request(
|
|
4837
|
+
getDummyEntity({ dummyEntityId: entityId })
|
|
4838
|
+
);
|
|
4839
|
+
return response.data.dummyEntity;
|
|
4840
|
+
},
|
|
4841
|
+
{}
|
|
4842
|
+
);
|
|
4843
|
+
},
|
|
4844
|
+
create: async (newEntity: any) => {
|
|
4845
|
+
// ✅ CORRECT: Wix API call wrapped with errorHandler
|
|
4846
|
+
return errorHandler.withErrorHandler(
|
|
4847
|
+
async () => {
|
|
4848
|
+
const response = await httpClient.request(
|
|
4849
|
+
createDummyEntity({ dummyEntity: newEntity })
|
|
4850
|
+
);
|
|
4851
|
+
return response.data.dummyEntity;
|
|
4852
|
+
},
|
|
4853
|
+
{}
|
|
4854
|
+
);
|
|
4855
|
+
},
|
|
4856
|
+
// ... other actions
|
|
4857
|
+
},
|
|
4858
|
+
};
|
|
4859
|
+
};
|
|
4860
|
+
```
|
|
4861
|
+
|
|
4862
|
+
### Actions Using SDK Methods (NO errorHandler needed)
|
|
4863
|
+
|
|
4864
|
+
**Example 7: Action using SDK methods (NO errorHandler needed)**
|
|
4865
|
+
```typescript
|
|
4866
|
+
import { CustomActionCellActionResolver } from '@wix/auto-patterns';
|
|
4867
|
+
|
|
4868
|
+
export const quickUpdate: CustomActionCellActionResolver = (params) => {
|
|
4869
|
+
const { actionParams, sdk } = params;
|
|
4870
|
+
const { item } = actionParams;
|
|
4871
|
+
|
|
4872
|
+
return {
|
|
4873
|
+
label: 'Quick Update',
|
|
4874
|
+
icon: <QuickUpdateIcon />,
|
|
4875
|
+
onClick: () => {
|
|
4876
|
+
// ✅ CORRECT: SDK methods - NO errorHandler needed
|
|
4877
|
+
const optimisticActions = sdk.getOptimisticActions(sdk.collectionId);
|
|
4878
|
+
const schema = sdk.getSchema(sdk.collectionId);
|
|
4879
|
+
|
|
4880
|
+
const updatedItem = { ...item, lastUpdated: new Date() };
|
|
4881
|
+
optimisticActions.updateOne(updatedItem, {
|
|
4882
|
+
submit: async (items) => schema.actions.update(items[0]),
|
|
4883
|
+
successToast: 'Item updated successfully',
|
|
4884
|
+
errorToast: (err, {retry}) => ({
|
|
4885
|
+
text: 'Update failed',
|
|
4886
|
+
action: { text: 'Retry', onClick: retry }
|
|
4887
|
+
})
|
|
4888
|
+
});
|
|
4889
|
+
},
|
|
4890
|
+
};
|
|
4891
|
+
};
|
|
4892
|
+
```
|