@consilioweb/payload-support 0.6.0 → 0.6.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.
Files changed (84) hide show
  1. package/dist/{styles/theme.css → components/TicketConversation.css} +13 -326
  2. package/dist/components/TicketConversation.js +3004 -0
  3. package/dist/index.cjs +11 -11
  4. package/dist/index.js +11 -11
  5. package/dist/views.cjs +6184 -0
  6. package/dist/{views/TicketingSettingsView/TicketingSettings.module.scss → views.css} +66 -138
  7. package/dist/views.d.cts +30 -0
  8. package/dist/views.d.ts +30 -0
  9. package/dist/views.js +6165 -0
  10. package/package.json +14 -7
  11. package/src/plugin.ts +11 -11
  12. package/src/views.ts +17 -0
  13. package/dist/components/TicketConversation/components/AISummaryPanel.js +0 -76
  14. package/dist/components/TicketConversation/components/ActionPanels.js +0 -118
  15. package/dist/components/TicketConversation/components/ActivityLog.js +0 -23
  16. package/dist/components/TicketConversation/components/ClientBar.js +0 -42
  17. package/dist/components/TicketConversation/components/ClientHistory.js +0 -137
  18. package/dist/components/TicketConversation/components/CodeBlock.js +0 -152
  19. package/dist/components/TicketConversation/components/CodeBlockInserter.js +0 -155
  20. package/dist/components/TicketConversation/components/QuickActions.js +0 -65
  21. package/dist/components/TicketConversation/components/TicketHeader.js +0 -92
  22. package/dist/components/TicketConversation/components/TimeTrackingPanel.js +0 -133
  23. package/dist/components/TicketConversation/config.js +0 -41
  24. package/dist/components/TicketConversation/constants.js +0 -96
  25. package/dist/components/TicketConversation/context.js +0 -11
  26. package/dist/components/TicketConversation/hooks/useAI.js +0 -176
  27. package/dist/components/TicketConversation/hooks/useMessageActions.js +0 -135
  28. package/dist/components/TicketConversation/hooks/useReply.js +0 -187
  29. package/dist/components/TicketConversation/hooks/useTicketActions.js +0 -230
  30. package/dist/components/TicketConversation/hooks/useTimeTracking.js +0 -122
  31. package/dist/components/TicketConversation/hooks/useTranslation.js +0 -70
  32. package/dist/components/TicketConversation/index.js +0 -1123
  33. package/dist/components/TicketConversation/locales/en.json +0 -878
  34. package/dist/components/TicketConversation/locales/fr.json +0 -878
  35. package/dist/components/TicketConversation/types.js +0 -2
  36. package/dist/components/TicketConversation/utils.js +0 -25
  37. package/dist/styles/BillingView.module.scss +0 -311
  38. package/dist/styles/ChatView.module.scss +0 -438
  39. package/dist/styles/CommandPalette.module.scss +0 -160
  40. package/dist/styles/CrmView.module.scss +0 -554
  41. package/dist/styles/EmailTracking.module.scss +0 -238
  42. package/dist/styles/ImportConversation.module.scss +0 -267
  43. package/dist/styles/Layout.module.scss +0 -55
  44. package/dist/styles/Logs.module.scss +0 -164
  45. package/dist/styles/NewTicket.module.scss +0 -143
  46. package/dist/styles/PendingEmails.module.scss +0 -629
  47. package/dist/styles/SupportDashboard.module.scss +0 -649
  48. package/dist/styles/TicketDetail.module.scss +0 -1050
  49. package/dist/styles/TicketInbox.module.scss +0 -296
  50. package/dist/styles/TicketingSettings.module.scss +0 -358
  51. package/dist/styles/TimeDashboard.module.scss +0 -287
  52. package/dist/styles/_tokens.scss +0 -78
  53. package/dist/views/BillingView/client.js +0 -204
  54. package/dist/views/BillingView/index.js +0 -29
  55. package/dist/views/ChatView/client.js +0 -252
  56. package/dist/views/ChatView/index.js +0 -29
  57. package/dist/views/CrmView/client.js +0 -232
  58. package/dist/views/CrmView/index.js +0 -29
  59. package/dist/views/EmailTrackingView/client.js +0 -154
  60. package/dist/views/EmailTrackingView/index.js +0 -29
  61. package/dist/views/ImportConversationView/client.js +0 -204
  62. package/dist/views/ImportConversationView/index.js +0 -29
  63. package/dist/views/LogsView/client.js +0 -148
  64. package/dist/views/LogsView/index.js +0 -27
  65. package/dist/views/NewTicketView/client.js +0 -224
  66. package/dist/views/NewTicketView/index.js +0 -27
  67. package/dist/views/PendingEmailsView/client.js +0 -172
  68. package/dist/views/PendingEmailsView/index.js +0 -29
  69. package/dist/views/SupportDashboardView/client.js +0 -296
  70. package/dist/views/SupportDashboardView/index.js +0 -29
  71. package/dist/views/TicketDetailView/client.js +0 -844
  72. package/dist/views/TicketDetailView/index.js +0 -29
  73. package/dist/views/TicketInboxView/client.js +0 -294
  74. package/dist/views/TicketInboxView/index.js +0 -27
  75. package/dist/views/TicketingSettingsView/client.js +0 -728
  76. package/dist/views/TicketingSettingsView/index.js +0 -29
  77. package/dist/views/TimeDashboardView/client.js +0 -164
  78. package/dist/views/TimeDashboardView/index.js +0 -29
  79. package/dist/views/shared/AdminViewHeader.js +0 -67
  80. package/dist/views/shared/ErrorBoundary.js +0 -50
  81. package/dist/views/shared/Skeleton.js +0 -72
  82. package/dist/views/shared/adminTokens.js +0 -32
  83. package/dist/views/shared/config.js +0 -41
  84. package/dist/views/shared/index.js +0 -6
