omni-sync-sdk 0.7.1 → 0.7.3

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/LICENSE ADDED
File without changes
package/README.md CHANGED
@@ -1921,6 +1921,148 @@ When building a store, implement these pages:
1921
1921
 
1922
1922
  ---
1923
1923
 
1924
+ ## Error Handling & Toast Notifications
1925
+
1926
+ For a polished user experience, use toast notifications to show success/error messages. We recommend [Sonner](https://sonner.emilkowal.ski/) - a lightweight toast library.
1927
+
1928
+ ### Setup Toast Notifications
1929
+
1930
+ ```bash
1931
+ npm install sonner
1932
+ ```
1933
+
1934
+ Add the Toaster component to your app layout:
1935
+
1936
+ ```tsx
1937
+ // app/layout.tsx or App.tsx
1938
+ import { Toaster } from 'sonner';
1939
+
1940
+ export default function RootLayout({ children }) {
1941
+ return (
1942
+ <html>
1943
+ <body>
1944
+ {children}
1945
+ <Toaster
1946
+ position="top-right"
1947
+ richColors
1948
+ closeButton
1949
+ toastOptions={{
1950
+ duration: 4000,
1951
+ }}
1952
+ />
1953
+ </body>
1954
+ </html>
1955
+ );
1956
+ }
1957
+ ```
1958
+
1959
+ ### Handling SDK Errors
1960
+
1961
+ The SDK throws `OmniSyncError` with helpful messages. Wrap SDK calls in try/catch:
1962
+
1963
+ ```tsx
1964
+ import { toast } from 'sonner';
1965
+ import { OmniSyncError } from 'omni-sync-sdk';
1966
+
1967
+ // Add to cart with toast feedback
1968
+ const handleAddToCart = async (productId: string, quantity: number) => {
1969
+ try {
1970
+ omni.addToLocalCart({ productId, quantity });
1971
+ toast.success('Added to cart!');
1972
+ } catch (error) {
1973
+ if (error instanceof OmniSyncError) {
1974
+ toast.error(error.message);
1975
+ } else {
1976
+ toast.error('Something went wrong');
1977
+ }
1978
+ }
1979
+ };
1980
+
1981
+ // Checkout with toast feedback
1982
+ const handleCheckout = async () => {
1983
+ try {
1984
+ const order = await omni.submitGuestOrder();
1985
+ toast.success(`Order placed! Order #${order.orderNumber}`);
1986
+ // Navigate to success page
1987
+ } catch (error) {
1988
+ if (error instanceof OmniSyncError) {
1989
+ // Show specific error message from SDK
1990
+ toast.error(error.message);
1991
+ } else {
1992
+ toast.error('Failed to place order. Please try again.');
1993
+ }
1994
+ }
1995
+ };
1996
+ ```
1997
+
1998
+ ### Common Error Messages
1999
+
2000
+ | Error | When it occurs |
2001
+ | ------------------------------ | ---------------------------------- |
2002
+ | `Cart is empty` | Trying to checkout with empty cart |
2003
+ | `Customer email is required` | Missing email at checkout |
2004
+ | `Shipping address is required` | Missing shipping address |
2005
+ | `Product not found` | Invalid product ID |
2006
+ | `Insufficient inventory` | Not enough stock |
2007
+ | `Invalid quantity` | Quantity < 1 or > available |
2008
+
2009
+ ### Custom Hook for SDK Operations (Optional)
2010
+
2011
+ Create a reusable hook for SDK operations with automatic toast handling:
2012
+
2013
+ ```tsx
2014
+ // hooks/useOmniAction.ts
2015
+ import { useState } from 'react';
2016
+ import { toast } from 'sonner';
2017
+ import { OmniSyncError } from 'omni-sync-sdk';
2018
+
2019
+ export function useOmniAction<T>() {
2020
+ const [isLoading, setIsLoading] = useState(false);
2021
+
2022
+ const execute = async (
2023
+ action: () => Promise<T>,
2024
+ options?: {
2025
+ successMessage?: string;
2026
+ errorMessage?: string;
2027
+ onSuccess?: (result: T) => void;
2028
+ }
2029
+ ): Promise<T | null> => {
2030
+ setIsLoading(true);
2031
+ try {
2032
+ const result = await action();
2033
+ if (options?.successMessage) {
2034
+ toast.success(options.successMessage);
2035
+ }
2036
+ options?.onSuccess?.(result);
2037
+ return result;
2038
+ } catch (error) {
2039
+ const message =
2040
+ error instanceof OmniSyncError
2041
+ ? error.message
2042
+ : options?.errorMessage || 'Something went wrong';
2043
+ toast.error(message);
2044
+ return null;
2045
+ } finally {
2046
+ setIsLoading(false);
2047
+ }
2048
+ };
2049
+
2050
+ return { execute, isLoading };
2051
+ }
2052
+
2053
+ // Usage:
2054
+ const { execute, isLoading } = useOmniAction();
2055
+
2056
+ const handlePlaceOrder = () => {
2057
+ execute(() => omni.submitGuestOrder(), {
2058
+ successMessage: 'Order placed successfully!',
2059
+ onSuccess: (order) => navigate(`/order/${order.orderId}`),
2060
+ });
2061
+ };
2062
+ ```
2063
+
2064
+ ---
2065
+
1924
2066
  ## Important Rules
1925
2067
 
1926
2068
  ### DO:
@@ -1928,9 +2070,11 @@ When building a store, implement these pages:
1928
2070
  - Install `omni-sync-sdk` and use it for ALL data
1929
2071
  - Import types from the SDK
1930
2072
  - Handle loading states and errors
2073
+ - **Use toast notifications (Sonner) for user feedback on actions**
1931
2074
  - Persist cart ID in localStorage
1932
2075
  - Persist customer token after login
1933
2076
  - **Check `descriptionFormat` and render HTML with `dangerouslySetInnerHTML` when format is `'html'`**
2077
+ - **Wrap SDK calls in try/catch and show error toasts**
1934
2078
 
1935
2079
  ### DON'T:
1936
2080
 
package/dist/index.d.mts CHANGED
@@ -2051,9 +2051,7 @@ declare class OmniSyncClient {
2051
2051
  */
2052
2052
  completeGuestCheckout(checkoutId: string, options?: {
2053
2053
  clearCartOnSuccess?: boolean;
2054
- }): Promise<{
2055
- orderId: string;
2056
- }>;
2054
+ }): Promise<GuestOrderResponse>;
2057
2055
  /**
2058
2056
  * Create order from custom data (not from local cart)
2059
2057
  * Use this if you manage cart state yourself
package/dist/index.d.ts CHANGED
@@ -2051,9 +2051,7 @@ declare class OmniSyncClient {
2051
2051
  */
2052
2052
  completeGuestCheckout(checkoutId: string, options?: {
2053
2053
  clearCartOnSuccess?: boolean;
2054
- }): Promise<{
2055
- orderId: string;
2056
- }>;
2054
+ }): Promise<GuestOrderResponse>;
2057
2055
  /**
2058
2056
  * Create order from custom data (not from local cart)
2059
2057
  * Use this if you manage cart state yourself
package/dist/index.js CHANGED
@@ -1747,12 +1747,10 @@ var OmniSyncClient = class {
1747
1747
  });
1748
1748
  return {
1749
1749
  orderId: orderResult.orderId,
1750
- orderNumber: orderResult.orderId,
1751
- // Will be overwritten by actual order number if returned
1752
- status: "pending",
1753
- total: 0,
1754
- // Actual total comes from server
1755
- message: "Order created successfully (tracked)"
1750
+ orderNumber: orderResult.orderNumber || orderResult.orderId,
1751
+ status: orderResult.status || "pending",
1752
+ total: orderResult.total ?? 0,
1753
+ message: orderResult.message || "Order created successfully"
1756
1754
  };
1757
1755
  }
1758
1756
  } catch {
package/dist/index.mjs CHANGED
@@ -1722,12 +1722,10 @@ var OmniSyncClient = class {
1722
1722
  });
1723
1723
  return {
1724
1724
  orderId: orderResult.orderId,
1725
- orderNumber: orderResult.orderId,
1726
- // Will be overwritten by actual order number if returned
1727
- status: "pending",
1728
- total: 0,
1729
- // Actual total comes from server
1730
- message: "Order created successfully (tracked)"
1725
+ orderNumber: orderResult.orderNumber || orderResult.orderId,
1726
+ status: orderResult.status || "pending",
1727
+ total: orderResult.total ?? 0,
1728
+ message: orderResult.message || "Order created successfully"
1731
1729
  };
1732
1730
  }
1733
1731
  } catch {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "omni-sync-sdk",
3
- "version": "0.7.1",
3
+ "version": "0.7.3",
4
4
  "description": "Official SDK for building e-commerce storefronts with OmniSync Platform. Perfect for vibe-coded sites, AI-built stores (Cursor, Lovable, v0), and custom storefronts.",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.mjs",
@@ -16,14 +16,6 @@
16
16
  "dist",
17
17
  "README.md"
18
18
  ],
19
- "scripts": {
20
- "build": "tsup src/index.ts --format cjs,esm --dts",
21
- "dev": "tsup src/index.ts --format cjs,esm --dts --watch",
22
- "lint": "eslint \"src/**/*.ts\"",
23
- "test": "vitest run",
24
- "test:watch": "vitest",
25
- "prepublishOnly": "pnpm build"
26
- },
27
19
  "keywords": [
28
20
  "omni-sync",
29
21
  "e-commerce",
@@ -72,5 +64,12 @@
72
64
  "typescript": {
73
65
  "optional": true
74
66
  }
67
+ },
68
+ "scripts": {
69
+ "build": "tsup src/index.ts --format cjs,esm --dts",
70
+ "dev": "tsup src/index.ts --format cjs,esm --dts --watch",
71
+ "lint": "eslint \"src/**/*.ts\"",
72
+ "test": "vitest run",
73
+ "test:watch": "vitest"
75
74
  }
76
- }
75
+ }