payload-plugin-newsletter 0.20.0 → 0.20.2
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/CHANGELOG.md +43 -0
- package/dist/admin.d.ts +706 -0
- package/dist/{components.js → admin.js} +832 -1458
- package/dist/broadcast-VMCYSZRY.js +6 -0
- package/dist/chunk-XVMYJQRQ.js +490 -0
- package/dist/client.d.ts +131 -15
- package/dist/client.js +1 -1
- package/dist/server.d.ts +735 -0
- package/dist/{index.js → server.js} +30 -654
- package/package.json +17 -27
- package/ESM_FIX_SUMMARY.md +0 -74
- package/PREVIEW_CUSTOMIZATION_TASK.md +0 -201
- package/dist/client.cjs +0 -891
- package/dist/client.cjs.map +0 -1
- package/dist/client.d.cts +0 -53
- package/dist/client.js.map +0 -1
- package/dist/components.cjs +0 -2460
- package/dist/components.cjs.map +0 -1
- package/dist/components.d.cts +0 -66
- package/dist/components.d.ts +0 -66
- package/dist/components.js.map +0 -1
- package/dist/index.cjs +0 -5545
- package/dist/index.cjs.map +0 -1
- package/dist/index.d.cts +0 -90
- package/dist/index.d.ts +0 -90
- package/dist/index.js.map +0 -1
|
@@ -0,0 +1,490 @@
|
|
|
1
|
+
// src/types/newsletter.ts
|
|
2
|
+
var NewsletterProviderError = class extends Error {
|
|
3
|
+
constructor(message, code, provider, details) {
|
|
4
|
+
super(message);
|
|
5
|
+
this.code = code;
|
|
6
|
+
this.provider = provider;
|
|
7
|
+
this.details = details;
|
|
8
|
+
this.name = "NewsletterProviderError";
|
|
9
|
+
}
|
|
10
|
+
};
|
|
11
|
+
|
|
12
|
+
// src/types/broadcast.ts
|
|
13
|
+
var BroadcastProviderError = class extends Error {
|
|
14
|
+
constructor(message, code, provider, details) {
|
|
15
|
+
super(message);
|
|
16
|
+
this.code = code;
|
|
17
|
+
this.provider = provider;
|
|
18
|
+
this.details = details;
|
|
19
|
+
this.name = "BroadcastProviderError";
|
|
20
|
+
}
|
|
21
|
+
};
|
|
22
|
+
|
|
23
|
+
// src/types/providers.ts
|
|
24
|
+
var BaseBroadcastProvider = class {
|
|
25
|
+
constructor(config) {
|
|
26
|
+
this.config = config;
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Schedule a broadcast - default implementation throws not supported
|
|
30
|
+
*/
|
|
31
|
+
async schedule(_id, _scheduledAt) {
|
|
32
|
+
const capabilities = this.getCapabilities();
|
|
33
|
+
if (!capabilities.supportsScheduling) {
|
|
34
|
+
throw new BroadcastProviderError(
|
|
35
|
+
"Scheduling is not supported by this provider",
|
|
36
|
+
"NOT_SUPPORTED" /* NOT_SUPPORTED */,
|
|
37
|
+
this.name
|
|
38
|
+
);
|
|
39
|
+
}
|
|
40
|
+
throw new Error("Method not implemented");
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Cancel scheduled broadcast - default implementation throws not supported
|
|
44
|
+
*/
|
|
45
|
+
async cancelSchedule(_id) {
|
|
46
|
+
const capabilities = this.getCapabilities();
|
|
47
|
+
if (!capabilities.supportsScheduling) {
|
|
48
|
+
throw new BroadcastProviderError(
|
|
49
|
+
"Scheduling is not supported by this provider",
|
|
50
|
+
"NOT_SUPPORTED" /* NOT_SUPPORTED */,
|
|
51
|
+
this.name
|
|
52
|
+
);
|
|
53
|
+
}
|
|
54
|
+
throw new Error("Method not implemented");
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Get analytics - default implementation returns zeros
|
|
58
|
+
*/
|
|
59
|
+
async getAnalytics(_id) {
|
|
60
|
+
const capabilities = this.getCapabilities();
|
|
61
|
+
if (!capabilities.supportsAnalytics) {
|
|
62
|
+
throw new BroadcastProviderError(
|
|
63
|
+
"Analytics are not supported by this provider",
|
|
64
|
+
"NOT_SUPPORTED" /* NOT_SUPPORTED */,
|
|
65
|
+
this.name
|
|
66
|
+
);
|
|
67
|
+
}
|
|
68
|
+
return {
|
|
69
|
+
sent: 0,
|
|
70
|
+
delivered: 0,
|
|
71
|
+
opened: 0,
|
|
72
|
+
clicked: 0,
|
|
73
|
+
bounced: 0,
|
|
74
|
+
complained: 0,
|
|
75
|
+
unsubscribed: 0
|
|
76
|
+
};
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Helper method to validate required fields
|
|
80
|
+
*/
|
|
81
|
+
validateRequiredFields(data, fields) {
|
|
82
|
+
const missing = fields.filter((field) => !data[field]);
|
|
83
|
+
if (missing.length > 0) {
|
|
84
|
+
throw new BroadcastProviderError(
|
|
85
|
+
`Missing required fields: ${missing.join(", ")}`,
|
|
86
|
+
"VALIDATION_ERROR" /* VALIDATION_ERROR */,
|
|
87
|
+
this.name
|
|
88
|
+
);
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
/**
|
|
92
|
+
* Helper method to check if a status transition is allowed
|
|
93
|
+
*/
|
|
94
|
+
canEditInStatus(status) {
|
|
95
|
+
const capabilities = this.getCapabilities();
|
|
96
|
+
return capabilities.editableStatuses.includes(status);
|
|
97
|
+
}
|
|
98
|
+
/**
|
|
99
|
+
* Helper to build pagination response
|
|
100
|
+
*/
|
|
101
|
+
buildListResponse(items, total, options = {}) {
|
|
102
|
+
const limit = options.limit || 20;
|
|
103
|
+
const offset = options.offset || 0;
|
|
104
|
+
return {
|
|
105
|
+
items,
|
|
106
|
+
total,
|
|
107
|
+
limit,
|
|
108
|
+
offset,
|
|
109
|
+
hasMore: offset + items.length < total
|
|
110
|
+
};
|
|
111
|
+
}
|
|
112
|
+
};
|
|
113
|
+
|
|
114
|
+
// src/providers/broadcast/broadcast.ts
|
|
115
|
+
var BroadcastApiProvider = class extends BaseBroadcastProvider {
|
|
116
|
+
constructor(config) {
|
|
117
|
+
super(config);
|
|
118
|
+
this.name = "broadcast";
|
|
119
|
+
this.apiUrl = config.apiUrl.replace(/\/$/, "");
|
|
120
|
+
this.token = config.token;
|
|
121
|
+
if (!this.token) {
|
|
122
|
+
throw new BroadcastProviderError(
|
|
123
|
+
"Broadcast API token is required",
|
|
124
|
+
"CONFIGURATION_ERROR" /* CONFIGURATION_ERROR */,
|
|
125
|
+
this.name
|
|
126
|
+
);
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
// Broadcast Management Methods
|
|
130
|
+
async list(options) {
|
|
131
|
+
try {
|
|
132
|
+
const params = new URLSearchParams();
|
|
133
|
+
if (options?.limit) params.append("limit", options.limit.toString());
|
|
134
|
+
if (options?.offset) params.append("offset", options.offset.toString());
|
|
135
|
+
const response = await fetch(`${this.apiUrl}/api/v1/broadcasts?${params}`, {
|
|
136
|
+
method: "GET",
|
|
137
|
+
headers: {
|
|
138
|
+
"Authorization": `Bearer ${this.token}`,
|
|
139
|
+
"Content-Type": "application/json"
|
|
140
|
+
}
|
|
141
|
+
});
|
|
142
|
+
if (!response.ok) {
|
|
143
|
+
const error = await response.text();
|
|
144
|
+
throw new Error(`Broadcast API error: ${response.status} - ${error}`);
|
|
145
|
+
}
|
|
146
|
+
const data = await response.json();
|
|
147
|
+
const broadcasts = data.data.map((broadcast) => this.transformBroadcastFromApi(broadcast));
|
|
148
|
+
return this.buildListResponse(broadcasts, data.total, options);
|
|
149
|
+
} catch (error) {
|
|
150
|
+
throw new BroadcastProviderError(
|
|
151
|
+
`Failed to list broadcasts: ${error instanceof Error ? error.message : "Unknown error"}`,
|
|
152
|
+
"PROVIDER_ERROR" /* PROVIDER_ERROR */,
|
|
153
|
+
this.name,
|
|
154
|
+
error
|
|
155
|
+
);
|
|
156
|
+
}
|
|
157
|
+
}
|
|
158
|
+
async get(id) {
|
|
159
|
+
try {
|
|
160
|
+
const response = await fetch(`${this.apiUrl}/api/v1/broadcasts/${id}`, {
|
|
161
|
+
method: "GET",
|
|
162
|
+
headers: {
|
|
163
|
+
"Authorization": `Bearer ${this.token}`,
|
|
164
|
+
"Content-Type": "application/json"
|
|
165
|
+
}
|
|
166
|
+
});
|
|
167
|
+
if (!response.ok) {
|
|
168
|
+
if (response.status === 404) {
|
|
169
|
+
throw new BroadcastProviderError(
|
|
170
|
+
`Broadcast not found: ${id}`,
|
|
171
|
+
"NOT_FOUND" /* NOT_FOUND */,
|
|
172
|
+
this.name
|
|
173
|
+
);
|
|
174
|
+
}
|
|
175
|
+
const error = await response.text();
|
|
176
|
+
throw new Error(`Broadcast API error: ${response.status} - ${error}`);
|
|
177
|
+
}
|
|
178
|
+
const broadcast = await response.json();
|
|
179
|
+
return this.transformBroadcastFromApi(broadcast);
|
|
180
|
+
} catch (error) {
|
|
181
|
+
if (error instanceof BroadcastProviderError) throw error;
|
|
182
|
+
throw new BroadcastProviderError(
|
|
183
|
+
`Failed to get broadcast: ${error instanceof Error ? error.message : "Unknown error"}`,
|
|
184
|
+
"PROVIDER_ERROR" /* PROVIDER_ERROR */,
|
|
185
|
+
this.name,
|
|
186
|
+
error
|
|
187
|
+
);
|
|
188
|
+
}
|
|
189
|
+
}
|
|
190
|
+
async create(data) {
|
|
191
|
+
try {
|
|
192
|
+
this.validateRequiredFields(data, ["name", "subject", "content"]);
|
|
193
|
+
const requestBody = {
|
|
194
|
+
broadcast: {
|
|
195
|
+
name: data.name,
|
|
196
|
+
subject: data.subject,
|
|
197
|
+
preheader: data.preheader,
|
|
198
|
+
body: data.content,
|
|
199
|
+
html_body: true,
|
|
200
|
+
track_opens: data.trackOpens ?? true,
|
|
201
|
+
track_clicks: data.trackClicks ?? true,
|
|
202
|
+
reply_to: data.replyTo,
|
|
203
|
+
segment_ids: data.audienceIds
|
|
204
|
+
}
|
|
205
|
+
};
|
|
206
|
+
console.log("[BroadcastApiProvider] Creating broadcast:", {
|
|
207
|
+
url: `${this.apiUrl}/api/v1/broadcasts`,
|
|
208
|
+
method: "POST",
|
|
209
|
+
hasToken: !!this.token,
|
|
210
|
+
tokenLength: this.token?.length,
|
|
211
|
+
body: JSON.stringify(requestBody, null, 2)
|
|
212
|
+
});
|
|
213
|
+
const response = await fetch(`${this.apiUrl}/api/v1/broadcasts`, {
|
|
214
|
+
method: "POST",
|
|
215
|
+
headers: {
|
|
216
|
+
"Authorization": `Bearer ${this.token}`,
|
|
217
|
+
"Content-Type": "application/json"
|
|
218
|
+
},
|
|
219
|
+
body: JSON.stringify(requestBody)
|
|
220
|
+
});
|
|
221
|
+
console.log("[BroadcastApiProvider] Response status:", response.status);
|
|
222
|
+
console.log("[BroadcastApiProvider] Response headers:", Object.fromEntries(response.headers.entries()));
|
|
223
|
+
if (!response.ok) {
|
|
224
|
+
const errorText = await response.text();
|
|
225
|
+
console.error("[BroadcastApiProvider] Error response body:", errorText);
|
|
226
|
+
let errorDetails;
|
|
227
|
+
try {
|
|
228
|
+
errorDetails = JSON.parse(errorText);
|
|
229
|
+
console.error("[BroadcastApiProvider] Parsed error:", errorDetails);
|
|
230
|
+
} catch {
|
|
231
|
+
}
|
|
232
|
+
throw new Error(`Broadcast API error: ${response.status} - ${errorText}`);
|
|
233
|
+
}
|
|
234
|
+
const result = await response.json();
|
|
235
|
+
return this.get(result.id.toString());
|
|
236
|
+
} catch (error) {
|
|
237
|
+
if (error instanceof BroadcastProviderError) throw error;
|
|
238
|
+
throw new BroadcastProviderError(
|
|
239
|
+
`Failed to create broadcast: ${error instanceof Error ? error.message : "Unknown error"}`,
|
|
240
|
+
"PROVIDER_ERROR" /* PROVIDER_ERROR */,
|
|
241
|
+
this.name,
|
|
242
|
+
error
|
|
243
|
+
);
|
|
244
|
+
}
|
|
245
|
+
}
|
|
246
|
+
async update(id, data) {
|
|
247
|
+
try {
|
|
248
|
+
const existing = await this.get(id);
|
|
249
|
+
if (!this.canEditInStatus(existing.sendStatus)) {
|
|
250
|
+
throw new BroadcastProviderError(
|
|
251
|
+
`Cannot update broadcast in status: ${existing.sendStatus}`,
|
|
252
|
+
"INVALID_STATUS" /* INVALID_STATUS */,
|
|
253
|
+
this.name
|
|
254
|
+
);
|
|
255
|
+
}
|
|
256
|
+
const response = await fetch(`${this.apiUrl}/api/v1/broadcasts/${id}`, {
|
|
257
|
+
method: "PATCH",
|
|
258
|
+
headers: {
|
|
259
|
+
"Authorization": `Bearer ${this.token}`,
|
|
260
|
+
"Content-Type": "application/json"
|
|
261
|
+
},
|
|
262
|
+
body: JSON.stringify({
|
|
263
|
+
broadcast: {
|
|
264
|
+
name: data.name,
|
|
265
|
+
subject: data.subject,
|
|
266
|
+
preheader: data.preheader,
|
|
267
|
+
body: data.content,
|
|
268
|
+
track_opens: data.trackOpens,
|
|
269
|
+
track_clicks: data.trackClicks,
|
|
270
|
+
reply_to: data.replyTo,
|
|
271
|
+
segment_ids: data.audienceIds
|
|
272
|
+
}
|
|
273
|
+
})
|
|
274
|
+
});
|
|
275
|
+
if (!response.ok) {
|
|
276
|
+
const error = await response.text();
|
|
277
|
+
throw new Error(`Broadcast API error: ${response.status} - ${error}`);
|
|
278
|
+
}
|
|
279
|
+
const broadcast = await response.json();
|
|
280
|
+
return this.transformBroadcastFromApi(broadcast);
|
|
281
|
+
} catch (error) {
|
|
282
|
+
if (error instanceof BroadcastProviderError) throw error;
|
|
283
|
+
throw new BroadcastProviderError(
|
|
284
|
+
`Failed to update broadcast: ${error instanceof Error ? error.message : "Unknown error"}`,
|
|
285
|
+
"PROVIDER_ERROR" /* PROVIDER_ERROR */,
|
|
286
|
+
this.name,
|
|
287
|
+
error
|
|
288
|
+
);
|
|
289
|
+
}
|
|
290
|
+
}
|
|
291
|
+
async delete(id) {
|
|
292
|
+
try {
|
|
293
|
+
const existing = await this.get(id);
|
|
294
|
+
if (!this.canEditInStatus(existing.sendStatus)) {
|
|
295
|
+
throw new BroadcastProviderError(
|
|
296
|
+
`Cannot delete broadcast in status: ${existing.sendStatus}`,
|
|
297
|
+
"INVALID_STATUS" /* INVALID_STATUS */,
|
|
298
|
+
this.name
|
|
299
|
+
);
|
|
300
|
+
}
|
|
301
|
+
const response = await fetch(`${this.apiUrl}/api/v1/broadcasts/${id}`, {
|
|
302
|
+
method: "DELETE",
|
|
303
|
+
headers: {
|
|
304
|
+
"Authorization": `Bearer ${this.token}`,
|
|
305
|
+
"Content-Type": "application/json"
|
|
306
|
+
}
|
|
307
|
+
});
|
|
308
|
+
if (!response.ok) {
|
|
309
|
+
const error = await response.text();
|
|
310
|
+
throw new Error(`Broadcast API error: ${response.status} - ${error}`);
|
|
311
|
+
}
|
|
312
|
+
} catch (error) {
|
|
313
|
+
if (error instanceof BroadcastProviderError) throw error;
|
|
314
|
+
throw new BroadcastProviderError(
|
|
315
|
+
`Failed to delete broadcast: ${error instanceof Error ? error.message : "Unknown error"}`,
|
|
316
|
+
"PROVIDER_ERROR" /* PROVIDER_ERROR */,
|
|
317
|
+
this.name,
|
|
318
|
+
error
|
|
319
|
+
);
|
|
320
|
+
}
|
|
321
|
+
}
|
|
322
|
+
async send(id, options) {
|
|
323
|
+
try {
|
|
324
|
+
if (options?.testMode && options.testRecipients?.length) {
|
|
325
|
+
throw new BroadcastProviderError(
|
|
326
|
+
"Test send is not yet implemented for Broadcast provider",
|
|
327
|
+
"NOT_SUPPORTED" /* NOT_SUPPORTED */,
|
|
328
|
+
this.name
|
|
329
|
+
);
|
|
330
|
+
}
|
|
331
|
+
const response = await fetch(`${this.apiUrl}/api/v1/broadcasts/${id}/send_broadcast`, {
|
|
332
|
+
method: "POST",
|
|
333
|
+
headers: {
|
|
334
|
+
"Authorization": `Bearer ${this.token}`,
|
|
335
|
+
"Content-Type": "application/json"
|
|
336
|
+
},
|
|
337
|
+
body: JSON.stringify({
|
|
338
|
+
segment_ids: options?.audienceIds
|
|
339
|
+
})
|
|
340
|
+
});
|
|
341
|
+
if (!response.ok) {
|
|
342
|
+
const error = await response.text();
|
|
343
|
+
throw new Error(`Broadcast API error: ${response.status} - ${error}`);
|
|
344
|
+
}
|
|
345
|
+
const result = await response.json();
|
|
346
|
+
return this.get(result.id.toString());
|
|
347
|
+
} catch (error) {
|
|
348
|
+
if (error instanceof BroadcastProviderError) throw error;
|
|
349
|
+
throw new BroadcastProviderError(
|
|
350
|
+
`Failed to send broadcast: ${error instanceof Error ? error.message : "Unknown error"}`,
|
|
351
|
+
"PROVIDER_ERROR" /* PROVIDER_ERROR */,
|
|
352
|
+
this.name,
|
|
353
|
+
error
|
|
354
|
+
);
|
|
355
|
+
}
|
|
356
|
+
}
|
|
357
|
+
async schedule(id, scheduledAt) {
|
|
358
|
+
try {
|
|
359
|
+
const response = await fetch(`${this.apiUrl}/api/v1/broadcasts/${id}`, {
|
|
360
|
+
method: "PATCH",
|
|
361
|
+
headers: {
|
|
362
|
+
"Authorization": `Bearer ${this.token}`,
|
|
363
|
+
"Content-Type": "application/json"
|
|
364
|
+
},
|
|
365
|
+
body: JSON.stringify({
|
|
366
|
+
broadcast: {
|
|
367
|
+
scheduled_send_at: scheduledAt.toISOString(),
|
|
368
|
+
// TODO: Handle timezone properly
|
|
369
|
+
scheduled_timezone: Intl.DateTimeFormat().resolvedOptions().timeZone
|
|
370
|
+
}
|
|
371
|
+
})
|
|
372
|
+
});
|
|
373
|
+
if (!response.ok) {
|
|
374
|
+
const error = await response.text();
|
|
375
|
+
throw new Error(`Broadcast API error: ${response.status} - ${error}`);
|
|
376
|
+
}
|
|
377
|
+
const broadcast = await response.json();
|
|
378
|
+
return this.transformBroadcastFromApi(broadcast);
|
|
379
|
+
} catch (error) {
|
|
380
|
+
throw new BroadcastProviderError(
|
|
381
|
+
`Failed to schedule broadcast: ${error instanceof Error ? error.message : "Unknown error"}`,
|
|
382
|
+
"PROVIDER_ERROR" /* PROVIDER_ERROR */,
|
|
383
|
+
this.name,
|
|
384
|
+
error
|
|
385
|
+
);
|
|
386
|
+
}
|
|
387
|
+
}
|
|
388
|
+
async cancelSchedule(id) {
|
|
389
|
+
try {
|
|
390
|
+
const response = await fetch(`${this.apiUrl}/api/v1/broadcasts/${id}`, {
|
|
391
|
+
method: "PATCH",
|
|
392
|
+
headers: {
|
|
393
|
+
"Authorization": `Bearer ${this.token}`,
|
|
394
|
+
"Content-Type": "application/json"
|
|
395
|
+
},
|
|
396
|
+
body: JSON.stringify({
|
|
397
|
+
broadcast: {
|
|
398
|
+
scheduled_send_at: null,
|
|
399
|
+
scheduled_timezone: null
|
|
400
|
+
}
|
|
401
|
+
})
|
|
402
|
+
});
|
|
403
|
+
if (!response.ok) {
|
|
404
|
+
const error = await response.text();
|
|
405
|
+
throw new Error(`Broadcast API error: ${response.status} - ${error}`);
|
|
406
|
+
}
|
|
407
|
+
const broadcast = await response.json();
|
|
408
|
+
return this.transformBroadcastFromApi(broadcast);
|
|
409
|
+
} catch (error) {
|
|
410
|
+
throw new BroadcastProviderError(
|
|
411
|
+
`Failed to cancel scheduled broadcast: ${error instanceof Error ? error.message : "Unknown error"}`,
|
|
412
|
+
"PROVIDER_ERROR" /* PROVIDER_ERROR */,
|
|
413
|
+
this.name,
|
|
414
|
+
error
|
|
415
|
+
);
|
|
416
|
+
}
|
|
417
|
+
}
|
|
418
|
+
async getAnalytics(_id) {
|
|
419
|
+
throw new BroadcastProviderError(
|
|
420
|
+
"Analytics API not yet implemented for Broadcast provider",
|
|
421
|
+
"NOT_SUPPORTED" /* NOT_SUPPORTED */,
|
|
422
|
+
this.name
|
|
423
|
+
);
|
|
424
|
+
}
|
|
425
|
+
getCapabilities() {
|
|
426
|
+
return {
|
|
427
|
+
supportsScheduling: true,
|
|
428
|
+
supportsSegmentation: true,
|
|
429
|
+
supportsAnalytics: false,
|
|
430
|
+
// Not documented yet
|
|
431
|
+
supportsABTesting: false,
|
|
432
|
+
supportsTemplates: false,
|
|
433
|
+
supportsPersonalization: true,
|
|
434
|
+
supportsMultipleChannels: false,
|
|
435
|
+
supportsChannelSegmentation: false,
|
|
436
|
+
editableStatuses: ["draft" /* DRAFT */, "scheduled" /* SCHEDULED */],
|
|
437
|
+
supportedContentTypes: ["html", "text"]
|
|
438
|
+
};
|
|
439
|
+
}
|
|
440
|
+
async validateConfiguration() {
|
|
441
|
+
try {
|
|
442
|
+
await this.list({ limit: 1 });
|
|
443
|
+
return true;
|
|
444
|
+
} catch {
|
|
445
|
+
return false;
|
|
446
|
+
}
|
|
447
|
+
}
|
|
448
|
+
transformBroadcastFromApi(broadcast) {
|
|
449
|
+
return {
|
|
450
|
+
id: broadcast.id.toString(),
|
|
451
|
+
name: broadcast.name,
|
|
452
|
+
subject: broadcast.subject,
|
|
453
|
+
preheader: broadcast.preheader,
|
|
454
|
+
content: broadcast.body,
|
|
455
|
+
sendStatus: this.mapBroadcastStatus(broadcast.status),
|
|
456
|
+
trackOpens: broadcast.track_opens,
|
|
457
|
+
trackClicks: broadcast.track_clicks,
|
|
458
|
+
replyTo: broadcast.reply_to,
|
|
459
|
+
recipientCount: broadcast.total_recipients,
|
|
460
|
+
sentAt: broadcast.sent_at ? new Date(broadcast.sent_at) : void 0,
|
|
461
|
+
scheduledAt: broadcast.scheduled_send_at ? new Date(broadcast.scheduled_send_at) : void 0,
|
|
462
|
+
createdAt: new Date(broadcast.created_at),
|
|
463
|
+
updatedAt: new Date(broadcast.updated_at),
|
|
464
|
+
providerData: { broadcast },
|
|
465
|
+
providerId: broadcast.id.toString(),
|
|
466
|
+
providerType: "broadcast"
|
|
467
|
+
};
|
|
468
|
+
}
|
|
469
|
+
mapBroadcastStatus(status) {
|
|
470
|
+
const statusMap = {
|
|
471
|
+
"draft": "draft" /* DRAFT */,
|
|
472
|
+
"scheduled": "scheduled" /* SCHEDULED */,
|
|
473
|
+
"queueing": "sending" /* SENDING */,
|
|
474
|
+
"sending": "sending" /* SENDING */,
|
|
475
|
+
"sent": "sent" /* SENT */,
|
|
476
|
+
"failed": "failed" /* FAILED */,
|
|
477
|
+
"partial_failure": "failed" /* FAILED */,
|
|
478
|
+
"paused": "paused" /* PAUSED */,
|
|
479
|
+
"aborted": "canceled" /* CANCELED */
|
|
480
|
+
};
|
|
481
|
+
return statusMap[status] || "draft" /* DRAFT */;
|
|
482
|
+
}
|
|
483
|
+
};
|
|
484
|
+
|
|
485
|
+
export {
|
|
486
|
+
NewsletterProviderError,
|
|
487
|
+
BroadcastProviderError,
|
|
488
|
+
BaseBroadcastProvider,
|
|
489
|
+
BroadcastApiProvider
|
|
490
|
+
};
|
package/dist/client.d.ts
CHANGED
|
@@ -1,12 +1,128 @@
|
|
|
1
|
-
import React from 'react';
|
|
2
|
-
import { SignupFormProps, PreferencesFormProps, Subscriber } from './types.js';
|
|
3
|
-
import 'payload';
|
|
1
|
+
import React$1 from 'react';
|
|
4
2
|
|
|
5
|
-
|
|
6
|
-
|
|
3
|
+
interface Subscriber {
|
|
4
|
+
id: string;
|
|
5
|
+
email: string;
|
|
6
|
+
name?: string;
|
|
7
|
+
locale?: string;
|
|
8
|
+
subscriptionStatus: 'active' | 'unsubscribed' | 'pending';
|
|
9
|
+
emailPreferences?: {
|
|
10
|
+
newsletter?: boolean;
|
|
11
|
+
announcements?: boolean;
|
|
12
|
+
[key: string]: boolean | undefined;
|
|
13
|
+
};
|
|
14
|
+
source?: string;
|
|
15
|
+
utmParameters?: {
|
|
16
|
+
source?: string;
|
|
17
|
+
medium?: string;
|
|
18
|
+
campaign?: string;
|
|
19
|
+
content?: string;
|
|
20
|
+
term?: string;
|
|
21
|
+
};
|
|
22
|
+
signupMetadata?: {
|
|
23
|
+
ipAddress?: string;
|
|
24
|
+
userAgent?: string;
|
|
25
|
+
referrer?: string;
|
|
26
|
+
signupPage?: string;
|
|
27
|
+
};
|
|
28
|
+
leadMagnet?: string;
|
|
29
|
+
unsubscribedAt?: string;
|
|
30
|
+
magicLinkToken?: string;
|
|
31
|
+
magicLinkTokenExpiry?: string;
|
|
32
|
+
createdAt: string;
|
|
33
|
+
updatedAt: string;
|
|
34
|
+
}
|
|
35
|
+
interface SignupFormProps {
|
|
36
|
+
onSuccess?: (subscriber: Subscriber) => void;
|
|
37
|
+
onError?: (error: Error) => void;
|
|
38
|
+
showName?: boolean;
|
|
39
|
+
showPreferences?: boolean;
|
|
40
|
+
leadMagnet?: {
|
|
41
|
+
id: string;
|
|
42
|
+
title: string;
|
|
43
|
+
description?: string;
|
|
44
|
+
};
|
|
45
|
+
className?: string;
|
|
46
|
+
styles?: {
|
|
47
|
+
form?: React.CSSProperties;
|
|
48
|
+
inputGroup?: React.CSSProperties;
|
|
49
|
+
label?: React.CSSProperties;
|
|
50
|
+
input?: React.CSSProperties;
|
|
51
|
+
button?: React.CSSProperties;
|
|
52
|
+
buttonDisabled?: React.CSSProperties;
|
|
53
|
+
error?: React.CSSProperties;
|
|
54
|
+
success?: React.CSSProperties;
|
|
55
|
+
checkbox?: React.CSSProperties;
|
|
56
|
+
checkboxInput?: React.CSSProperties;
|
|
57
|
+
checkboxLabel?: React.CSSProperties;
|
|
58
|
+
};
|
|
59
|
+
apiEndpoint?: string;
|
|
60
|
+
buttonText?: string;
|
|
61
|
+
loadingText?: string;
|
|
62
|
+
successMessage?: string;
|
|
63
|
+
placeholders?: {
|
|
64
|
+
email?: string;
|
|
65
|
+
name?: string;
|
|
66
|
+
};
|
|
67
|
+
labels?: {
|
|
68
|
+
email?: string;
|
|
69
|
+
name?: string;
|
|
70
|
+
newsletter?: string;
|
|
71
|
+
announcements?: string;
|
|
72
|
+
};
|
|
73
|
+
}
|
|
74
|
+
interface PreferencesFormProps {
|
|
75
|
+
subscriber?: Subscriber;
|
|
76
|
+
onSuccess?: (subscriber: Subscriber) => void;
|
|
77
|
+
onError?: (error: Error) => void;
|
|
78
|
+
className?: string;
|
|
79
|
+
styles?: {
|
|
80
|
+
container?: React.CSSProperties;
|
|
81
|
+
heading?: React.CSSProperties;
|
|
82
|
+
form?: React.CSSProperties;
|
|
83
|
+
section?: React.CSSProperties;
|
|
84
|
+
sectionTitle?: React.CSSProperties;
|
|
85
|
+
inputGroup?: React.CSSProperties;
|
|
86
|
+
label?: React.CSSProperties;
|
|
87
|
+
input?: React.CSSProperties;
|
|
88
|
+
select?: React.CSSProperties;
|
|
89
|
+
checkbox?: React.CSSProperties;
|
|
90
|
+
checkboxInput?: React.CSSProperties;
|
|
91
|
+
checkboxLabel?: React.CSSProperties;
|
|
92
|
+
buttonGroup?: React.CSSProperties;
|
|
93
|
+
button?: React.CSSProperties;
|
|
94
|
+
primaryButton?: React.CSSProperties;
|
|
95
|
+
secondaryButton?: React.CSSProperties;
|
|
96
|
+
dangerButton?: React.CSSProperties;
|
|
97
|
+
error?: React.CSSProperties;
|
|
98
|
+
success?: React.CSSProperties;
|
|
99
|
+
info?: React.CSSProperties;
|
|
100
|
+
};
|
|
101
|
+
sessionToken?: string;
|
|
102
|
+
apiEndpoint?: string;
|
|
103
|
+
showUnsubscribe?: boolean;
|
|
104
|
+
locales?: string[];
|
|
105
|
+
labels?: {
|
|
106
|
+
title?: string;
|
|
107
|
+
personalInfo?: string;
|
|
108
|
+
emailPreferences?: string;
|
|
109
|
+
name?: string;
|
|
110
|
+
language?: string;
|
|
111
|
+
newsletter?: string;
|
|
112
|
+
announcements?: string;
|
|
113
|
+
saveButton?: string;
|
|
114
|
+
unsubscribeButton?: string;
|
|
115
|
+
saving?: string;
|
|
116
|
+
saved?: string;
|
|
117
|
+
unsubscribeConfirm?: string;
|
|
118
|
+
};
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
declare const NewsletterForm: React$1.FC<SignupFormProps>;
|
|
122
|
+
declare function createNewsletterForm(defaultProps: Partial<SignupFormProps>): React$1.FC<SignupFormProps>;
|
|
7
123
|
|
|
8
|
-
declare const PreferencesForm: React.FC<PreferencesFormProps>;
|
|
9
|
-
declare function createPreferencesForm(defaultProps: Partial<PreferencesFormProps>): React.FC<PreferencesFormProps>;
|
|
124
|
+
declare const PreferencesForm: React$1.FC<PreferencesFormProps>;
|
|
125
|
+
declare function createPreferencesForm(defaultProps: Partial<PreferencesFormProps>): React$1.FC<PreferencesFormProps>;
|
|
10
126
|
|
|
11
127
|
interface MagicLinkVerifyProps {
|
|
12
128
|
token?: string;
|
|
@@ -15,11 +131,11 @@ interface MagicLinkVerifyProps {
|
|
|
15
131
|
apiEndpoint?: string;
|
|
16
132
|
className?: string;
|
|
17
133
|
styles?: {
|
|
18
|
-
container?: React.CSSProperties;
|
|
19
|
-
heading?: React.CSSProperties;
|
|
20
|
-
message?: React.CSSProperties;
|
|
21
|
-
error?: React.CSSProperties;
|
|
22
|
-
button?: React.CSSProperties;
|
|
134
|
+
container?: React$1.CSSProperties;
|
|
135
|
+
heading?: React$1.CSSProperties;
|
|
136
|
+
message?: React$1.CSSProperties;
|
|
137
|
+
error?: React$1.CSSProperties;
|
|
138
|
+
button?: React$1.CSSProperties;
|
|
23
139
|
};
|
|
24
140
|
labels?: {
|
|
25
141
|
verifying?: string;
|
|
@@ -31,8 +147,8 @@ interface MagicLinkVerifyProps {
|
|
|
31
147
|
tryAgain?: string;
|
|
32
148
|
};
|
|
33
149
|
}
|
|
34
|
-
declare const MagicLinkVerify: React.FC<MagicLinkVerifyProps>;
|
|
35
|
-
declare function createMagicLinkVerify(defaultProps: Partial<MagicLinkVerifyProps>): React.FC<MagicLinkVerifyProps>;
|
|
150
|
+
declare const MagicLinkVerify: React$1.FC<MagicLinkVerifyProps>;
|
|
151
|
+
declare function createMagicLinkVerify(defaultProps: Partial<MagicLinkVerifyProps>): React$1.FC<MagicLinkVerifyProps>;
|
|
36
152
|
|
|
37
153
|
interface UseNewsletterAuthOptions {
|
|
38
154
|
}
|
|
@@ -50,4 +166,4 @@ interface UseNewsletterAuthReturn {
|
|
|
50
166
|
}
|
|
51
167
|
declare function useNewsletterAuth(_options?: UseNewsletterAuthOptions): UseNewsletterAuthReturn;
|
|
52
168
|
|
|
53
|
-
export { MagicLinkVerify, type MagicLinkVerifyProps, NewsletterForm, PreferencesForm,
|
|
169
|
+
export { MagicLinkVerify, type MagicLinkVerifyProps, NewsletterForm, PreferencesForm, createMagicLinkVerify, createNewsletterForm, createPreferencesForm, useNewsletterAuth };
|
package/dist/client.js
CHANGED