@cshah18/sdk 4.0.0 → 4.2.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/dist/cobuy-sdk.esm.js +1135 -80
- package/dist/cobuy-sdk.esm.js.map +1 -1
- package/dist/cobuy-sdk.umd.js +1135 -80
- package/dist/cobuy-sdk.umd.js.map +1 -1
- package/dist/types/core/analytics.d.ts +6 -2
- package/dist/types/core/api-client.d.ts +2 -2
- package/dist/types/core/cobuy.d.ts +19 -2
- package/dist/types/core/group-channel-manager.d.ts +74 -0
- package/dist/types/core/offline-redemption.d.ts +41 -0
- package/dist/types/core/socket.d.ts +2 -1
- package/dist/types/core/types.d.ts +76 -5
- package/dist/types/ui/group-list/group-list-modal.d.ts +1 -0
- package/dist/types/ui/lobby/lobby-modal.d.ts +39 -1
- package/dist/types/ui/offline-redemption/offline-redemption-modal.d.ts +35 -0
- package/dist/types/ui/widget/widget-root.d.ts +6 -0
- package/package.json +1 -1
- package/dist/types/core/socket-client.d.ts +0 -126
|
@@ -4,9 +4,9 @@ import { ApiClient } from "./api-client";
|
|
|
4
4
|
*/
|
|
5
5
|
export interface AnalyticsEvent {
|
|
6
6
|
event: string;
|
|
7
|
-
productId: string;
|
|
8
7
|
timestamp: string;
|
|
9
|
-
|
|
8
|
+
productId?: string;
|
|
9
|
+
sessionId?: string;
|
|
10
10
|
context?: {
|
|
11
11
|
pageUrl?: string;
|
|
12
12
|
userAgent?: string;
|
|
@@ -31,6 +31,10 @@ export declare class AnalyticsClient {
|
|
|
31
31
|
* Send event to backend analytics endpoint using unified ApiClient
|
|
32
32
|
*/
|
|
33
33
|
private sendEvent;
|
|
34
|
+
/**
|
|
35
|
+
* Track page view event
|
|
36
|
+
*/
|
|
37
|
+
trackPageView(): Promise<void>;
|
|
34
38
|
/**
|
|
35
39
|
* Track custom event (extensible for future use)
|
|
36
40
|
*/
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { ApiRequestOptions, ApiResponse, ApiClientConfig, ProductRewardData, ProductPrimaryGroupData, GroupJoinResponseData, GroupInviteResponseData, AuthStrategy, ShareChannel, Contact, CheckoutValidationData } from "./types";
|
|
1
|
+
import { ApiRequestOptions, ApiResponse, ApiClientConfig, ProductRewardData, ProductPrimaryGroupData, GroupJoinResponseData, GroupInviteResponseData, AuthStrategy, ShareChannel, Contact, CheckoutValidationData, CheckoutConfirmData } from "./types";
|
|
2
2
|
/**
|
|
3
3
|
* HTTP client for communicating with CoBuy API
|
|
4
4
|
*
|
|
@@ -158,5 +158,5 @@ export declare class ApiClient {
|
|
|
158
158
|
* @param checkoutRef - The checkout reference ID from the prepare step
|
|
159
159
|
* @returns Promise with success status
|
|
160
160
|
*/
|
|
161
|
-
confirmCheckout(groupId: string, checkoutRef: string): Promise<ApiResponse<void>>;
|
|
161
|
+
confirmCheckout(groupId: string, checkoutRef: string, data?: CheckoutConfirmData): Promise<ApiResponse<void>>;
|
|
162
162
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { CoBuySDK, CoBuyInitOptions, RenderWidgetOptions, ModalOptions, Contact, CheckoutValidationData } from "./types";
|
|
1
|
+
import { CoBuySDK, CoBuyInitOptions, RenderWidgetOptions, ModalOptions, Contact, CheckoutValidationData, CheckoutConfirmData } from "./types";
|
|
2
2
|
import { ApiClient } from "./api-client";
|
|
3
3
|
import { AnalyticsClient } from "./analytics";
|
|
4
4
|
import { SocketManager } from "./socket";
|
|
@@ -119,14 +119,31 @@ export declare class CoBuy implements CoBuySDK {
|
|
|
119
119
|
*
|
|
120
120
|
* @param groupId - The group ID to confirm checkout for
|
|
121
121
|
* @param checkoutRef - The checkout reference ID from the prepare step
|
|
122
|
+
/**
|
|
123
|
+
* Confirm checkout for a group
|
|
124
|
+
* Should be called after validateCheckout to complete the checkout process.
|
|
125
|
+
*
|
|
126
|
+
* @param groupId The group ID to confirm checkout for
|
|
127
|
+
* @param checkoutRef The checkout reference from the prepare step
|
|
128
|
+
* @param data Optional order details (order_id, order_total, discount_applied, currency, payment_method, metadata)
|
|
122
129
|
*
|
|
123
130
|
* @example
|
|
124
131
|
* ```typescript
|
|
125
132
|
* // Confirm checkout for a group
|
|
126
133
|
* await CoBuy.confirmCheckout('fae238ae-7468-47e9-9eec-b6d52fe3b012', 'chk_9a6d8750-ed60-4795-a207-2abe955e8509');
|
|
134
|
+
*
|
|
135
|
+
* // Confirm checkout with order details
|
|
136
|
+
* await CoBuy.confirmCheckout('fae238ae-7468-47e9-9eec-b6d52fe3b012', 'chk_9a6d8750-ed60-4795-a207-2abe955e8509', {
|
|
137
|
+
* order_id: 'ORDER-1001',
|
|
138
|
+
* order_total: 100.00,
|
|
139
|
+
* discount_applied: 20.00,
|
|
140
|
+
* currency: 'USD',
|
|
141
|
+
* payment_method: 'card',
|
|
142
|
+
* metadata: { coupon_code: 'WELCOME20', customer_id: 'cust_123' }
|
|
143
|
+
* });
|
|
127
144
|
* ```
|
|
128
145
|
*/
|
|
129
|
-
confirmCheckout(groupId: string, checkoutRef: string): Promise<void>;
|
|
146
|
+
confirmCheckout(groupId: string, checkoutRef: string, data?: CheckoutConfirmData): Promise<void>;
|
|
130
147
|
/**
|
|
131
148
|
* Get the initialized API client instance
|
|
132
149
|
*/
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
import { InternalConfig, GroupFulfilledEvent, Reward } from "./types";
|
|
2
|
+
export interface GroupRealtimeSnapshot {
|
|
3
|
+
groupId: string;
|
|
4
|
+
productId: string;
|
|
5
|
+
participants: number;
|
|
6
|
+
maxParticipants?: number;
|
|
7
|
+
progressPercent?: number;
|
|
8
|
+
expiresAt?: string;
|
|
9
|
+
reward?: Reward | null;
|
|
10
|
+
status?: string;
|
|
11
|
+
timeLeftSeconds?: number;
|
|
12
|
+
}
|
|
13
|
+
export type GroupChannelEvent = {
|
|
14
|
+
type: "update";
|
|
15
|
+
snapshot: GroupRealtimeSnapshot;
|
|
16
|
+
} | {
|
|
17
|
+
type: "fulfilled";
|
|
18
|
+
snapshot: GroupRealtimeSnapshot;
|
|
19
|
+
};
|
|
20
|
+
export type GroupChannelListener = (event: GroupChannelEvent) => void;
|
|
21
|
+
/**
|
|
22
|
+
* Centralized real-time channel manager for all group-aware UI surfaces.
|
|
23
|
+
* Ensures a single socket connection, one room subscription per group, and
|
|
24
|
+
* shared event dispatch to interested listeners.
|
|
25
|
+
*/
|
|
26
|
+
export declare class GroupChannelManager {
|
|
27
|
+
private readonly config;
|
|
28
|
+
private readonly sdkVersion;
|
|
29
|
+
private readonly onFulfilledCallback?;
|
|
30
|
+
private socket;
|
|
31
|
+
private readonly logger;
|
|
32
|
+
private readonly listeners;
|
|
33
|
+
private readonly groupRefCount;
|
|
34
|
+
private readonly groupToProduct;
|
|
35
|
+
private readonly latestByGroup;
|
|
36
|
+
private readonly latestByProduct;
|
|
37
|
+
private isConnecting;
|
|
38
|
+
constructor(config: InternalConfig, sdkVersion: string, onFulfilledCallback?: ((event: GroupFulfilledEvent) => void) | undefined);
|
|
39
|
+
/**
|
|
40
|
+
* Start socket connection if not already connected.
|
|
41
|
+
*/
|
|
42
|
+
connect(): void;
|
|
43
|
+
/**
|
|
44
|
+
* Subscribe to realtime updates for a group. Multiple callers are reference-counted.
|
|
45
|
+
*/
|
|
46
|
+
subscribeToGroup(groupId: string, productId: string): void;
|
|
47
|
+
/**
|
|
48
|
+
* Unsubscribe from a group when no listeners remain.
|
|
49
|
+
*/
|
|
50
|
+
unsubscribeFromGroup(groupId: string): void;
|
|
51
|
+
/**
|
|
52
|
+
* Switch from one group room to another, ensuring only one active subscription.
|
|
53
|
+
*/
|
|
54
|
+
switchGroup(oldGroupId: string | null, newGroupId: string, productId: string): void;
|
|
55
|
+
/**
|
|
56
|
+
* Register for realtime events. Returns an unsubscribe function.
|
|
57
|
+
*/
|
|
58
|
+
addListener(listener: GroupChannelListener): () => void;
|
|
59
|
+
/**
|
|
60
|
+
* Retrieve the latest snapshot for a product if one exists.
|
|
61
|
+
*/
|
|
62
|
+
getLatestSnapshotForProduct(productId: string): GroupRealtimeSnapshot | null;
|
|
63
|
+
/**
|
|
64
|
+
* Disconnect and clear state.
|
|
65
|
+
*/
|
|
66
|
+
disconnect(): void;
|
|
67
|
+
private handleGroupUpdate;
|
|
68
|
+
private handleGroupFulfilled;
|
|
69
|
+
private cacheSnapshot;
|
|
70
|
+
private broadcast;
|
|
71
|
+
private normalizeSnapshot;
|
|
72
|
+
private pickString;
|
|
73
|
+
private pickNumber;
|
|
74
|
+
}
|
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Offline Redemption Utilities
|
|
3
|
+
* Helpers for constructing QR URLs, copying codes, and downloading QR images
|
|
4
|
+
*/
|
|
5
|
+
import { OfflineRedemption } from "./types";
|
|
6
|
+
/**
|
|
7
|
+
* Build full S3 URL for QR code image
|
|
8
|
+
* @param qrCodeData - S3 key from offline_redemption.qr_code_data
|
|
9
|
+
* @returns Full HTTPS URL to the QR code image
|
|
10
|
+
*/
|
|
11
|
+
export declare function buildQRUrl(qrCodeData: string): string;
|
|
12
|
+
/**
|
|
13
|
+
* Copy redemption code to clipboard
|
|
14
|
+
* @param code - Redemption code to copy
|
|
15
|
+
* @returns Promise that resolves when copy is complete
|
|
16
|
+
*/
|
|
17
|
+
export declare function copyRedemptionCode(code: string): Promise<boolean>;
|
|
18
|
+
/**
|
|
19
|
+
* Download QR code image
|
|
20
|
+
* @param qrUrl - Full URL to the QR code image
|
|
21
|
+
* @param filename - Name for the downloaded file
|
|
22
|
+
*/
|
|
23
|
+
export declare function downloadQRCode(qrUrl: string, filename?: string): Promise<boolean>;
|
|
24
|
+
/**
|
|
25
|
+
* Validate offline redemption data
|
|
26
|
+
* @param redemption - Offline redemption object
|
|
27
|
+
* @returns true if data is valid and complete
|
|
28
|
+
*/
|
|
29
|
+
export declare function isValidOfflineRedemption(redemption: unknown): redemption is OfflineRedemption;
|
|
30
|
+
/**
|
|
31
|
+
* Format expiry date for display
|
|
32
|
+
* @param isoDate - ISO 8601 date string
|
|
33
|
+
* @returns Formatted date string (e.g., "Feb 20, 2026 at 10:21 AM")
|
|
34
|
+
*/
|
|
35
|
+
export declare function formatExpiryDate(isoDate: string): string;
|
|
36
|
+
/**
|
|
37
|
+
* Check if offline redemption is still valid
|
|
38
|
+
* @param expiryDate - ISO 8601 expiry date string
|
|
39
|
+
* @returns true if redemption has not expired
|
|
40
|
+
*/
|
|
41
|
+
export declare function isRedemptionValid(expiryDate: string): boolean;
|
|
@@ -11,9 +11,10 @@ export interface SocketHandlers {
|
|
|
11
11
|
export declare class SocketManager {
|
|
12
12
|
private readonly config;
|
|
13
13
|
private readonly sdkVersion;
|
|
14
|
+
private readonly sessionId;
|
|
14
15
|
private socket;
|
|
15
16
|
private readonly logger;
|
|
16
|
-
constructor(config: InternalConfig, sdkVersion: string);
|
|
17
|
+
constructor(config: InternalConfig, sdkVersion: string, sessionId: string);
|
|
17
18
|
private dispatchWindowEvent;
|
|
18
19
|
private formatPayload;
|
|
19
20
|
/**
|
|
@@ -161,14 +161,78 @@ export interface CheckoutValidationData {
|
|
|
161
161
|
reward?: CheckoutValidationReward;
|
|
162
162
|
message?: string;
|
|
163
163
|
}
|
|
164
|
+
/**
|
|
165
|
+
* Optional metadata for checkout confirmation
|
|
166
|
+
*/
|
|
167
|
+
export interface CheckoutConfirmMetadata {
|
|
168
|
+
coupon_code?: string;
|
|
169
|
+
customer_id?: string;
|
|
170
|
+
note?: string;
|
|
171
|
+
[key: string]: string | number | boolean | undefined;
|
|
172
|
+
}
|
|
173
|
+
/**
|
|
174
|
+
* Optional order details for checkout confirmation
|
|
175
|
+
*/
|
|
176
|
+
export interface CheckoutConfirmData {
|
|
177
|
+
order_id?: string;
|
|
178
|
+
order_total?: number;
|
|
179
|
+
discount_applied?: number;
|
|
180
|
+
currency?: string;
|
|
181
|
+
payment_method?: "cod" | "card" | string;
|
|
182
|
+
metadata?: CheckoutConfirmMetadata;
|
|
183
|
+
}
|
|
184
|
+
/**
|
|
185
|
+
* Offline redemption information for fulfilled groups
|
|
186
|
+
*/
|
|
187
|
+
export interface OfflineRedemption {
|
|
188
|
+
member_id: string;
|
|
189
|
+
qr_code_value: string;
|
|
190
|
+
redemption_code: string;
|
|
191
|
+
qr_code_data: string;
|
|
192
|
+
offline_expires_at: string;
|
|
193
|
+
}
|
|
194
|
+
/**
|
|
195
|
+
* Group information in fulfillment event
|
|
196
|
+
*/
|
|
197
|
+
export interface FulfilledGroup {
|
|
198
|
+
id: string;
|
|
199
|
+
group_name: string;
|
|
200
|
+
description?: string;
|
|
201
|
+
campaign_creative_name?: string;
|
|
202
|
+
campaign_id: string;
|
|
203
|
+
campaign_name: string;
|
|
204
|
+
campaign_status: string;
|
|
205
|
+
participants_count: number;
|
|
206
|
+
max_participants: number;
|
|
207
|
+
status: string;
|
|
208
|
+
expiry_at: string;
|
|
209
|
+
timeLeftSeconds: number;
|
|
210
|
+
}
|
|
211
|
+
/**
|
|
212
|
+
* Frozen reward information in fulfillment event
|
|
213
|
+
*/
|
|
214
|
+
export interface FrozenReward {
|
|
215
|
+
reward: Reward;
|
|
216
|
+
group_id: string;
|
|
217
|
+
frozen_at: string;
|
|
218
|
+
product_id: string;
|
|
219
|
+
eligibility?: {
|
|
220
|
+
isEligible: boolean;
|
|
221
|
+
};
|
|
222
|
+
}
|
|
164
223
|
/**
|
|
165
224
|
* Socket payload emitted when a group reaches fulfillment
|
|
225
|
+
* Includes all details needed for offline redemption
|
|
166
226
|
*/
|
|
167
227
|
export interface GroupFulfilledEvent {
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
228
|
+
group: FulfilledGroup;
|
|
229
|
+
frozen_reward: FrozenReward;
|
|
230
|
+
product_id: string;
|
|
231
|
+
offline_redemption?: OfflineRedemption;
|
|
232
|
+
groupId?: string;
|
|
233
|
+
productId?: string;
|
|
234
|
+
participants?: number;
|
|
235
|
+
reward?: Reward;
|
|
172
236
|
}
|
|
173
237
|
/**
|
|
174
238
|
* Socket payload emitted when a new group is created
|
|
@@ -302,6 +366,10 @@ export interface ModalOptions {
|
|
|
302
366
|
timeAgo: string;
|
|
303
367
|
color: "pink" | "purple" | "blue" | "green" | "orange";
|
|
304
368
|
}>;
|
|
369
|
+
/**
|
|
370
|
+
* Offline redemption data for fulfilled groups
|
|
371
|
+
*/
|
|
372
|
+
offlineRedemption?: OfflineRedemption;
|
|
305
373
|
/**
|
|
306
374
|
* Optional callback when modal opens
|
|
307
375
|
*/
|
|
@@ -393,6 +461,7 @@ export interface ProductPrimaryGroupData {
|
|
|
393
461
|
status: string;
|
|
394
462
|
expiry_at: string;
|
|
395
463
|
timeLeftSeconds: number;
|
|
464
|
+
offline_redemption?: OfflineRedemption;
|
|
396
465
|
}
|
|
397
466
|
/**
|
|
398
467
|
* Group join response data
|
|
@@ -414,6 +483,7 @@ export interface GroupJoinResponseData {
|
|
|
414
483
|
};
|
|
415
484
|
isPrimary: boolean;
|
|
416
485
|
product_id: string;
|
|
486
|
+
offline_redemption?: OfflineRedemption;
|
|
417
487
|
}
|
|
418
488
|
export type ShareChannel = "whatsapp" | "facebook" | "email" | "sms" | "copy_link" | "tiktok" | "x" | "other";
|
|
419
489
|
export interface GroupInviteResponseData {
|
|
@@ -531,8 +601,9 @@ export interface CoBuySDK {
|
|
|
531
601
|
* Finalizes the checkout and confirms the order
|
|
532
602
|
* @param _groupId The group ID to confirm checkout for
|
|
533
603
|
* @param _checkoutRef The checkout reference ID from the prepare step
|
|
604
|
+
* @param _data (optional) Additional order details (order_id, order_total, discount_applied, currency, payment_method, metadata)
|
|
534
605
|
*/
|
|
535
|
-
confirmCheckout(_groupId: string, _checkoutRef: string): Promise<void>;
|
|
606
|
+
confirmCheckout(_groupId: string, _checkoutRef: string, _data?: CheckoutConfirmData): Promise<void>;
|
|
536
607
|
/**
|
|
537
608
|
* Retrieve stored checkout reference for a product in this session
|
|
538
609
|
* Returns both the storage key and value; key/value null if not found or storage unavailable
|
|
@@ -2,6 +2,7 @@ import { ApiClient } from "../../core/api-client";
|
|
|
2
2
|
import { ProductPrimaryGroupData, GroupJoinResponseData } from "../../core/types";
|
|
3
3
|
export interface GroupListItem {
|
|
4
4
|
groupId: string;
|
|
5
|
+
name?: string;
|
|
5
6
|
timeLabel: string;
|
|
6
7
|
timeLeftSeconds?: number;
|
|
7
8
|
joined: number;
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { ApiClient } from "../../core/api-client";
|
|
2
|
+
import { OfflineRedemption } from "../../core/types";
|
|
2
3
|
import { AnalyticsClient } from "../../core/analytics";
|
|
3
4
|
import { SocketManager } from "../../core/socket";
|
|
4
5
|
import "./styles/styles.css";
|
|
@@ -16,6 +17,7 @@ export interface LobbyModalData {
|
|
|
16
17
|
shareMessage?: string;
|
|
17
18
|
activities?: ActivityItem[];
|
|
18
19
|
isLocked?: boolean;
|
|
20
|
+
offlineRedemption?: OfflineRedemption;
|
|
19
21
|
}
|
|
20
22
|
export interface ActivityItem {
|
|
21
23
|
emoji: string;
|
|
@@ -58,6 +60,18 @@ export declare class LobbyModal {
|
|
|
58
60
|
* Default activity items
|
|
59
61
|
*/
|
|
60
62
|
private getDefaultActivities;
|
|
63
|
+
/**
|
|
64
|
+
* Create entrance animation overlay
|
|
65
|
+
*/
|
|
66
|
+
private createEntranceAnimation;
|
|
67
|
+
/**
|
|
68
|
+
* Show entrance animation and auto-hide after duration
|
|
69
|
+
*/
|
|
70
|
+
private showEntranceAnimation;
|
|
71
|
+
/**
|
|
72
|
+
* Hide entrance animation with exit effect
|
|
73
|
+
*/
|
|
74
|
+
private hideEntranceAnimation;
|
|
61
75
|
/**
|
|
62
76
|
* Create the modal DOM structure
|
|
63
77
|
*/
|
|
@@ -83,9 +97,29 @@ export declare class LobbyModal {
|
|
|
83
97
|
*/
|
|
84
98
|
private createTitleSection;
|
|
85
99
|
/**
|
|
86
|
-
* Create link
|
|
100
|
+
* Create connected section (subtitle + link + share)
|
|
101
|
+
*/
|
|
102
|
+
private createConnectedSection;
|
|
103
|
+
/**
|
|
104
|
+
* Create link section (just the link box and share button, no wrapper)
|
|
87
105
|
*/
|
|
88
106
|
private createLinkSection;
|
|
107
|
+
/**
|
|
108
|
+
* Create offline redemption section
|
|
109
|
+
*/
|
|
110
|
+
private createOfflineRedemptionSection;
|
|
111
|
+
/**
|
|
112
|
+
* Handle copying offline redemption code
|
|
113
|
+
*/
|
|
114
|
+
private copyOfflineRedemptionCode;
|
|
115
|
+
/**
|
|
116
|
+
* Handle downloading offline QR code
|
|
117
|
+
*/
|
|
118
|
+
private downloadOfflineQR;
|
|
119
|
+
/**
|
|
120
|
+
* Inject styles for offline redemption section
|
|
121
|
+
*/
|
|
122
|
+
private injectOfflineRedemptionStyles;
|
|
89
123
|
/**
|
|
90
124
|
* Create offer section
|
|
91
125
|
*/
|
|
@@ -230,6 +264,10 @@ export declare class LobbyModal {
|
|
|
230
264
|
* Show/hide link section based on lock state
|
|
231
265
|
*/
|
|
232
266
|
private updateLinkVisibility;
|
|
267
|
+
/**
|
|
268
|
+
* Update offline redemption visibility when group is fulfilled
|
|
269
|
+
*/
|
|
270
|
+
private updateOfflineRedemptionVisibility;
|
|
233
271
|
/**
|
|
234
272
|
* Subscribe to socket events
|
|
235
273
|
*/
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Offline Redemption Modal
|
|
3
|
+
* Displays QR code and redemption code for fulfilled groups
|
|
4
|
+
*/
|
|
5
|
+
import { OfflineRedemption } from "../../core/types";
|
|
6
|
+
export declare class OfflineRedemptionModal {
|
|
7
|
+
private modalElement;
|
|
8
|
+
private offlineRedemption;
|
|
9
|
+
private onClose?;
|
|
10
|
+
constructor(offlineRedemption: OfflineRedemption, onClose?: () => void);
|
|
11
|
+
/**
|
|
12
|
+
* Open the modal
|
|
13
|
+
*/
|
|
14
|
+
open(): void;
|
|
15
|
+
/**
|
|
16
|
+
* Close the modal
|
|
17
|
+
*/
|
|
18
|
+
close(): void;
|
|
19
|
+
/**
|
|
20
|
+
* Create the modal DOM structure
|
|
21
|
+
*/
|
|
22
|
+
private createModalStructure;
|
|
23
|
+
/**
|
|
24
|
+
* Handle download QR button click
|
|
25
|
+
*/
|
|
26
|
+
private handleDownloadQR;
|
|
27
|
+
/**
|
|
28
|
+
* Handle copy code button click
|
|
29
|
+
*/
|
|
30
|
+
private handleCopyCode;
|
|
31
|
+
/**
|
|
32
|
+
* Inject modal styles
|
|
33
|
+
*/
|
|
34
|
+
private injectStyles;
|
|
35
|
+
}
|
|
@@ -29,6 +29,8 @@ export declare class WidgetRoot {
|
|
|
29
29
|
private lastGroupDataRefreshTime;
|
|
30
30
|
private readonly GROUP_REFRESH_DEBOUNCE;
|
|
31
31
|
private groupExpiryRefreshTriggered;
|
|
32
|
+
private offlineRedemption;
|
|
33
|
+
private offlineRedemptionModal;
|
|
32
34
|
constructor(config: InternalConfig, apiClient: ApiClient | null, analyticsClient?: AnalyticsClient | null);
|
|
33
35
|
/** Subscribe once to backend socket events routed through the host page */
|
|
34
36
|
private subscribeToSocketEvents;
|
|
@@ -104,6 +106,10 @@ export declare class WidgetRoot {
|
|
|
104
106
|
* Handle CTA button click with analytics and modal opening
|
|
105
107
|
*/
|
|
106
108
|
private handleCTAClick;
|
|
109
|
+
/**
|
|
110
|
+
* Open offline redemption modal when user clicks "Redeem In-store"
|
|
111
|
+
*/
|
|
112
|
+
private openOfflineRedemptionModal;
|
|
107
113
|
/**
|
|
108
114
|
* Emit checkout intent without performing navigation
|
|
109
115
|
*/
|
package/package.json
CHANGED
|
@@ -1,126 +0,0 @@
|
|
|
1
|
-
import { InternalConfig } from "./types";
|
|
2
|
-
export interface GroupPayload {
|
|
3
|
-
id: string;
|
|
4
|
-
group_name: string;
|
|
5
|
-
participants_count: number;
|
|
6
|
-
max_participants: number;
|
|
7
|
-
status: string;
|
|
8
|
-
expiry_at: Date | string;
|
|
9
|
-
timeLeftSeconds: number;
|
|
10
|
-
}
|
|
11
|
-
export interface MembershipPayload {
|
|
12
|
-
id: string;
|
|
13
|
-
session_id: string;
|
|
14
|
-
created_at: Date | string;
|
|
15
|
-
}
|
|
16
|
-
export interface GroupMemberJoinedPayload {
|
|
17
|
-
group: GroupPayload;
|
|
18
|
-
membership: MembershipPayload;
|
|
19
|
-
product_id?: string;
|
|
20
|
-
isPrimary?: boolean;
|
|
21
|
-
}
|
|
22
|
-
export interface GroupCreatedPayload {
|
|
23
|
-
group: GroupPayload;
|
|
24
|
-
membership: MembershipPayload;
|
|
25
|
-
product_id?: string;
|
|
26
|
-
}
|
|
27
|
-
export interface GroupFulfilledPayload {
|
|
28
|
-
group: GroupPayload;
|
|
29
|
-
frozen_reward: unknown;
|
|
30
|
-
product_id?: string | null;
|
|
31
|
-
}
|
|
32
|
-
export interface SocketClientConfig {
|
|
33
|
-
serverUrl: string;
|
|
34
|
-
merchantKey?: string;
|
|
35
|
-
sdkVersion?: string;
|
|
36
|
-
sessionId?: string;
|
|
37
|
-
debug?: boolean;
|
|
38
|
-
}
|
|
39
|
-
export interface SocketEventHandlers {
|
|
40
|
-
onGroupMemberJoined?: (payload: GroupMemberJoinedPayload) => void;
|
|
41
|
-
onGroupCreated?: (payload: GroupCreatedPayload) => void;
|
|
42
|
-
onGroupFulfilled?: (payload: GroupFulfilledPayload) => void;
|
|
43
|
-
onConnect?: () => void;
|
|
44
|
-
onDisconnect?: (reason: string) => void;
|
|
45
|
-
onError?: (error: Error) => void;
|
|
46
|
-
}
|
|
47
|
-
/**
|
|
48
|
-
* Frontend Socket.IO client for real-time group updates
|
|
49
|
-
* Manages connection to the backend /sdk namespace and handles group subscriptions
|
|
50
|
-
*/
|
|
51
|
-
export declare class SocketClient {
|
|
52
|
-
private socket;
|
|
53
|
-
private logger;
|
|
54
|
-
private config;
|
|
55
|
-
private handlers;
|
|
56
|
-
private currentGroupId;
|
|
57
|
-
private currentProductId;
|
|
58
|
-
private maxReconnectAttempts;
|
|
59
|
-
constructor(config: SocketClientConfig);
|
|
60
|
-
/**
|
|
61
|
-
* Connect to the Socket.IO server
|
|
62
|
-
* @param handlers - Event handlers for socket events
|
|
63
|
-
*/
|
|
64
|
-
connect(handlers: SocketEventHandlers): Promise<void>;
|
|
65
|
-
/**
|
|
66
|
-
* Register event listeners for group updates
|
|
67
|
-
*/
|
|
68
|
-
private registerEventListeners;
|
|
69
|
-
/**
|
|
70
|
-
* Subscribe to a specific group's updates
|
|
71
|
-
* @param groupId - The group ID to subscribe to
|
|
72
|
-
*/
|
|
73
|
-
subscribeToGroup(groupId: string): void;
|
|
74
|
-
/**
|
|
75
|
-
* Unsubscribe from a specific group's updates
|
|
76
|
-
* @param groupId - The group ID to unsubscribe from
|
|
77
|
-
*/
|
|
78
|
-
unsubscribeFromGroup(groupId: string): void;
|
|
79
|
-
/**
|
|
80
|
-
* Subscribe to product availability updates (groups being created for the product)
|
|
81
|
-
* @param productId - The product ID to watch for
|
|
82
|
-
*/
|
|
83
|
-
subscribeToProductAvailable(productId: string): void;
|
|
84
|
-
/**
|
|
85
|
-
* Unsubscribe from product availability updates
|
|
86
|
-
* @param productId - The product ID to stop watching
|
|
87
|
-
*/
|
|
88
|
-
unsubscribeFromProductAvailable(productId: string): void;
|
|
89
|
-
/**
|
|
90
|
-
* Check if socket is connected
|
|
91
|
-
*/
|
|
92
|
-
isConnected(): boolean;
|
|
93
|
-
/**
|
|
94
|
-
* Get current socket ID
|
|
95
|
-
*/
|
|
96
|
-
getSocketId(): string | null;
|
|
97
|
-
/**
|
|
98
|
-
* Get currently subscribed group ID
|
|
99
|
-
*/
|
|
100
|
-
getCurrentGroupId(): string | null;
|
|
101
|
-
/**
|
|
102
|
-
* Get currently subscribed product ID
|
|
103
|
-
*/
|
|
104
|
-
getCurrentProductId(): string | null;
|
|
105
|
-
/**
|
|
106
|
-
* Disconnect from the server
|
|
107
|
-
*/
|
|
108
|
-
disconnect(): void;
|
|
109
|
-
/**
|
|
110
|
-
* Force reconnection to the server
|
|
111
|
-
*/
|
|
112
|
-
reconnect(): void;
|
|
113
|
-
/**
|
|
114
|
-
* Update authentication credentials
|
|
115
|
-
* @param merchantKey - New merchant key
|
|
116
|
-
*/
|
|
117
|
-
updateAuth(merchantKey: string): void;
|
|
118
|
-
}
|
|
119
|
-
/**
|
|
120
|
-
* Create a socket client from SDK config
|
|
121
|
-
* @param config - Internal SDK configuration
|
|
122
|
-
* @param sdkVersion - SDK version
|
|
123
|
-
* @param sessionId - Session ID from CoBuy instance
|
|
124
|
-
* @returns Configured SocketClient instance
|
|
125
|
-
*/
|
|
126
|
-
export declare function createSocketClient(config: InternalConfig, sdkVersion: string, sessionId: string): SocketClient;
|