create-crm-tmp 2.0.0 → 2.1.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/bin/create-crm-tmp.js +56 -35
- package/package.json +1 -1
- package/template/README.md +230 -115
- package/template/eslint.config.mjs +13 -0
- package/template/next.config.ts +14 -0
- package/template/package.json +15 -2
- package/template/prisma/migrations/20260318095700_init_db/migration.sql +978 -0
- package/template/prisma/migrations/migration_lock.toml +3 -0
- package/template/prisma/schema.prisma +132 -637
- package/template/src/app/(auth)/invite/[token]/page.tsx +10 -8
- package/template/src/app/(auth)/layout.tsx +1 -1
- package/template/src/app/(auth)/reset-password/complete/page.tsx +11 -8
- package/template/src/app/(auth)/reset-password/page.tsx +4 -4
- package/template/src/app/(auth)/reset-password/verify/page.tsx +4 -4
- package/template/src/app/(auth)/signin/page.tsx +14 -6
- package/template/src/app/(dashboard)/agenda/page.tsx +2243 -988
- package/template/src/app/(dashboard)/automatisation/_components/workflow-editor.tsx +18 -104
- package/template/src/app/(dashboard)/automatisation/page.tsx +10 -26
- package/template/src/app/(dashboard)/closing/page.tsx +78 -62
- package/template/src/app/(dashboard)/contacts/[id]/page.tsx +2082 -1080
- package/template/src/app/(dashboard)/contacts/companies/[id]/page.tsx +46 -47
- package/template/src/app/(dashboard)/contacts/page.tsx +1062 -780
- package/template/src/app/(dashboard)/dashboard/page.tsx +533 -37
- package/template/src/app/(dashboard)/dev/page.tsx +1291 -0
- package/template/src/app/(dashboard)/layout.tsx +6 -2
- package/template/src/app/(dashboard)/settings/page.tsx +797 -2582
- package/template/src/app/(dashboard)/templates/page.tsx +55 -54
- package/template/src/app/(dashboard)/users/list/page.tsx +51 -48
- package/template/src/app/(dashboard)/users/page.tsx +1 -1
- package/template/src/app/(dashboard)/users/permissions/page.tsx +2 -2
- package/template/src/app/(dashboard)/users/roles/page.tsx +7 -5
- package/template/src/app/api/agenda/google-events/route.ts +92 -0
- package/template/src/app/api/auth/check-active/route.ts +3 -2
- package/template/src/app/api/auth/google/route.ts +2 -1
- package/template/src/app/api/auth/google/status/route.ts +7 -31
- package/template/src/app/api/companies/[id]/activities/route.ts +1 -3
- package/template/src/app/api/companies/[id]/route.ts +1 -2
- package/template/src/app/api/companies/route.ts +42 -12
- package/template/src/app/api/contacts/[id]/files/[fileId]/preview/route.ts +9 -31
- package/template/src/app/api/contacts/[id]/files/[fileId]/route.ts +14 -32
- package/template/src/app/api/contacts/[id]/files/route.ts +112 -212
- package/template/src/app/api/contacts/[id]/interactions/[interactionId]/route.ts +27 -1
- package/template/src/app/api/contacts/[id]/interactions/route.ts +16 -16
- package/template/src/app/api/contacts/[id]/kyc/route.ts +21 -11
- package/template/src/app/api/contacts/[id]/meet/route.ts +19 -2
- package/template/src/app/api/contacts/[id]/route.ts +106 -34
- package/template/src/app/api/contacts/[id]/send-email/route.ts +27 -11
- package/template/src/app/api/contacts/[id]/workflows/run/route.ts +6 -0
- package/template/src/app/api/contacts/export/route.ts +9 -13
- package/template/src/app/api/contacts/import/route.ts +55 -25
- package/template/src/app/api/contacts/import-preview/route.ts +1 -1
- package/template/src/app/api/contacts/origins/route.ts +63 -0
- package/template/src/app/api/contacts/route.ts +153 -41
- package/template/src/app/api/cron/cleanup-editor-images/route.ts +166 -0
- package/template/src/app/api/dashboard/widgets/[id]/route.ts +44 -0
- package/template/src/app/api/dashboard/widgets/route.ts +181 -0
- package/template/src/app/api/dev/reminders/test/route.ts +114 -0
- package/template/src/app/api/editor/upload-image/route.ts +61 -0
- package/template/src/app/api/integrations/google-sheet/jobs/[jobId]/route.ts +47 -0
- package/template/src/app/api/integrations/google-sheet/jobs/usage/route.ts +50 -0
- package/template/src/app/api/integrations/google-sheet/sync/route.ts +24 -556
- package/template/src/app/api/jobs/google-sheet/process/route.ts +84 -0
- package/template/src/app/api/jobs/google-sheet/schedule/route.ts +50 -0
- package/template/src/app/api/reminders/clear/route.ts +120 -0
- package/template/src/app/api/reminders/clear/undo/route.ts +112 -0
- package/template/src/app/api/reminders/route.ts +164 -39
- package/template/src/app/api/reminders/state/route.ts +164 -0
- package/template/src/app/api/reset-password/request/route.ts +1 -1
- package/template/src/app/api/reset-password/verify/route.ts +1 -1
- package/template/src/app/api/send/route.ts +16 -4
- package/template/src/app/api/settings/google-ads/route.ts +14 -0
- package/template/src/app/api/settings/google-calendar/calendars/route.ts +97 -0
- package/template/src/app/api/settings/google-calendar/route.ts +124 -0
- package/template/src/app/api/settings/google-sheet/[id]/route.ts +28 -0
- package/template/src/app/api/settings/google-sheet/auto-map/route.ts +37 -4
- package/template/src/app/api/settings/google-sheet/preview/route.ts +9 -3
- package/template/src/app/api/settings/google-sheet/route.ts +14 -0
- package/template/src/app/api/settings/integrations/logs/route.ts +93 -0
- package/template/src/app/api/settings/integrations/notifications/route.ts +67 -0
- package/template/src/app/api/settings/meta-leads/[id]/route.ts +0 -1
- package/template/src/app/api/settings/meta-leads/route.ts +14 -2
- package/template/src/app/api/settings/smtp/route.ts +53 -6
- package/template/src/app/api/tasks/[id]/attendees/route.ts +24 -8
- package/template/src/app/api/tasks/[id]/route.ts +234 -58
- package/template/src/app/api/tasks/meet/route.ts +27 -19
- package/template/src/app/api/tasks/route.ts +62 -17
- package/template/src/app/api/users/[id]/route.ts +20 -14
- package/template/src/app/api/users/list/route.ts +57 -19
- package/template/src/app/api/webhooks/google-ads/route.ts +34 -14
- package/template/src/app/api/webhooks/meta-leads/route.ts +32 -12
- package/template/src/app/api/workflows/[id]/route.ts +0 -4
- package/template/src/app/api/workflows/process/route.ts +22 -51
- package/template/src/app/api/workflows/route.ts +0 -4
- package/template/src/app/globals.css +342 -4
- package/template/src/app/layout.tsx +11 -3
- package/template/src/app/page.tsx +1 -1
- package/template/src/components/address-autocomplete.tsx +7 -6
- package/template/src/components/config-error-alert.tsx +46 -0
- package/template/src/components/contacts/filter-bar.tsx +12 -3
- package/template/src/components/contacts/filter-builder.tsx +28 -43
- package/template/src/components/contacts/save-view-dialog.tsx +1 -1
- package/template/src/components/contacts/views-tab-bar.tsx +15 -6
- package/template/src/components/dashboard/activity-chart.tsx +41 -28
- package/template/src/components/dashboard/add-widget-dialog.tsx +157 -0
- package/template/src/components/dashboard/color-picker.tsx +64 -0
- package/template/src/components/dashboard/contacts-chart.tsx +69 -0
- package/template/src/components/dashboard/interactions-by-type-chart.tsx +121 -0
- package/template/src/components/dashboard/recent-activity.tsx +154 -0
- package/template/src/components/dashboard/stat-card.tsx +40 -40
- package/template/src/components/dashboard/status-distribution-chart.tsx +81 -0
- package/template/src/components/dashboard/tasks-pie-chart.tsx +37 -34
- package/template/src/components/dashboard/top-contacts-list.tsx +113 -0
- package/template/src/components/dashboard/upcoming-tasks-list.tsx +72 -81
- package/template/src/components/dashboard/widget-wrapper.tsx +36 -0
- package/template/src/components/date-picker.tsx +9 -6
- package/template/src/components/editor/upload-editor-image.ts +42 -0
- package/template/src/components/editor.tsx +161 -22
- package/template/src/components/email-template.tsx +2 -2
- package/template/src/components/global-search.tsx +30 -28
- package/template/src/components/header.tsx +178 -80
- package/template/src/components/inactive-account-guard.tsx +58 -0
- package/template/src/components/integration-notifications-listener.tsx +12 -0
- package/template/src/components/invitation-email-template.tsx +2 -2
- package/template/src/components/meet-cancellation-email-template.tsx +3 -3
- package/template/src/components/meet-confirmation-email-template.tsx +3 -3
- package/template/src/components/meet-update-email-template.tsx +3 -3
- package/template/src/components/page-header.tsx +5 -5
- package/template/src/components/protected-page.tsx +1 -1
- package/template/src/components/reset-password-email-template.tsx +2 -2
- package/template/src/components/settings/integrations/GoogleAdsIntegration.tsx +428 -0
- package/template/src/components/settings/integrations/GoogleSheetConfigMonitoringModal.tsx +680 -0
- package/template/src/components/settings/integrations/GoogleSheetIntegration.tsx +809 -0
- package/template/src/components/settings/integrations/ImportResultDialog.tsx +124 -0
- package/template/src/components/settings/integrations/IntegrationLogPanel.tsx +57 -0
- package/template/src/components/settings/integrations/IntegrationLogsTable.tsx +186 -0
- package/template/src/components/settings/integrations/MetaLeadIntegration.tsx +451 -0
- package/template/src/components/sidebar.tsx +45 -26
- package/template/src/components/skeleton.tsx +40 -43
- package/template/src/components/ui/accordion.tsx +2 -2
- package/template/src/components/ui/alert-dialog.tsx +1 -1
- package/template/src/components/ui/button.tsx +20 -9
- package/template/src/components/ui/components.tsx +1 -1
- package/template/src/components/ui/date-picker.tsx +422 -0
- package/template/src/components/ui/datetime-picker.tsx +338 -0
- package/template/src/components/ui/status-select.tsx +271 -0
- package/template/src/components/ui/tooltip.tsx +37 -0
- package/template/src/components/view-as-modal.tsx +13 -7
- package/template/src/contexts/app-toast-context.tsx +245 -57
- package/template/src/contexts/dashboard-theme-context.tsx +53 -0
- package/template/src/contexts/sidebar-context.tsx +22 -17
- package/template/src/contexts/task-reminder-context.tsx +134 -160
- package/template/src/contexts/view-as-context.tsx +33 -6
- package/template/src/hooks/use-focus-trap.ts +2 -2
- package/template/src/hooks/useIntegrationNotifications.ts +49 -0
- package/template/src/lib/auth.ts +8 -1
- package/template/src/lib/config-links.ts +14 -0
- package/template/src/lib/contact-duplicate.ts +79 -61
- package/template/src/lib/contact-interactions.ts +21 -21
- package/template/src/lib/contact-view-filters.ts +24 -64
- package/template/src/lib/contacts-list-url.ts +190 -0
- package/template/src/lib/dashboard-stats.ts +65 -7
- package/template/src/lib/dashboard-themes.ts +135 -0
- package/template/src/lib/date-utils.ts +127 -0
- package/template/src/lib/default-widgets.ts +12 -0
- package/template/src/lib/editor-html-image-dimensions.ts +172 -0
- package/template/src/lib/editor-image-limits.ts +19 -0
- package/template/src/lib/email-html-sanitize.ts +19 -0
- package/template/src/lib/encryption.ts +9 -6
- package/template/src/lib/fr-geography.ts +192 -0
- package/template/src/lib/google-calendar-agenda.ts +201 -0
- package/template/src/lib/google-calendar.ts +255 -5
- package/template/src/lib/google-sheet-sync-jobs.ts +96 -0
- package/template/src/lib/google-sheet-sync-runner.ts +514 -0
- package/template/src/lib/integration-import-log.ts +21 -0
- package/template/src/lib/permissions.ts +40 -10
- package/template/src/lib/prisma.ts +4 -1
- package/template/src/lib/qstash.ts +65 -0
- package/template/src/lib/reminder-state-server.ts +80 -0
- package/template/src/lib/reminder-state.ts +29 -0
- package/template/src/lib/supabase-storage.ts +113 -0
- package/template/src/lib/template-variables.ts +164 -23
- package/template/src/lib/utils.ts +45 -0
- package/template/src/lib/widget-registry.ts +173 -0
- package/template/src/lib/workflow-executor.ts +16 -70
- package/template/src/proxy.ts +1 -0
- package/template/vercel.json +3 -10
- package/template/skills-lock.json +0 -25
- package/template/src/components/dashboard/dashboard-content.tsx +0 -79
- package/template/src/lib/google-drive.ts +0 -1101
- package/template/src/types/yousign.ts +0 -52
|
@@ -6,7 +6,7 @@ import { Plus, Edit, Trash2, Mail, MessageSquare, FileText, X } from 'lucide-rea
|
|
|
6
6
|
import { LazyEditor as Editor, type DefaultTemplateRef } from '@/components/lazy-editor';
|
|
7
7
|
import { AVAILABLE_VARIABLES, VARIABLE_SECTIONS } from '@/lib/template-variables';
|
|
8
8
|
import { TemplatesPageSkeleton } from '@/components/skeleton';
|
|
9
|
-
import { cn } from '@/lib/utils';
|
|
9
|
+
import { cn, devToast } from '@/lib/utils';
|
|
10
10
|
import { ProtectedPage } from '@/components/protected-page';
|
|
11
11
|
import { useConfirm } from '@/hooks/use-confirm';
|
|
12
12
|
import { useUserRole } from '@/hooks/use-user-role';
|
|
@@ -64,7 +64,7 @@ export default function TemplatesPage() {
|
|
|
64
64
|
}
|
|
65
65
|
} catch (error) {
|
|
66
66
|
console.error('Erreur:', error);
|
|
67
|
-
setError('Erreur lors du chargement des templates');
|
|
67
|
+
setError(devToast('Erreur lors du chargement des templates', error));
|
|
68
68
|
} finally {
|
|
69
69
|
setLoading(false);
|
|
70
70
|
}
|
|
@@ -153,7 +153,7 @@ export default function TemplatesPage() {
|
|
|
153
153
|
|
|
154
154
|
setTimeout(() => setSuccess(''), 5000);
|
|
155
155
|
} catch (err: any) {
|
|
156
|
-
setError(err
|
|
156
|
+
setError(devToast("Erreur lors de l'enregistrement du template", err));
|
|
157
157
|
}
|
|
158
158
|
};
|
|
159
159
|
|
|
@@ -184,7 +184,7 @@ export default function TemplatesPage() {
|
|
|
184
184
|
fetchTemplates();
|
|
185
185
|
setTimeout(() => setSuccess(''), 5000);
|
|
186
186
|
} catch (err: any) {
|
|
187
|
-
setError(err
|
|
187
|
+
setError(devToast('Erreur lors de la suppression du template', err));
|
|
188
188
|
}
|
|
189
189
|
};
|
|
190
190
|
|
|
@@ -292,7 +292,7 @@ export default function TemplatesPage() {
|
|
|
292
292
|
canCreate ? (
|
|
293
293
|
<button
|
|
294
294
|
onClick={handleNewTemplate}
|
|
295
|
-
className="cursor-pointer rounded-xl
|
|
295
|
+
className="bg-primary text-primary-foreground hover:bg-primary/90 cursor-pointer rounded-xl px-5 py-2.5 text-sm font-semibold shadow-(--shadow-card) transition-colors duration-200"
|
|
296
296
|
>
|
|
297
297
|
<Plus className="mr-2 inline h-4 w-4" />
|
|
298
298
|
Nouveau template
|
|
@@ -307,10 +307,10 @@ export default function TemplatesPage() {
|
|
|
307
307
|
<button
|
|
308
308
|
onClick={() => setFilterType('ALL')}
|
|
309
309
|
className={cn(
|
|
310
|
-
'group cursor-pointer rounded-xl px-5 py-2.5 text-sm font-semibold transition-
|
|
310
|
+
'group cursor-pointer rounded-xl px-5 py-2.5 text-sm font-semibold transition-[color,background-color,box-shadow] duration-200',
|
|
311
311
|
filterType === 'ALL'
|
|
312
312
|
? 'bg-primary text-primary-foreground shadow-(--shadow-card)'
|
|
313
|
-
: 'border
|
|
313
|
+
: 'border-border bg-card text-muted-foreground hover:bg-muted hover:text-foreground border shadow-sm',
|
|
314
314
|
)}
|
|
315
315
|
>
|
|
316
316
|
<span className="flex items-center gap-2">
|
|
@@ -325,10 +325,10 @@ export default function TemplatesPage() {
|
|
|
325
325
|
<button
|
|
326
326
|
onClick={() => setFilterType('EMAIL')}
|
|
327
327
|
className={cn(
|
|
328
|
-
'group cursor-pointer rounded-xl px-5 py-2.5 text-sm font-semibold transition-
|
|
328
|
+
'group cursor-pointer rounded-xl px-5 py-2.5 text-sm font-semibold transition-[color,background-color,box-shadow] duration-200',
|
|
329
329
|
filterType === 'EMAIL'
|
|
330
330
|
? 'bg-linear-to-r from-blue-600 to-blue-700 text-white shadow-md shadow-blue-500/30'
|
|
331
|
-
: 'border
|
|
331
|
+
: 'border-border bg-card text-muted-foreground hover:bg-muted hover:text-foreground border shadow-sm',
|
|
332
332
|
)}
|
|
333
333
|
>
|
|
334
334
|
<span className="flex items-center gap-2">
|
|
@@ -344,10 +344,10 @@ export default function TemplatesPage() {
|
|
|
344
344
|
<button
|
|
345
345
|
onClick={() => setFilterType('SMS')}
|
|
346
346
|
className={cn(
|
|
347
|
-
'group cursor-pointer rounded-xl px-5 py-2.5 text-sm font-semibold transition-
|
|
347
|
+
'group cursor-pointer rounded-xl px-5 py-2.5 text-sm font-semibold transition-[color,background-color,box-shadow] duration-200',
|
|
348
348
|
filterType === 'SMS'
|
|
349
349
|
? 'bg-linear-to-r from-emerald-600 to-emerald-700 text-white shadow-md shadow-emerald-500/30'
|
|
350
|
-
: 'border
|
|
350
|
+
: 'border-border bg-card text-muted-foreground hover:bg-muted hover:text-foreground border shadow-sm',
|
|
351
351
|
)}
|
|
352
352
|
>
|
|
353
353
|
<span className="flex items-center gap-2">
|
|
@@ -363,10 +363,10 @@ export default function TemplatesPage() {
|
|
|
363
363
|
<button
|
|
364
364
|
onClick={() => setFilterType('NOTE')}
|
|
365
365
|
className={cn(
|
|
366
|
-
'group cursor-pointer rounded-xl px-5 py-2.5 text-sm font-semibold transition-
|
|
366
|
+
'group cursor-pointer rounded-xl px-5 py-2.5 text-sm font-semibold transition-[color,background-color,box-shadow] duration-200',
|
|
367
367
|
filterType === 'NOTE'
|
|
368
368
|
? 'bg-linear-to-r from-violet-600 to-violet-700 text-white shadow-md shadow-violet-500/30'
|
|
369
|
-
: 'border
|
|
369
|
+
: 'border-border bg-card text-muted-foreground hover:bg-muted hover:text-foreground border shadow-sm',
|
|
370
370
|
)}
|
|
371
371
|
>
|
|
372
372
|
<span className="flex items-center gap-2">
|
|
@@ -383,19 +383,19 @@ export default function TemplatesPage() {
|
|
|
383
383
|
|
|
384
384
|
{/* Liste des templates */}
|
|
385
385
|
{filteredTemplates.length === 0 ? (
|
|
386
|
-
<div className="rounded-2xl border border-dashed
|
|
387
|
-
<div className="mx-auto flex h-20 w-20 items-center justify-center rounded-full
|
|
388
|
-
<FileText className="h-10 w-10
|
|
386
|
+
<div className="border-border from-muted to-card rounded-2xl border border-dashed bg-linear-to-br p-16 text-center shadow-sm">
|
|
387
|
+
<div className="bg-primary/15 mx-auto flex h-20 w-20 items-center justify-center rounded-full">
|
|
388
|
+
<FileText className="text-primary h-10 w-10" />
|
|
389
389
|
</div>
|
|
390
|
-
<h2 className="mt-6 text-xl font-bold
|
|
391
|
-
<p className="mt-2 text-sm
|
|
390
|
+
<h2 className="text-foreground mt-6 text-xl font-bold">Aucun template</h2>
|
|
391
|
+
<p className="text-muted-foreground mt-2 text-sm">
|
|
392
392
|
{filterType === 'ALL'
|
|
393
393
|
? 'Commencez par créer votre premier template pour gagner du temps'
|
|
394
394
|
: `Aucun template de type ${getTypeLabel(filterType)} trouvé`}
|
|
395
395
|
</p>
|
|
396
396
|
<button
|
|
397
397
|
onClick={handleNewTemplate}
|
|
398
|
-
className="mt-8 cursor-pointer rounded-xl
|
|
398
|
+
className="bg-primary text-primary-foreground hover:bg-primary/90 mt-8 cursor-pointer rounded-xl px-6 py-3 text-sm font-semibold shadow-(--shadow-card) transition-colors duration-200"
|
|
399
399
|
>
|
|
400
400
|
<Plus className="mr-2 inline h-4 w-4" />
|
|
401
401
|
Créer un template
|
|
@@ -406,7 +406,7 @@ export default function TemplatesPage() {
|
|
|
406
406
|
{filteredTemplates.map((template) => (
|
|
407
407
|
<div
|
|
408
408
|
key={template.id}
|
|
409
|
-
className="group relative overflow-hidden rounded-2xl border
|
|
409
|
+
className="group border-border bg-card hover:border-primary/30 relative overflow-hidden rounded-2xl border p-6 shadow-(--shadow-card) transition-[border-color,box-shadow] duration-300"
|
|
410
410
|
>
|
|
411
411
|
{/* Badge de type avec icône */}
|
|
412
412
|
<div className="mb-4 flex items-center justify-between">
|
|
@@ -426,7 +426,7 @@ export default function TemplatesPage() {
|
|
|
426
426
|
</span>
|
|
427
427
|
</div>
|
|
428
428
|
<div>
|
|
429
|
-
<h3 className="text-lg font-bold
|
|
429
|
+
<h3 className="text-foreground group-hover:text-primary text-lg font-bold transition-colors">
|
|
430
430
|
{template.name}
|
|
431
431
|
</h3>
|
|
432
432
|
<span
|
|
@@ -443,15 +443,17 @@ export default function TemplatesPage() {
|
|
|
443
443
|
|
|
444
444
|
{/* Sujet pour les emails */}
|
|
445
445
|
{template.type === 'EMAIL' && template.subject && (
|
|
446
|
-
<div className="mb-3 rounded-lg
|
|
447
|
-
<p className="text-xs font-medium
|
|
448
|
-
<p className="mt-1 text-sm font-semibold
|
|
446
|
+
<div className="bg-muted mb-3 rounded-lg p-3">
|
|
447
|
+
<p className="text-muted-foreground text-xs font-medium">Sujet</p>
|
|
448
|
+
<p className="text-foreground mt-1 text-sm font-semibold">
|
|
449
|
+
{template.subject}
|
|
450
|
+
</p>
|
|
449
451
|
</div>
|
|
450
452
|
)}
|
|
451
453
|
|
|
452
454
|
{/* Aperçu du contenu */}
|
|
453
455
|
<div className="mb-4">
|
|
454
|
-
<p className="line-clamp-3 text-sm leading-relaxed
|
|
456
|
+
<p className="text-muted-foreground line-clamp-3 text-sm leading-relaxed">
|
|
455
457
|
{template.content.replace(/<[^>]+>/g, '').substring(0, 120)}
|
|
456
458
|
{template.content.replace(/<[^>]+>/g, '').length > 120 && '...'}
|
|
457
459
|
</p>
|
|
@@ -459,11 +461,11 @@ export default function TemplatesPage() {
|
|
|
459
461
|
|
|
460
462
|
{/* Actions */}
|
|
461
463
|
{(canEdit || canDelete) && (
|
|
462
|
-
<div className="flex items-center justify-end gap-2 border-t
|
|
464
|
+
<div className="border-border flex items-center justify-end gap-2 border-t pt-4">
|
|
463
465
|
{canEdit && (
|
|
464
466
|
<button
|
|
465
467
|
onClick={() => handleEdit(template)}
|
|
466
|
-
className="
|
|
468
|
+
className="text-muted-foreground hover:bg-primary/15 hover:text-primary cursor-pointer rounded-lg p-2 transition-colors duration-200"
|
|
467
469
|
title="Modifier"
|
|
468
470
|
>
|
|
469
471
|
<Edit className="h-4 w-4" />
|
|
@@ -472,7 +474,7 @@ export default function TemplatesPage() {
|
|
|
472
474
|
{canDelete && (
|
|
473
475
|
<button
|
|
474
476
|
onClick={() => handleDelete(template.id)}
|
|
475
|
-
className="cursor-pointer rounded-lg p-2 text-gray-600 transition-
|
|
477
|
+
className="cursor-pointer rounded-lg p-2 text-gray-600 transition-colors hover:bg-red-50 hover:text-red-600"
|
|
476
478
|
title="Supprimer"
|
|
477
479
|
>
|
|
478
480
|
<Trash2 className="h-4 w-4" />
|
|
@@ -488,16 +490,16 @@ export default function TemplatesPage() {
|
|
|
488
490
|
|
|
489
491
|
{/* Modal de création/édition */}
|
|
490
492
|
{showModal && (
|
|
491
|
-
<div className="fixed inset-0 z-50 flex items-center justify-center
|
|
492
|
-
<div className="flex max-h-[90vh] w-full max-w-5xl flex-col overflow-hidden rounded-2xl border
|
|
493
|
+
<div className="bg-foreground/30 fixed inset-0 z-50 flex items-center justify-center p-4 backdrop-blur-sm sm:p-6">
|
|
494
|
+
<div className="border-border bg-card flex max-h-[90vh] w-full max-w-5xl flex-col overflow-hidden rounded-2xl border shadow-(--shadow-dropdown)">
|
|
493
495
|
{/* En-tête fixe */}
|
|
494
|
-
<div className="shrink-0 border-b
|
|
496
|
+
<div className="border-border from-muted to-card shrink-0 border-b bg-linear-to-r px-6 py-5 sm:px-8 sm:py-6">
|
|
495
497
|
<div className="flex items-center justify-between">
|
|
496
498
|
<div>
|
|
497
|
-
<h2 className="text-2xl font-bold
|
|
499
|
+
<h2 className="text-foreground text-2xl font-bold">
|
|
498
500
|
{editingTemplate ? 'Modifier le template' : 'Nouveau template'}
|
|
499
501
|
</h2>
|
|
500
|
-
<p className="mt-1 text-sm
|
|
502
|
+
<p className="text-muted-foreground mt-1 text-sm">
|
|
501
503
|
{editingTemplate
|
|
502
504
|
? 'Modifiez les informations du template'
|
|
503
505
|
: 'Créez un nouveau template réutilisable'}
|
|
@@ -510,7 +512,7 @@ export default function TemplatesPage() {
|
|
|
510
512
|
setEditingTemplate(null);
|
|
511
513
|
setError('');
|
|
512
514
|
}}
|
|
513
|
-
className="cursor-pointer rounded-xl p-2
|
|
515
|
+
className="text-muted-foreground hover:bg-muted hover:text-foreground cursor-pointer rounded-xl p-2 transition-colors duration-200"
|
|
514
516
|
>
|
|
515
517
|
<X className="h-6 w-6" />
|
|
516
518
|
</button>
|
|
@@ -524,7 +526,7 @@ export default function TemplatesPage() {
|
|
|
524
526
|
className="flex-1 space-y-6 overflow-y-auto px-6 py-6 [-ms-overflow-style:none] [scrollbar-width:none] sm:px-8 sm:py-8 [&::-webkit-scrollbar]:hidden"
|
|
525
527
|
>
|
|
526
528
|
<div>
|
|
527
|
-
<label className="block text-sm font-semibold
|
|
529
|
+
<label className="text-foreground block text-sm font-semibold">
|
|
528
530
|
Nom du template <span className="text-red-500">*</span>
|
|
529
531
|
</label>
|
|
530
532
|
<input
|
|
@@ -532,13 +534,13 @@ export default function TemplatesPage() {
|
|
|
532
534
|
required
|
|
533
535
|
value={formData.name}
|
|
534
536
|
onChange={(e) => setFormData({ ...formData, name: e.target.value })}
|
|
535
|
-
className="mt-2 block w-full rounded-xl border
|
|
537
|
+
className="border-border bg-background text-foreground focus:border-primary/50 focus:ring-primary/20 mt-2 block w-full rounded-xl border px-4 py-3 shadow-sm transition-[border-color,box-shadow] focus:ring-2 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring/50"
|
|
536
538
|
placeholder="Ex: Email de bienvenue"
|
|
537
539
|
/>
|
|
538
540
|
</div>
|
|
539
541
|
|
|
540
542
|
<div>
|
|
541
|
-
<label className="block text-sm font-semibold
|
|
543
|
+
<label className="text-foreground block text-sm font-semibold">
|
|
542
544
|
Type <span className="text-red-500">*</span>
|
|
543
545
|
</label>
|
|
544
546
|
<select
|
|
@@ -551,7 +553,7 @@ export default function TemplatesPage() {
|
|
|
551
553
|
subject: e.target.value === 'EMAIL' ? formData.subject : '',
|
|
552
554
|
});
|
|
553
555
|
}}
|
|
554
|
-
className="mt-2 block w-full rounded-xl border
|
|
556
|
+
className="border-border bg-background text-foreground focus:border-primary/50 focus:ring-primary/20 mt-2 block w-full rounded-xl border px-4 py-3 shadow-sm transition-[border-color,box-shadow] focus:ring-2 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring/50"
|
|
555
557
|
>
|
|
556
558
|
<option value="EMAIL">Email</option>
|
|
557
559
|
<option value="SMS">SMS</option>
|
|
@@ -561,7 +563,7 @@ export default function TemplatesPage() {
|
|
|
561
563
|
|
|
562
564
|
{formData.type === 'EMAIL' && (
|
|
563
565
|
<div>
|
|
564
|
-
<label className="block text-sm font-semibold
|
|
566
|
+
<label className="text-foreground block text-sm font-semibold">
|
|
565
567
|
Sujet <span className="text-red-500">*</span>
|
|
566
568
|
</label>
|
|
567
569
|
<input
|
|
@@ -569,18 +571,18 @@ export default function TemplatesPage() {
|
|
|
569
571
|
required
|
|
570
572
|
value={formData.subject}
|
|
571
573
|
onChange={(e) => setFormData({ ...formData, subject: e.target.value })}
|
|
572
|
-
className="mt-2 block w-full rounded-xl border
|
|
574
|
+
className="border-border bg-background text-foreground focus:border-primary/50 focus:ring-primary/20 mt-2 block w-full rounded-xl border px-4 py-3 shadow-sm transition-[border-color,box-shadow] focus:ring-2 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring/50"
|
|
573
575
|
placeholder="Ex: Bienvenue dans notre CRM"
|
|
574
576
|
/>
|
|
575
577
|
</div>
|
|
576
578
|
)}
|
|
577
579
|
|
|
578
580
|
<div>
|
|
579
|
-
<label className="block text-sm font-semibold
|
|
581
|
+
<label className="text-foreground block text-sm font-semibold">
|
|
580
582
|
Contenu <span className="text-red-500">*</span>
|
|
581
583
|
</label>
|
|
582
584
|
{formData.type === 'EMAIL' || formData.type === 'NOTE' ? (
|
|
583
|
-
<div className="mt-2 rounded-xl border
|
|
585
|
+
<div className="border-border mt-2 rounded-xl border shadow-sm">
|
|
584
586
|
<Editor
|
|
585
587
|
ref={formData.type === 'EMAIL' ? emailEditorRef : noteEditorRef}
|
|
586
588
|
onReady={(methods) => {
|
|
@@ -603,21 +605,21 @@ export default function TemplatesPage() {
|
|
|
603
605
|
value={formData.content}
|
|
604
606
|
onChange={(e) => setFormData({ ...formData, content: e.target.value })}
|
|
605
607
|
rows={6}
|
|
606
|
-
className="mt-2 block w-full rounded-xl border
|
|
608
|
+
className="border-border bg-background text-foreground focus:border-primary/50 focus:ring-primary/20 mt-2 block w-full rounded-xl border px-4 py-3 shadow-sm transition-[border-color,box-shadow] focus:ring-2 focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring/50"
|
|
607
609
|
placeholder="Contenu du SMS..."
|
|
608
610
|
/>
|
|
609
611
|
</div>
|
|
610
612
|
)}
|
|
611
613
|
|
|
612
614
|
{/* Section Variables */}
|
|
613
|
-
<div className="mt-6 rounded-xl border
|
|
615
|
+
<div className="border-primary/20 from-primary/10 to-card mt-6 rounded-xl border bg-linear-to-br p-5">
|
|
614
616
|
<div className="mb-4 flex items-center gap-2">
|
|
615
|
-
<div className="flex h-8 w-8 items-center justify-center rounded-lg
|
|
616
|
-
<FileText className="h-4 w-4
|
|
617
|
+
<div className="bg-primary/15 flex h-8 w-8 items-center justify-center rounded-lg">
|
|
618
|
+
<FileText className="text-primary h-4 w-4" />
|
|
617
619
|
</div>
|
|
618
620
|
<div>
|
|
619
|
-
<p className="text-sm font-bold
|
|
620
|
-
<p className="text-
|
|
621
|
+
<p className="text-foreground text-sm font-bold">Variables disponibles</p>
|
|
622
|
+
<p className="text-muted-foreground text-xs">
|
|
621
623
|
Cliquez sur une variable pour l'insérer dans le contenu
|
|
622
624
|
</p>
|
|
623
625
|
</div>
|
|
@@ -707,7 +709,7 @@ export default function TemplatesPage() {
|
|
|
707
709
|
}
|
|
708
710
|
}}
|
|
709
711
|
className={cn(
|
|
710
|
-
'cursor-pointer rounded-lg border px-3 py-2 text-left shadow-sm transition-
|
|
712
|
+
'cursor-pointer rounded-lg border px-3 py-2 text-left shadow-sm transition-[border-color,box-shadow] hover:shadow-md',
|
|
711
713
|
colors.border,
|
|
712
714
|
colors.bg,
|
|
713
715
|
colors.hoverBg,
|
|
@@ -720,7 +722,7 @@ export default function TemplatesPage() {
|
|
|
720
722
|
>
|
|
721
723
|
{variable.key}
|
|
722
724
|
</span>
|
|
723
|
-
<p className="mt-1 max-w-[200px] text-[11px] leading-tight font-normal
|
|
725
|
+
<p className="text-muted-foreground mt-1 max-w-[200px] text-[11px] leading-tight font-normal">
|
|
724
726
|
{variable.description}
|
|
725
727
|
</p>
|
|
726
728
|
</button>
|
|
@@ -731,11 +733,10 @@ export default function TemplatesPage() {
|
|
|
731
733
|
})}
|
|
732
734
|
</div>
|
|
733
735
|
</div>
|
|
734
|
-
|
|
735
736
|
</form>
|
|
736
737
|
|
|
737
738
|
{/* Pied de modal fixe */}
|
|
738
|
-
<div className="shrink-0 border-t
|
|
739
|
+
<div className="border-border bg-muted shrink-0 border-t px-6 py-5 sm:px-8 sm:py-6">
|
|
739
740
|
<div className="flex flex-col gap-3 sm:flex-row sm:justify-end">
|
|
740
741
|
<button
|
|
741
742
|
type="button"
|
|
@@ -744,14 +745,14 @@ export default function TemplatesPage() {
|
|
|
744
745
|
setEditingTemplate(null);
|
|
745
746
|
setError('');
|
|
746
747
|
}}
|
|
747
|
-
className="w-full cursor-pointer rounded-xl border
|
|
748
|
+
className="border-border bg-card text-foreground hover:bg-background w-full cursor-pointer rounded-xl border px-6 py-3 text-sm font-semibold shadow-sm transition-[color,background-color,box-shadow] duration-200 hover:shadow-md sm:w-auto"
|
|
748
749
|
>
|
|
749
750
|
Annuler
|
|
750
751
|
</button>
|
|
751
752
|
<button
|
|
752
753
|
type="submit"
|
|
753
754
|
form="template-form"
|
|
754
|
-
className="w-full cursor-pointer rounded-xl
|
|
755
|
+
className="bg-primary text-primary-foreground hover:bg-primary/90 w-full cursor-pointer rounded-xl px-6 py-3 text-sm font-semibold shadow-(--shadow-card) transition-colors duration-200 sm:w-auto"
|
|
755
756
|
>
|
|
756
757
|
{editingTemplate ? 'Modifier le template' : 'Créer le template'}
|
|
757
758
|
</button>
|