@@ -1,296 +0,0 @@
1
- "use client";
2
- import { jsxs, jsx } from 'react/jsx-runtime';
3
- import { useState, useCallback, useEffect, useMemo } from 'react';
4
- import Link from 'next/link';
5
- import { useTranslation } from '../../components/TicketConversation/hooks/useTranslation';
6
-
7
- function formatResponseTime(hours) {
8
- if (hours == null) return "--";
9
- const h = Math.floor(hours);
10
- const m = Math.round((hours - h) * 60);
11
- if (h === 0) return `${m}m`;
12
- if (m === 0) return `${h}h`;
13
- return `${h}h${m.toString().padStart(2, "0")}m`;
14
- }
15
- function timeAgo(dateStr) {
16
- const diff = Date.now() - new Date(dateStr).getTime();
17
- const mins = Math.floor(diff / 6e4);
18
- if (mins < 1) return "a l'instant";
19
- if (mins < 60) return `${mins}min`;
20
- const hours = Math.floor(mins / 60);
21
- if (hours < 24) return `${hours}h`;
22
- const days = Math.floor(hours / 24);
23
- if (days < 7) return `${days}j`;
24
- return `${Math.floor(days / 7)}sem`;
25
- }
26
- function computeTrend(current, previous) {
27
- if (previous === 0 && current === 0) return { pct: 0, dir: "neutral" };
28
- if (previous === 0) return { pct: 100, dir: "up" };
29
- const pct = Math.round((current - previous) / previous * 100);
30
- if (pct === 0) return { pct: 0, dir: "neutral" };
31
- return { pct: Math.abs(pct), dir: pct > 0 ? "up" : "down" };
32
- }
33
- function StatCard({ label, value, trend, accentColor }) {
34
- return /* @__PURE__ */ jsxs("div", { style: { padding: "16px 20px", borderRadius: 10, border: "1px solid var(--theme-elevation-150)", background: "var(--theme-elevation-0)", borderLeft: `3px solid ${accentColor || "#2563eb"}` }, children: [
35
- /* @__PURE__ */ jsx("div", { style: { fontSize: 12, color: "var(--theme-elevation-500)", marginBottom: 4 }, children: label }),
36
- /* @__PURE__ */ jsx("div", { style: { fontSize: 24, fontWeight: 700, color: "var(--theme-text)" }, children: value }),
37
- trend && trend.dir !== "neutral" && /* @__PURE__ */ jsxs("div", { style: { fontSize: 11, color: trend.dir === "up" ? "#dc2626" : "#16a34a", marginTop: 4 }, children: [
38
- trend.dir === "up" ? "\u2191" : "\u2193",
39
- " ",
40
- trend.pct,
41
- "%"
42
- ] }),
43
- trend && trend.dir === "neutral" && /* @__PURE__ */ jsx("div", { style: { fontSize: 11, color: "#6b7280", marginTop: 4 }, children: "-- stable" })
44
- ] });
45
- }
46
- function formatSlaTime(minutes) {
47
- const absMin = Math.abs(minutes);
48
- if (absMin < 60) return `${Math.round(absMin)}min`;
49
- const h = Math.floor(absMin / 60);
50
- const m = Math.round(absMin % 60);
51
- if (h < 24) return m > 0 ? `${h}h${m.toString().padStart(2, "0")}` : `${h}h`;
52
- const d = Math.floor(h / 24);
53
- const remainH = h % 24;
54
- return remainH > 0 ? `${d}j ${remainH}h` : `${d}j`;
55
- }
56
- function SlaSection() {
57
- const { t } = useTranslation();
58
- const [sla, setSla] = useState(null);
59
- const [slaLoading, setSlaLoading] = useState(true);
60
- useEffect(() => {
61
- const fetchSla = async () => {
62
- try {
63
- const res = await fetch("/api/support/sla-check");
64
- if (res.ok) setSla(await res.json());
65
- } catch {
66
- }
67
- setSlaLoading(false);
68
- };
69
- fetchSla();
70
- const interval = setInterval(fetchSla, 6e4);
71
- return () => clearInterval(interval);
72
- }, []);
73
- if (slaLoading) return /* @__PURE__ */ jsx("div", { style: { padding: 16, color: "#94a3b8", fontSize: 13 }, children: t("sla.loading") });
74
- if (!sla) return null;
75
- return /* @__PURE__ */ jsxs("div", { style: { marginTop: 24 }, children: [
76
- /* @__PURE__ */ jsx("h2", { style: { fontSize: 16, fontWeight: 700, marginBottom: 12, color: "var(--theme-text)" }, children: t("sla.title") }),
77
- /* @__PURE__ */ jsxs("div", { style: { display: "grid", gridTemplateColumns: "1fr 1fr", gap: 16 }, children: [
78
- /* @__PURE__ */ jsxs("div", { style: { padding: 16, borderRadius: 10, border: "1px solid #fecaca", background: "#fef2f2" }, children: [
79
- /* @__PURE__ */ jsxs("div", { style: { display: "flex", justifyContent: "space-between", marginBottom: 8 }, children: [
80
- /* @__PURE__ */ jsx("h3", { style: { fontSize: 14, fontWeight: 700, color: "#dc2626", margin: 0 }, children: t("sla.breached") }),
81
- /* @__PURE__ */ jsx("span", { style: { padding: "2px 8px", borderRadius: 10, background: "#fecaca", color: "#dc2626", fontSize: 12, fontWeight: 700 }, children: sla.breached.length })
82
- ] }),
83
- sla.breached.length === 0 ? /* @__PURE__ */ jsx("div", { style: { fontSize: 13, color: "#6b7280" }, children: t("sla.noBreached") }) : /* @__PURE__ */ jsx("ul", { style: { listStyle: "none", margin: 0, padding: 0 }, children: sla.breached.map((ticket) => {
84
- const overdueMin = Math.round((Date.now() - new Date(ticket.createdAt).getTime()) / 6e4);
85
- return /* @__PURE__ */ jsxs("li", { style: { padding: "6px 0", borderBottom: "1px solid #fecaca", cursor: "pointer", display: "flex", justifyContent: "space-between", alignItems: "center", fontSize: 13 }, onClick: () => {
86
- window.location.href = `/admin/support/ticket?id=${ticket.id}`;
87
- }, children: [
88
- /* @__PURE__ */ jsxs("div", { children: [
89
- /* @__PURE__ */ jsxs("span", { style: { fontWeight: 600 }, children: [
90
- "#",
91
- ticket.ticketNumber
92
- ] }),
93
- " ",
94
- /* @__PURE__ */ jsx("span", { style: { color: "#6b7280" }, children: ticket.subject })
95
- ] }),
96
- /* @__PURE__ */ jsxs("span", { style: { color: "#dc2626", fontWeight: 600, fontSize: 12 }, children: [
97
- "+",
98
- formatSlaTime(overdueMin)
99
- ] })
100
- ] }, ticket.id);
101
- }) })
102
- ] }),
103
- /* @__PURE__ */ jsxs("div", { style: { padding: 16, borderRadius: 10, border: "1px solid #fde68a", background: "#fefce8" }, children: [
104
- /* @__PURE__ */ jsxs("div", { style: { display: "flex", justifyContent: "space-between", marginBottom: 8 }, children: [
105
- /* @__PURE__ */ jsx("h3", { style: { fontSize: 14, fontWeight: 700, color: "#d97706", margin: 0 }, children: t("sla.atRisk") }),
106
- /* @__PURE__ */ jsx("span", { style: { padding: "2px 8px", borderRadius: 10, background: "#fde68a", color: "#d97706", fontSize: 12, fontWeight: 700 }, children: sla.atRisk.length })
107
- ] }),
108
- sla.atRisk.length === 0 ? /* @__PURE__ */ jsx("div", { style: { fontSize: 13, color: "#6b7280" }, children: t("sla.noAtRisk") }) : /* @__PURE__ */ jsx("ul", { style: { listStyle: "none", margin: 0, padding: 0 }, children: sla.atRisk.map((ticket) => {
109
- const elapsedMin = Math.round((Date.now() - new Date(ticket.createdAt).getTime()) / 6e4);
110
- const estimatedTotalMin = Math.round(elapsedMin / 0.8);
111
- const remainingMin = Math.max(estimatedTotalMin - elapsedMin, 0);
112
- return /* @__PURE__ */ jsxs("li", { style: { padding: "6px 0", borderBottom: "1px solid #fde68a", cursor: "pointer", display: "flex", justifyContent: "space-between", alignItems: "center", fontSize: 13 }, onClick: () => {
113
- window.location.href = `/admin/support/ticket?id=${ticket.id}`;
114
- }, children: [
115
- /* @__PURE__ */ jsxs("div", { children: [
116
- /* @__PURE__ */ jsxs("span", { style: { fontWeight: 600 }, children: [
117
- "#",
118
- ticket.ticketNumber
119
- ] }),
120
- " ",
121
- /* @__PURE__ */ jsx("span", { style: { color: "#6b7280" }, children: ticket.subject })
122
- ] }),
123
- /* @__PURE__ */ jsx("span", { style: { color: "#d97706", fontWeight: 600, fontSize: 12 }, children: t("sla.remaining", { time: formatSlaTime(remainingMin) }) })
124
- ] }, ticket.id);
125
- }) })
126
- ] })
127
- ] })
128
- ] });
129
- }
130
- const SupportDashboardClient = () => {
131
- const { t } = useTranslation();
132
- const [stats, setStats] = useState(null);
133
- const [tickets, setTickets] = useState([]);
134
- const [loading, setLoading] = useState(true);
135
- const [sessionExpired, setSessionExpired] = useState(false);
136
- const fetchData = useCallback(async () => {
137
- try {
138
- const [statsRes, ticketsRes] = await Promise.all([
139
- fetch("/api/support/admin-stats"),
140
- fetch("/api/tickets?where[status][not_equals]=resolved&sort=-updatedAt&limit=8&depth=1")
141
- ]);
142
- if (statsRes.ok) {
143
- setStats(await statsRes.json());
144
- } else if (statsRes.status === 401 || statsRes.status === 403) {
145
- setSessionExpired(true);
146
- return;
147
- }
148
- if (ticketsRes.ok) {
149
- const data = await ticketsRes.json();
150
- setTickets(data.docs || []);
151
- }
152
- } catch {
153
- }
154
- setLoading(false);
155
- }, []);
156
- useEffect(() => {
157
- fetchData();
158
- if (sessionExpired) return;
159
- const interval = setInterval(fetchData, 3e4);
160
- return () => clearInterval(interval);
161
- }, [fetchData, sessionExpired]);
162
- useEffect(() => {
163
- if (sessionExpired) return;
164
- const onFocus = () => fetchData();
165
- window.addEventListener("focus", onFocus);
166
- return () => window.removeEventListener("focus", onFocus);
167
- }, [fetchData, sessionExpired]);
168
- const volumeData = useMemo(() => {
169
- if (!stats) return [];
170
- const avg = stats.createdLast7Days;
171
- const days = [t("dashboard.weekDays.mon"), t("dashboard.weekDays.tue"), t("dashboard.weekDays.wed"), t("dashboard.weekDays.thu"), t("dashboard.weekDays.fri"), t("dashboard.weekDays.sat"), t("dashboard.weekDays.sun")];
172
- const base = Math.max(Math.floor(avg / 7), 0);
173
- return days.map((label, i) => ({
174
- label,
175
- value: Math.max(base + (i * 3 + 1) % 5 - 2, 0)
176
- }));
177
- }, [stats, t]);
178
- if (loading) {
179
- return /* @__PURE__ */ jsxs("div", { style: { padding: "20px 30px", maxWidth: 1100, margin: "0 auto" }, children: [
180
- /* @__PURE__ */ jsx("h1", { style: { fontSize: 24, fontWeight: 700 }, children: t("dashboard.title") }),
181
- /* @__PURE__ */ jsx("p", { style: { color: "#94a3b8" }, children: t("dashboard.loadingMetrics") }),
182
- /* @__PURE__ */ jsx("div", { style: { display: "grid", gridTemplateColumns: "repeat(4, 1fr)", gap: 16, marginTop: 20 }, children: [0, 1, 2, 3].map((i) => /* @__PURE__ */ jsx("div", { style: { height: 80, borderRadius: 10, background: "#f1f5f9" } }, i)) })
183
- ] });
184
- }
185
- if (!stats) {
186
- return /* @__PURE__ */ jsx("div", { style: { padding: "20px 30px", maxWidth: 1100, margin: "0 auto" }, children: /* @__PURE__ */ jsxs("div", { style: { padding: 40, textAlign: "center", color: "#dc2626" }, children: [
187
- /* @__PURE__ */ jsx("strong", { children: t("dashboard.loadError") }),
188
- /* @__PURE__ */ jsx("p", { children: sessionExpired ? t("common.sessionExpired") : t("dashboard.cannotLoadStats") })
189
- ] }) });
190
- }
191
- const openCount = stats.byStatus.open || 0;
192
- const waitingCount = stats.byStatus.waiting_client || 0;
193
- const trendOpen = computeTrend(stats.createdLast7Days, Math.round(stats.createdLast30Days / 4));
194
- const waitingTrend = waitingCount === 0 ? { pct: 0, dir: "neutral" } : waitingCount > openCount * 0.5 ? { pct: Math.round(waitingCount / Math.max(openCount, 1) * 100), dir: "up" } : { pct: Math.round(100 - waitingCount / Math.max(openCount, 1) * 100), dir: "down" };
195
- const getClientName = (ticket) => {
196
- if (!ticket.client) return "--";
197
- if (typeof ticket.client === "string") return ticket.client;
198
- return ticket.client.company || ticket.client.firstName || "--";
199
- };
200
- const statusDotColor = (status) => {
201
- switch (status) {
202
- case "open":
203
- return "#22c55e";
204
- case "waiting_client":
205
- return "#eab308";
206
- case "resolved":
207
- return "#94a3b8";
208
- default:
209
- return "#94a3b8";
210
- }
211
- };
212
- const maxVolume = Math.max(...volumeData.map((d) => d.value), 1);
213
- const csatScore = stats.satisfactionAvg;
214
- const csatPct = csatScore > 0 ? csatScore / 5 * 100 : 0;
215
- const csatRadius = 42;
216
- const csatCircumference = 2 * Math.PI * csatRadius;
217
- const csatStrokeDashoffset = csatCircumference - csatPct / 100 * csatCircumference;
218
- const csatColor = csatScore >= 4 ? "#22c55e" : csatScore >= 3 ? "#f59e0b" : csatScore > 0 ? "#ef4444" : "#94a3b8";
219
- return /* @__PURE__ */ jsxs("div", { style: { padding: "20px 30px", maxWidth: 1100, margin: "0 auto" }, children: [
220
- /* @__PURE__ */ jsxs("div", { style: { marginBottom: 20 }, children: [
221
- /* @__PURE__ */ jsx("h1", { style: { fontSize: 24, fontWeight: 700, margin: 0, color: "var(--theme-text)" }, children: t("dashboard.title") }),
222
- /* @__PURE__ */ jsx("p", { style: { color: "var(--theme-elevation-500)", margin: "4px 0 0", fontSize: 14 }, children: t("dashboard.subtitle") })
223
- ] }),
224
- /* @__PURE__ */ jsxs("div", { style: { display: "grid", gridTemplateColumns: "repeat(4, 1fr)", gap: 16, marginBottom: 24 }, children: [
225
- /* @__PURE__ */ jsx(StatCard, { label: t("dashboard.openTickets"), value: String(openCount), trend: trendOpen, accentColor: "#3b82f6" }),
226
- /* @__PURE__ */ jsx(StatCard, { label: t("dashboard.waitingClient"), value: String(waitingCount), trend: waitingTrend, accentColor: "#f59e0b" }),
227
- /* @__PURE__ */ jsx(StatCard, { label: t("dashboard.responseTime"), value: formatResponseTime(stats.avgResponseTimeHours), accentColor: stats.avgResponseTimeHours != null && stats.avgResponseTimeHours > 24 ? "#ef4444" : "#22c55e" }),
228
- /* @__PURE__ */ jsx(StatCard, { label: t("dashboard.satisfaction"), value: stats.satisfactionAvg > 0 ? `${stats.satisfactionAvg}/5` : "--", accentColor: stats.satisfactionAvg >= 4 ? "#22c55e" : stats.satisfactionAvg >= 3 ? "#f59e0b" : "#94a3b8" })
229
- ] }),
230
- /* @__PURE__ */ jsxs("div", { style: { display: "grid", gridTemplateColumns: "1fr 320px", gap: 20, marginBottom: 24 }, children: [
231
- /* @__PURE__ */ jsxs("div", { style: { padding: 16, borderRadius: 10, border: "1px solid var(--theme-elevation-150)" }, children: [
232
- /* @__PURE__ */ jsx("h2", { style: { fontSize: 15, fontWeight: 700, margin: "0 0 12px", color: "var(--theme-text)" }, children: t("dashboard.activeTickets") }),
233
- tickets.length === 0 ? /* @__PURE__ */ jsx("div", { style: { padding: 20, textAlign: "center", color: "#94a3b8" }, children: t("dashboard.noActiveTickets") }) : /* @__PURE__ */ jsxs("table", { style: { width: "100%", borderCollapse: "collapse", fontSize: 13 }, children: [
234
- /* @__PURE__ */ jsx("thead", { children: /* @__PURE__ */ jsxs("tr", { children: [
235
- /* @__PURE__ */ jsx("th", { style: { textAlign: "left", padding: "6px 8px", borderBottom: "1px solid var(--theme-elevation-200)", fontSize: 11, color: "var(--theme-elevation-500)" }, children: t("dashboard.tableHeaders.status") }),
236
- /* @__PURE__ */ jsx("th", { style: { textAlign: "left", padding: "6px 8px", borderBottom: "1px solid var(--theme-elevation-200)", fontSize: 11, color: "var(--theme-elevation-500)" }, children: t("dashboard.tableHeaders.number") }),
237
- /* @__PURE__ */ jsx("th", { style: { textAlign: "left", padding: "6px 8px", borderBottom: "1px solid var(--theme-elevation-200)", fontSize: 11, color: "var(--theme-elevation-500)" }, children: t("dashboard.tableHeaders.subject") }),
238
- /* @__PURE__ */ jsx("th", { style: { textAlign: "left", padding: "6px 8px", borderBottom: "1px solid var(--theme-elevation-200)", fontSize: 11, color: "var(--theme-elevation-500)" }, children: t("dashboard.tableHeaders.client") }),
239
- /* @__PURE__ */ jsx("th", { style: { textAlign: "left", padding: "6px 8px", borderBottom: "1px solid var(--theme-elevation-200)", fontSize: 11, color: "var(--theme-elevation-500)" }, children: t("dashboard.tableHeaders.modified") })
240
- ] }) }),
241
- /* @__PURE__ */ jsx("tbody", { children: tickets.map((tk) => /* @__PURE__ */ jsxs("tr", { style: { cursor: "pointer" }, onClick: () => {
242
- window.location.href = `/admin/support/ticket?id=${tk.id}`;
243
- }, children: [
244
- /* @__PURE__ */ jsx("td", { style: { padding: "8px" }, children: /* @__PURE__ */ jsx("span", { style: { width: 8, height: 8, borderRadius: "50%", display: "inline-block", backgroundColor: statusDotColor(tk.status) } }) }),
245
- /* @__PURE__ */ jsxs("td", { style: { padding: "8px", fontWeight: 600, fontSize: 12 }, children: [
246
- "#",
247
- tk.ticketNumber
248
- ] }),
249
- /* @__PURE__ */ jsx("td", { style: { padding: "8px", maxWidth: 250, overflow: "hidden", textOverflow: "ellipsis", whiteSpace: "nowrap" }, children: tk.subject }),
250
- /* @__PURE__ */ jsx("td", { style: { padding: "8px", color: "var(--theme-elevation-500)", fontSize: 12 }, children: getClientName(tk) }),
251
- /* @__PURE__ */ jsx("td", { style: { padding: "8px", color: "var(--theme-elevation-400)", fontSize: 12 }, children: timeAgo(tk.updatedAt) })
252
- ] }, tk.id)) })
253
- ] })
254
- ] }),
255
- /* @__PURE__ */ jsxs("div", { style: { display: "flex", flexDirection: "column", gap: 16 }, children: [
256
- /* @__PURE__ */ jsxs("div", { style: { padding: 16, borderRadius: 10, border: "1px solid var(--theme-elevation-150)" }, children: [
257
- /* @__PURE__ */ jsx("h2", { style: { fontSize: 15, fontWeight: 700, margin: "0 0 12px", color: "var(--theme-text)" }, children: t("dashboard.volume7days") }),
258
- /* @__PURE__ */ jsx("div", { style: { display: "flex", alignItems: "flex-end", gap: 4, height: 80 }, children: volumeData.map((d, i) => /* @__PURE__ */ jsx("div", { style: { flex: 1, background: "#3b82f6", borderRadius: "3px 3px 0 0", height: `${Math.max(d.value / maxVolume * 100, 5)}%` }, title: `${d.label}: ${d.value}` }, i)) }),
259
- /* @__PURE__ */ jsxs("div", { style: { display: "flex", justifyContent: "space-between", fontSize: 10, color: "var(--theme-elevation-400)", marginTop: 4 }, children: [
260
- /* @__PURE__ */ jsx("span", { children: volumeData[0]?.label }),
261
- /* @__PURE__ */ jsx("span", { children: volumeData[volumeData.length - 1]?.label })
262
- ] })
263
- ] }),
264
- /* @__PURE__ */ jsxs("div", { style: { padding: 16, borderRadius: 10, border: "1px solid var(--theme-elevation-150)" }, children: [
265
- /* @__PURE__ */ jsx("h2", { style: { fontSize: 15, fontWeight: 700, margin: "0 0 12px", color: "var(--theme-text)" }, children: t("dashboard.csat") }),
266
- /* @__PURE__ */ jsxs("div", { style: { display: "flex", alignItems: "center", gap: 16 }, children: [
267
- /* @__PURE__ */ jsxs("div", { style: { position: "relative", width: 80, height: 80 }, children: [
268
- /* @__PURE__ */ jsxs("svg", { width: "80", height: "80", viewBox: "0 0 100 100", children: [
269
- /* @__PURE__ */ jsx("circle", { cx: "50", cy: "50", r: csatRadius, fill: "none", stroke: "var(--theme-elevation-150, #e2e8f0)", strokeWidth: "6" }),
270
- /* @__PURE__ */ jsx("circle", { cx: "50", cy: "50", r: csatRadius, fill: "none", stroke: csatColor, strokeWidth: "6", strokeLinecap: "round", strokeDasharray: csatCircumference, strokeDashoffset: csatStrokeDashoffset, transform: "rotate(-90 50 50)", style: { transition: "stroke-dashoffset 600ms ease" } })
271
- ] }),
272
- /* @__PURE__ */ jsx("div", { style: { position: "absolute", inset: 0, display: "flex", alignItems: "center", justifyContent: "center", fontWeight: 700, fontSize: 16 }, children: csatScore > 0 ? csatScore.toFixed(1) : "--" })
273
- ] }),
274
- /* @__PURE__ */ jsxs("div", { children: [
275
- /* @__PURE__ */ jsx("div", { style: { fontSize: 13, fontWeight: 600 }, children: csatScore > 0 ? `${csatScore.toFixed(1)} / 5` : t("dashboard.csatNoData") }),
276
- /* @__PURE__ */ jsx("div", { style: { fontSize: 12, color: "var(--theme-elevation-500)" }, children: stats.satisfactionCount > 0 ? t("dashboard.csatReviews", { count: String(stats.satisfactionCount) }) : t("dashboard.csatNoReviews") })
277
- ] })
278
- ] })
279
- ] })
280
- ] })
281
- ] }),
282
- /* @__PURE__ */ jsx(SlaSection, {}),
283
- /* @__PURE__ */ jsxs("div", { style: { display: "flex", gap: 10, marginTop: 24, flexWrap: "wrap" }, children: [
284
- /* @__PURE__ */ jsx(Link, { href: "/admin/support/new-ticket", style: { padding: "8px 16px", borderRadius: 8, background: "#2563eb", color: "#fff", fontSize: 13, fontWeight: 600, textDecoration: "none" }, children: t("dashboard.newTicketAction") }),
285
- /* @__PURE__ */ jsxs(Link, { href: "/admin/support/emails", style: { padding: "8px 16px", borderRadius: 8, border: "1px solid var(--theme-elevation-200)", fontSize: 13, fontWeight: 500, textDecoration: "none", color: "var(--theme-text)", display: "flex", alignItems: "center", gap: 6 }, children: [
286
- t("dashboard.pendingEmails"),
287
- stats.pendingEmailsCount > 0 ? /* @__PURE__ */ jsx("span", { style: { padding: "1px 6px", borderRadius: 10, background: "#fef2f2", color: "#dc2626", fontSize: 11, fontWeight: 700 }, children: stats.pendingEmailsCount }) : /* @__PURE__ */ jsx("span", { style: { padding: "1px 6px", borderRadius: 10, background: "#dcfce7", color: "#16a34a", fontSize: 11, fontWeight: 700 }, children: "0" })
288
- ] }),
289
- /* @__PURE__ */ jsx(Link, { href: "/admin/support/crm", style: { padding: "8px 16px", borderRadius: 8, border: "1px solid var(--theme-elevation-200)", fontSize: 13, fontWeight: 500, textDecoration: "none", color: "var(--theme-text)" }, children: t("dashboard.crm") }),
290
- /* @__PURE__ */ jsx(Link, { href: "/admin/support/billing", style: { padding: "8px 16px", borderRadius: 8, border: "1px solid var(--theme-elevation-200)", fontSize: 13, fontWeight: 500, textDecoration: "none", color: "var(--theme-text)" }, children: t("dashboard.preBilling") }),
291
- /* @__PURE__ */ jsx("a", { href: "/api/support/export-csv", style: { padding: "8px 16px", borderRadius: 8, border: "1px solid var(--theme-elevation-200)", fontSize: 13, fontWeight: 500, textDecoration: "none", color: "var(--theme-text)" }, target: "_blank", rel: "noopener noreferrer", children: t("dashboard.exportCsv") })
292
- ] })
293
- ] });
294
- };
295
-
296
- export { SupportDashboardClient };
@@ -1,29 +0,0 @@
1
- import { jsx } from 'react/jsx-runtime';
2
- import { DefaultTemplate } from '@payloadcms/next/templates';
3
- import { redirect } from 'next/navigation';
4
- import { AdminErrorBoundary } from '../shared/ErrorBoundary';
5
- import { SupportDashboardClient } from './client';
6
-
7
- const SupportDashboardView = ({ initPageResult }) => {
8
- const { req, visibleEntities } = initPageResult;
9
- if (!req.user) {
10
- redirect("/admin/login");
11
- }
12
- return /* @__PURE__ */ jsx(
13
- DefaultTemplate,
14
- {
15
- i18n: req.i18n,
16
- locale: initPageResult.locale,
17
- params: {},
18
- payload: req.payload,
19
- permissions: initPageResult.permissions,
20
- searchParams: {},
21
- user: req.user,
22
- visibleEntities,
23
- children: /* @__PURE__ */ jsx(AdminErrorBoundary, { viewName: "SupportDashboardView", children: /* @__PURE__ */ jsx(SupportDashboardClient, {}) })
24
- }
25
- );
26
- };
27
- var SupportDashboardView_default = SupportDashboardView;
28
-
29
- export { SupportDashboardView, SupportDashboardView_default as default };