payload-plugin-newsletter 0.15.1 → 0.16.1

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.
@@ -52,8 +52,6 @@ declare const EmailRenderer: React.FC<EmailRendererProps>;
52
52
 
53
53
  declare const StatusBadge: React.FC<DefaultCellComponentProps>;
54
54
 
55
- declare const ActionsCell: React.FC<DefaultCellComponentProps>;
56
-
57
55
  declare const EmptyField: React.FC;
58
56
 
59
57
  interface BroadcastTemplateProps {
@@ -63,4 +61,4 @@ interface BroadcastTemplateProps {
63
61
  }
64
62
  declare const DefaultBroadcastTemplate: React.FC<BroadcastTemplateProps>;
65
63
 
66
- export { ActionsCell, BroadcastEditor, BroadcastInlinePreview, BroadcastPreviewField, type BroadcastTemplateProps, DefaultBroadcastTemplate, EmailPreview, EmailPreviewField, EmailRenderer, EmptyField, PreviewControls, StatusBadge };
64
+ export { BroadcastEditor, BroadcastInlinePreview, BroadcastPreviewField, type BroadcastTemplateProps, DefaultBroadcastTemplate, EmailPreview, EmailPreviewField, EmailRenderer, EmptyField, PreviewControls, StatusBadge };
@@ -52,8 +52,6 @@ declare const EmailRenderer: React.FC<EmailRendererProps>;
52
52
 
53
53
  declare const StatusBadge: React.FC<DefaultCellComponentProps>;
54
54
 
55
- declare const ActionsCell: React.FC<DefaultCellComponentProps>;
56
-
57
55
  declare const EmptyField: React.FC;
58
56
 
59
57
  interface BroadcastTemplateProps {
@@ -63,4 +61,4 @@ interface BroadcastTemplateProps {
63
61
  }
64
62
  declare const DefaultBroadcastTemplate: React.FC<BroadcastTemplateProps>;
65
63
 
66
- export { ActionsCell, BroadcastEditor, BroadcastInlinePreview, BroadcastPreviewField, type BroadcastTemplateProps, DefaultBroadcastTemplate, EmailPreview, EmailPreviewField, EmailRenderer, EmptyField, PreviewControls, StatusBadge };
64
+ export { BroadcastEditor, BroadcastInlinePreview, BroadcastPreviewField, type BroadcastTemplateProps, DefaultBroadcastTemplate, EmailPreview, EmailPreviewField, EmailRenderer, EmptyField, PreviewControls, StatusBadge };
@@ -2198,448 +2198,11 @@ var StatusBadge = ({ cellData }) => {
2198
2198
  );
2199
2199
  };
2200
2200
 
2201
- // src/components/Broadcasts/ActionsCell.tsx
2202
- import { useState as useState11 } from "react";
2203
-
2204
- // src/components/Broadcasts/SendBroadcastModal.tsx
2205
- import { useState as useState10, useEffect as useEffect6 } from "react";
2206
- import { Fragment as Fragment3, jsx as jsx13, jsxs as jsxs11 } from "react/jsx-runtime";
2207
- var SendBroadcastModal = ({
2208
- broadcast,
2209
- onClose,
2210
- onSuccess
2211
- }) => {
2212
- const [loading, setLoading] = useState10(false);
2213
- const [error, setError] = useState10(null);
2214
- const [selectedAudiences, setSelectedAudiences] = useState10([]);
2215
- const [audiences, setAudiences] = useState10([]);
2216
- const [providerCapabilities, setProviderCapabilities] = useState10(null);
2217
- const [sendMode, setSendMode] = useState10("now");
2218
- const [scheduledDate, setScheduledDate] = useState10("");
2219
- const [scheduledTime, setScheduledTime] = useState10("");
2220
- useEffect6(() => {
2221
- const fetchData = async () => {
2222
- try {
2223
- setAudiences([
2224
- { id: "all", name: "All Subscribers", subscriberCount: 1e3 },
2225
- { id: "active", name: "Active Subscribers", subscriberCount: 850 }
2226
- ]);
2227
- if (broadcast.channel?.providerType === "broadcast") {
2228
- setProviderCapabilities({ supportsScheduling: true });
2229
- } else {
2230
- setProviderCapabilities({ supportsScheduling: false });
2231
- }
2232
- } catch (err) {
2233
- console.error("Failed to fetch modal data:", err);
2234
- }
2235
- };
2236
- fetchData();
2237
- }, [broadcast.channel]);
2238
- const handleSubmit = async (e) => {
2239
- e.preventDefault();
2240
- setError(null);
2241
- setLoading(true);
2242
- try {
2243
- if (sendMode === "now") {
2244
- const response = await fetch(`/api/broadcasts/${broadcast.id}/send`, {
2245
- method: "POST",
2246
- headers: {
2247
- "Content-Type": "application/json"
2248
- },
2249
- body: JSON.stringify({
2250
- audienceIds: selectedAudiences.length > 0 ? selectedAudiences : void 0
2251
- })
2252
- });
2253
- if (!response.ok) {
2254
- const data = await response.json();
2255
- throw new Error(data.error || "Failed to send broadcast");
2256
- }
2257
- alert(`Broadcast "${broadcast.name}" has been sent successfully`);
2258
- } else {
2259
- if (!scheduledDate || !scheduledTime) {
2260
- throw new Error("Please select both date and time for scheduling");
2261
- }
2262
- const scheduledAt = (/* @__PURE__ */ new Date(`${scheduledDate}T${scheduledTime}`)).toISOString();
2263
- const response = await fetch(`/api/broadcasts/${broadcast.id}/schedule`, {
2264
- method: "POST",
2265
- headers: {
2266
- "Content-Type": "application/json"
2267
- },
2268
- body: JSON.stringify({
2269
- scheduledAt,
2270
- audienceIds: selectedAudiences.length > 0 ? selectedAudiences : void 0
2271
- })
2272
- });
2273
- if (!response.ok) {
2274
- const data = await response.json();
2275
- throw new Error(data.error || "Failed to schedule broadcast");
2276
- }
2277
- alert(`Broadcast "${broadcast.name}" has been scheduled successfully`);
2278
- }
2279
- onSuccess();
2280
- } catch (err) {
2281
- setError(err instanceof Error ? err.message : "An error occurred");
2282
- } finally {
2283
- setLoading(false);
2284
- }
2285
- };
2286
- const handleAudienceToggle = (audienceId) => {
2287
- setSelectedAudiences(
2288
- (prev) => prev.includes(audienceId) ? prev.filter((id) => id !== audienceId) : [...prev, audienceId]
2289
- );
2290
- };
2291
- const now = /* @__PURE__ */ new Date();
2292
- const minDate = now.toISOString().split("T")[0];
2293
- const minTime = now.toTimeString().slice(0, 5);
2294
- return /* @__PURE__ */ jsx13("div", { style: {
2295
- position: "fixed",
2296
- top: 0,
2297
- left: 0,
2298
- right: 0,
2299
- bottom: 0,
2300
- backgroundColor: "rgba(0, 0, 0, 0.5)",
2301
- display: "flex",
2302
- alignItems: "center",
2303
- justifyContent: "center",
2304
- zIndex: 9999
2305
- }, children: /* @__PURE__ */ jsxs11("div", { style: {
2306
- backgroundColor: "white",
2307
- borderRadius: "8px",
2308
- padding: "32px",
2309
- maxWidth: "500px",
2310
- width: "90%",
2311
- maxHeight: "90vh",
2312
- overflowY: "auto"
2313
- }, children: [
2314
- /* @__PURE__ */ jsxs11("h2", { style: { marginTop: 0, marginBottom: "24px" }, children: [
2315
- "Send Broadcast: ",
2316
- broadcast.name
2317
- ] }),
2318
- /* @__PURE__ */ jsxs11("form", { onSubmit: handleSubmit, children: [
2319
- /* @__PURE__ */ jsxs11("div", { style: { marginBottom: "24px" }, children: [
2320
- /* @__PURE__ */ jsx13("label", { style: { fontWeight: "bold", display: "block", marginBottom: "8px" }, children: "When to send:" }),
2321
- /* @__PURE__ */ jsxs11("div", { style: { display: "flex", gap: "16px" }, children: [
2322
- /* @__PURE__ */ jsxs11("label", { style: { display: "flex", alignItems: "center", cursor: "pointer" }, children: [
2323
- /* @__PURE__ */ jsx13(
2324
- "input",
2325
- {
2326
- type: "radio",
2327
- value: "now",
2328
- checked: sendMode === "now",
2329
- onChange: (e) => setSendMode(e.target.value),
2330
- style: { marginRight: "8px" }
2331
- }
2332
- ),
2333
- "Send Now"
2334
- ] }),
2335
- providerCapabilities?.supportsScheduling && /* @__PURE__ */ jsxs11("label", { style: { display: "flex", alignItems: "center", cursor: "pointer" }, children: [
2336
- /* @__PURE__ */ jsx13(
2337
- "input",
2338
- {
2339
- type: "radio",
2340
- value: "schedule",
2341
- checked: sendMode === "schedule",
2342
- onChange: (e) => setSendMode(e.target.value),
2343
- style: { marginRight: "8px" }
2344
- }
2345
- ),
2346
- "Schedule for Later"
2347
- ] })
2348
- ] })
2349
- ] }),
2350
- sendMode === "schedule" && /* @__PURE__ */ jsxs11("div", { style: { marginBottom: "24px" }, children: [
2351
- /* @__PURE__ */ jsx13("label", { style: { fontWeight: "bold", display: "block", marginBottom: "8px" }, children: "Schedule Date & Time:" }),
2352
- /* @__PURE__ */ jsxs11("div", { style: { display: "flex", gap: "8px" }, children: [
2353
- /* @__PURE__ */ jsx13(
2354
- "input",
2355
- {
2356
- type: "date",
2357
- value: scheduledDate,
2358
- onChange: (e) => setScheduledDate(e.target.value),
2359
- min: minDate,
2360
- required: sendMode === "schedule",
2361
- style: {
2362
- padding: "8px 12px",
2363
- border: "1px solid #D1D5DB",
2364
- borderRadius: "4px",
2365
- flex: 1
2366
- }
2367
- }
2368
- ),
2369
- /* @__PURE__ */ jsx13(
2370
- "input",
2371
- {
2372
- type: "time",
2373
- value: scheduledTime,
2374
- onChange: (e) => setScheduledTime(e.target.value),
2375
- min: scheduledDate === minDate ? minTime : void 0,
2376
- required: sendMode === "schedule",
2377
- style: {
2378
- padding: "8px 12px",
2379
- border: "1px solid #D1D5DB",
2380
- borderRadius: "4px",
2381
- flex: 1
2382
- }
2383
- }
2384
- )
2385
- ] })
2386
- ] }),
2387
- audiences.length > 0 && /* @__PURE__ */ jsxs11("div", { style: { marginBottom: "24px" }, children: [
2388
- /* @__PURE__ */ jsx13("label", { style: { fontWeight: "bold", display: "block", marginBottom: "8px" }, children: "Target Audiences (optional):" }),
2389
- /* @__PURE__ */ jsx13("div", { style: {
2390
- border: "1px solid #D1D5DB",
2391
- borderRadius: "4px",
2392
- maxHeight: "200px",
2393
- overflowY: "auto"
2394
- }, children: audiences.map((audience) => /* @__PURE__ */ jsxs11(
2395
- "label",
2396
- {
2397
- style: {
2398
- display: "flex",
2399
- alignItems: "center",
2400
- padding: "12px",
2401
- borderBottom: "1px solid #E5E7EB",
2402
- cursor: "pointer",
2403
- backgroundColor: selectedAudiences.includes(audience.id) ? "#F3F4F6" : "transparent"
2404
- },
2405
- children: [
2406
- /* @__PURE__ */ jsx13(
2407
- "input",
2408
- {
2409
- type: "checkbox",
2410
- checked: selectedAudiences.includes(audience.id),
2411
- onChange: () => handleAudienceToggle(audience.id),
2412
- style: { marginRight: "12px" }
2413
- }
2414
- ),
2415
- /* @__PURE__ */ jsxs11("div", { style: { flex: 1 }, children: [
2416
- /* @__PURE__ */ jsx13("div", { style: { fontWeight: 500 }, children: audience.name }),
2417
- /* @__PURE__ */ jsxs11("div", { style: { fontSize: "14px", color: "#6B7280" }, children: [
2418
- audience.subscriberCount.toLocaleString(),
2419
- " subscribers"
2420
- ] })
2421
- ] })
2422
- ]
2423
- },
2424
- audience.id
2425
- )) }),
2426
- selectedAudiences.length === 0 && /* @__PURE__ */ jsx13("p", { style: { fontSize: "14px", color: "#6B7280", marginTop: "8px" }, children: "If no audiences are selected, the broadcast will be sent to all subscribers." })
2427
- ] }),
2428
- /* @__PURE__ */ jsxs11("div", { style: {
2429
- backgroundColor: "#F3F4F6",
2430
- padding: "16px",
2431
- borderRadius: "4px",
2432
- marginBottom: "24px"
2433
- }, children: [
2434
- /* @__PURE__ */ jsx13("h4", { style: { marginTop: 0, marginBottom: "8px" }, children: "Summary" }),
2435
- /* @__PURE__ */ jsxs11("p", { style: { margin: 0, fontSize: "14px" }, children: [
2436
- /* @__PURE__ */ jsx13("strong", { children: "Subject:" }),
2437
- " ",
2438
- broadcast.subject,
2439
- /* @__PURE__ */ jsx13("br", {}),
2440
- /* @__PURE__ */ jsx13("strong", { children: "Channel:" }),
2441
- " ",
2442
- broadcast.channel?.name || "Unknown",
2443
- /* @__PURE__ */ jsx13("br", {}),
2444
- /* @__PURE__ */ jsx13("strong", { children: "Provider:" }),
2445
- " ",
2446
- broadcast.channel?.providerType || "Unknown",
2447
- /* @__PURE__ */ jsx13("br", {}),
2448
- /* @__PURE__ */ jsx13("strong", { children: "When:" }),
2449
- " ",
2450
- sendMode === "now" ? "Immediately" : `${scheduledDate} at ${scheduledTime}`,
2451
- /* @__PURE__ */ jsx13("br", {}),
2452
- selectedAudiences.length > 0 && /* @__PURE__ */ jsxs11(Fragment3, { children: [
2453
- /* @__PURE__ */ jsx13("strong", { children: "Audiences:" }),
2454
- " ",
2455
- selectedAudiences.length,
2456
- " selected"
2457
- ] })
2458
- ] })
2459
- ] }),
2460
- error && /* @__PURE__ */ jsx13("div", { style: {
2461
- backgroundColor: "#FEE2E2",
2462
- border: "1px solid #FCA5A5",
2463
- color: "#DC2626",
2464
- padding: "12px",
2465
- borderRadius: "4px",
2466
- marginBottom: "24px"
2467
- }, children: error }),
2468
- /* @__PURE__ */ jsxs11("div", { style: { display: "flex", justifyContent: "flex-end", gap: "12px" }, children: [
2469
- /* @__PURE__ */ jsx13(
2470
- "button",
2471
- {
2472
- type: "button",
2473
- onClick: onClose,
2474
- disabled: loading,
2475
- style: {
2476
- padding: "8px 24px",
2477
- backgroundColor: "#E5E7EB",
2478
- color: "#1F2937",
2479
- border: "none",
2480
- borderRadius: "4px",
2481
- fontSize: "16px",
2482
- cursor: loading ? "not-allowed" : "pointer",
2483
- opacity: loading ? 0.6 : 1
2484
- },
2485
- children: "Cancel"
2486
- }
2487
- ),
2488
- /* @__PURE__ */ jsx13(
2489
- "button",
2490
- {
2491
- type: "submit",
2492
- disabled: loading,
2493
- style: {
2494
- padding: "8px 24px",
2495
- backgroundColor: "#2563EB",
2496
- color: "white",
2497
- border: "none",
2498
- borderRadius: "4px",
2499
- fontSize: "16px",
2500
- cursor: loading ? "not-allowed" : "pointer",
2501
- opacity: loading ? 0.6 : 1
2502
- },
2503
- children: loading ? "Processing..." : sendMode === "now" ? "Send Now" : "Schedule"
2504
- }
2505
- )
2506
- ] })
2507
- ] })
2508
- ] }) });
2509
- };
2510
-
2511
- // src/components/Broadcasts/ActionsCell.tsx
2512
- import { Fragment as Fragment4, jsx as jsx14, jsxs as jsxs12 } from "react/jsx-runtime";
2513
- var ActionsCell = ({ rowData }) => {
2514
- const [loading, setLoading] = useState11(false);
2515
- const [showSendModal, setShowSendModal] = useState11(false);
2516
- const broadcast = rowData;
2517
- const handleSend = () => {
2518
- if (!broadcast.providerId) {
2519
- alert("This broadcast has not been synced with the provider yet");
2520
- return;
2521
- }
2522
- setShowSendModal(true);
2523
- };
2524
- const handleSchedule = () => {
2525
- if (!broadcast.providerId) {
2526
- alert("This broadcast has not been synced with the provider yet");
2527
- return;
2528
- }
2529
- setShowSendModal(true);
2530
- };
2531
- const handleDuplicate = async () => {
2532
- try {
2533
- setLoading(true);
2534
- const response = await fetch(`/api/broadcasts/${broadcast.id}`);
2535
- const data = await response.json();
2536
- delete data.id;
2537
- delete data.createdAt;
2538
- delete data.updatedAt;
2539
- delete data.providerId;
2540
- delete data.sentAt;
2541
- delete data.scheduledAt;
2542
- delete data.analytics;
2543
- data.name = `${data.name} (Copy)`;
2544
- data.status = "draft" /* DRAFT */;
2545
- const createResponse = await fetch("/api/broadcasts", {
2546
- method: "POST",
2547
- headers: {
2548
- "Content-Type": "application/json"
2549
- },
2550
- body: JSON.stringify(data)
2551
- });
2552
- if (!createResponse.ok) {
2553
- throw new Error("Failed to duplicate broadcast");
2554
- }
2555
- alert("Broadcast duplicated successfully");
2556
- window.location.reload();
2557
- } catch (error) {
2558
- alert(error instanceof Error ? error.message : "Failed to duplicate broadcast");
2559
- } finally {
2560
- setLoading(false);
2561
- }
2562
- };
2563
- const canSend = broadcast.status === "draft" /* DRAFT */;
2564
- const canSchedule = broadcast.status === "draft" /* DRAFT */;
2565
- const canDuplicate = true;
2566
- return /* @__PURE__ */ jsxs12(Fragment4, { children: [
2567
- /* @__PURE__ */ jsxs12("div", { style: { display: "flex", gap: "8px", alignItems: "center" }, children: [
2568
- canSend && /* @__PURE__ */ jsx14(
2569
- "button",
2570
- {
2571
- onClick: handleSend,
2572
- disabled: loading,
2573
- style: {
2574
- padding: "4px 12px",
2575
- backgroundColor: "#2563EB",
2576
- color: "white",
2577
- border: "none",
2578
- borderRadius: "4px",
2579
- fontSize: "12px",
2580
- cursor: loading ? "not-allowed" : "pointer",
2581
- opacity: loading ? 0.6 : 1
2582
- },
2583
- children: "Send"
2584
- }
2585
- ),
2586
- canSchedule && /* @__PURE__ */ jsx14(
2587
- "button",
2588
- {
2589
- onClick: handleSchedule,
2590
- disabled: loading,
2591
- style: {
2592
- padding: "4px 12px",
2593
- backgroundColor: "#6366F1",
2594
- color: "white",
2595
- border: "none",
2596
- borderRadius: "4px",
2597
- fontSize: "12px",
2598
- cursor: loading ? "not-allowed" : "pointer",
2599
- opacity: loading ? 0.6 : 1
2600
- },
2601
- children: "Schedule"
2602
- }
2603
- ),
2604
- canDuplicate && /* @__PURE__ */ jsx14(
2605
- "button",
2606
- {
2607
- onClick: handleDuplicate,
2608
- disabled: loading,
2609
- style: {
2610
- padding: "4px 12px",
2611
- backgroundColor: "#6B7280",
2612
- color: "white",
2613
- border: "none",
2614
- borderRadius: "4px",
2615
- fontSize: "12px",
2616
- cursor: loading ? "not-allowed" : "pointer",
2617
- opacity: loading ? 0.6 : 1
2618
- },
2619
- children: "Duplicate"
2620
- }
2621
- )
2622
- ] }),
2623
- showSendModal && /* @__PURE__ */ jsx14(
2624
- SendBroadcastModal,
2625
- {
2626
- broadcast,
2627
- onClose: () => setShowSendModal(false),
2628
- onSuccess: () => {
2629
- setShowSendModal(false);
2630
- window.location.reload();
2631
- }
2632
- }
2633
- )
2634
- ] });
2635
- };
2636
-
2637
2201
  // src/components/Broadcasts/EmptyField.tsx
2638
2202
  var EmptyField = () => {
2639
2203
  return null;
2640
2204
  };
2641
2205
  export {
2642
- ActionsCell,
2643
2206
  BroadcastEditor,
2644
2207
  BroadcastInlinePreview,
2645
2208
  BroadcastPreviewField,