Seth commited on
Commit ·
d9926cf
1
Parent(s): 5e70d64
update
Browse files- frontend/src/pages/Leads.jsx +50 -4
frontend/src/pages/Leads.jsx
CHANGED
|
@@ -11,6 +11,7 @@ import {
|
|
| 11 |
Trash2,
|
| 12 |
Handshake,
|
| 13 |
Pencil,
|
|
|
|
| 14 |
} from 'lucide-react';
|
| 15 |
import { Button } from '@/components/ui/button';
|
| 16 |
import { Select, SelectTrigger, SelectContent, SelectItem } from '@/components/ui/select';
|
|
@@ -72,6 +73,26 @@ export default function Leads() {
|
|
| 72 |
const [rowSelection, setRowSelection] = useState({});
|
| 73 |
const [bulkBusy, setBulkBusy] = useState(null);
|
| 74 |
const [tableEditRowId, setTableEditRowId] = useState(null);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 75 |
|
| 76 |
const selectedIds = useMemo(
|
| 77 |
() => Object.keys(rowSelection).filter((id) => rowSelection[id]).map(Number),
|
|
@@ -82,8 +103,12 @@ export default function Leads() {
|
|
| 82 |
|
| 83 |
const webhookUrl = useMemo(() => {
|
| 84 |
if (typeof window === 'undefined') return '';
|
| 85 |
-
|
| 86 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
| 87 |
|
| 88 |
const fetchLeads = useCallback(async () => {
|
| 89 |
setLoading(true);
|
|
@@ -380,8 +405,29 @@ export default function Leads() {
|
|
| 380 |
title="Leads"
|
| 381 |
subtitle={
|
| 382 |
<>
|
| 383 |
-
Replies from Smartlead campaigns appear here. Webhook URL:{' '}
|
| 384 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 385 |
</>
|
| 386 |
}
|
| 387 |
>
|
|
|
|
| 11 |
Trash2,
|
| 12 |
Handshake,
|
| 13 |
Pencil,
|
| 14 |
+
ClipboardCopy,
|
| 15 |
} from 'lucide-react';
|
| 16 |
import { Button } from '@/components/ui/button';
|
| 17 |
import { Select, SelectTrigger, SelectContent, SelectItem } from '@/components/ui/select';
|
|
|
|
| 73 |
const [rowSelection, setRowSelection] = useState({});
|
| 74 |
const [bulkBusy, setBulkBusy] = useState(null);
|
| 75 |
const [tableEditRowId, setTableEditRowId] = useState(null);
|
| 76 |
+
/** undefined = loading /auth/me; null = signed out or no tenant; number = workspace id for webhook */
|
| 77 |
+
const [webhookTenantId, setWebhookTenantId] = useState(undefined);
|
| 78 |
+
|
| 79 |
+
useEffect(() => {
|
| 80 |
+
let cancelled = false;
|
| 81 |
+
apiFetch('/api/auth/me').then(async (r) => {
|
| 82 |
+
if (cancelled) return;
|
| 83 |
+
if (!r.ok) {
|
| 84 |
+
setWebhookTenantId(null);
|
| 85 |
+
return;
|
| 86 |
+
}
|
| 87 |
+
const u = await r.json().catch(() => null);
|
| 88 |
+
if (cancelled) return;
|
| 89 |
+
const tid = u?.current_tenant_id;
|
| 90 |
+
setWebhookTenantId(tid != null ? Number(tid) : null);
|
| 91 |
+
});
|
| 92 |
+
return () => {
|
| 93 |
+
cancelled = true;
|
| 94 |
+
};
|
| 95 |
+
}, []);
|
| 96 |
|
| 97 |
const selectedIds = useMemo(
|
| 98 |
() => Object.keys(rowSelection).filter((id) => rowSelection[id]).map(Number),
|
|
|
|
| 103 |
|
| 104 |
const webhookUrl = useMemo(() => {
|
| 105 |
if (typeof window === 'undefined') return '';
|
| 106 |
+
const base = `${window.location.origin}/api/webhooks/smartlead`;
|
| 107 |
+
if (typeof webhookTenantId === 'number' && !Number.isNaN(webhookTenantId)) {
|
| 108 |
+
return `${base}?tenant_id=${webhookTenantId}`;
|
| 109 |
+
}
|
| 110 |
+
return base;
|
| 111 |
+
}, [webhookTenantId]);
|
| 112 |
|
| 113 |
const fetchLeads = useCallback(async () => {
|
| 114 |
setLoading(true);
|
|
|
|
| 405 |
title="Leads"
|
| 406 |
subtitle={
|
| 407 |
<>
|
| 408 |
+
Replies from Smartlead campaigns appear here. Webhook URL (this workspace):{' '}
|
| 409 |
+
{webhookTenantId === undefined ? (
|
| 410 |
+
<Loader2 className="inline h-3.5 w-3.5 animate-spin align-middle text-slate-400" />
|
| 411 |
+
) : (
|
| 412 |
+
<span className="inline-flex max-w-full flex-wrap items-center gap-1 align-middle">
|
| 413 |
+
<code className="text-xs bg-slate-100 px-1.5 py-0.5 rounded break-all">
|
| 414 |
+
{webhookUrl}
|
| 415 |
+
</code>
|
| 416 |
+
<Button
|
| 417 |
+
type="button"
|
| 418 |
+
variant="outline"
|
| 419 |
+
size="sm"
|
| 420 |
+
className="h-7 shrink-0 gap-1 px-2 text-xs"
|
| 421 |
+
title="Copy webhook URL"
|
| 422 |
+
onClick={() => {
|
| 423 |
+
if (webhookUrl) navigator.clipboard.writeText(webhookUrl);
|
| 424 |
+
}}
|
| 425 |
+
>
|
| 426 |
+
<ClipboardCopy className="h-3.5 w-3.5" />
|
| 427 |
+
Copy
|
| 428 |
+
</Button>
|
| 429 |
+
</span>
|
| 430 |
+
)}
|
| 431 |
</>
|
| 432 |
}
|
| 433 |
>
|