Actualizar frontend/src/components/ConfigModal.jsx
This commit is contained in:
@@ -888,9 +888,16 @@ export default function ConfigModal({ onClose }) {
|
||||
<button onClick={() => setSeccion("plantillas")}
|
||||
style={{ width: "100%", textAlign: "left", padding: "10px 12px", borderRadius: 8,
|
||||
border: "none", cursor: "pointer", fontSize: 14, fontWeight: 600, whiteSpace: "nowrap",
|
||||
marginBottom: 4,
|
||||
background: seccion === "plantillas" ? "#e2e8f0" : "transparent", color: "#1e293b" }}>
|
||||
Plantillas
|
||||
</button>
|
||||
<button onClick={() => setSeccion("exportar_base")}
|
||||
style={{ width: "100%", textAlign: "left", padding: "10px 12px", borderRadius: 8,
|
||||
border: "none", cursor: "pointer", fontSize: 14, fontWeight: 600, whiteSpace: "nowrap",
|
||||
background: seccion === "exportar_base" ? "#e2e8f0" : "transparent", color: "#1e293b" }}>
|
||||
Exportar Base
|
||||
</button>
|
||||
</div>
|
||||
{/* Contenido */}
|
||||
<div style={{ flex: 1, display: "flex", flexDirection: "column" }}>
|
||||
@@ -902,6 +909,7 @@ export default function ConfigModal({ onClose }) {
|
||||
: seccion === "leyendas" ? "Leyenda"
|
||||
: seccion === "plantillas" ? "Plantillas"
|
||||
: seccion === "subir_base" ? "Subir Base"
|
||||
: seccion === "exportar_base" ? "Exportar Base"
|
||||
: "Sedes de Anuncios"}
|
||||
</div>
|
||||
<button onClick={onClose}
|
||||
@@ -912,6 +920,10 @@ export default function ConfigModal({ onClose }) {
|
||||
<div style={{ flex: 1, overflow: "auto", padding: "16px 22px 24px" }}>
|
||||
<SubirBase />
|
||||
</div>
|
||||
) : seccion === "exportar_base" ? (
|
||||
<div style={{ flex: 1, overflow: "auto", padding: "16px 22px 24px" }}>
|
||||
<ExportarBase />
|
||||
</div>
|
||||
) : seccion === "plantillas" ? (
|
||||
<div style={{ flex: 1, overflow: "auto", padding: "16px 22px 24px" }}>
|
||||
<Plantillas ocultarTitulo />
|
||||
@@ -1238,3 +1250,97 @@ function SubirBase() {
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
// ── EXPORTAR BASE ──────────────────────────────────────────────────────────
|
||||
// Elige un asesor (en vivo de Chatwoot) y descarga su base de leads deduplicada
|
||||
// (teléfono más antiguo), con SEDE_ACT por asesor y última etiqueta.
|
||||
function ExportarBase() {
|
||||
const [asesores, setAsesores] = useState([]);
|
||||
const [asesorSel, setAsesorSel] = useState("");
|
||||
const [etiquetas, setEtiquetas] = useState([]);
|
||||
const [etiqSel, setEtiqSel] = useState([]);
|
||||
const [cargando, setCargando] = useState(false);
|
||||
const [msg, setMsg] = useState("");
|
||||
|
||||
useEffect(() => {
|
||||
api.exportarBaseAsesores().then((r) => setAsesores(r.asesores || [])).catch(() => {});
|
||||
api.subirBaseEtiquetas().then((r) => setEtiquetas(r.etiquetas || [])).catch(() => {});
|
||||
}, []);
|
||||
|
||||
function toggleEtiqueta(t) {
|
||||
setEtiqSel((p) => p.includes(t) ? p.filter((x) => x !== t) : [...p, t]);
|
||||
}
|
||||
|
||||
async function exportar() {
|
||||
if (!asesorSel || cargando) return;
|
||||
setCargando(true); setMsg("");
|
||||
try {
|
||||
await api.exportarBaseDescargar(asesorSel, etiqSel);
|
||||
setMsg("✓ Base descargada.");
|
||||
} catch (e) {
|
||||
setMsg("Error al exportar: " + e.message);
|
||||
}
|
||||
setCargando(false);
|
||||
}
|
||||
|
||||
const puede = asesorSel && !cargando;
|
||||
const card = { background: "#fff", border: "1px solid #e6eaf0", borderRadius: 14,
|
||||
padding: 20, boxShadow: "0 1px 3px rgba(15,23,42,.04)" };
|
||||
const cardHead = { display: "flex", alignItems: "center", gap: 10, marginBottom: 4 };
|
||||
const step = { width: 26, height: 26, borderRadius: 8, background: "#1e3a5f", color: "#fff",
|
||||
display: "flex", alignItems: "center", justifyContent: "center",
|
||||
fontSize: 13, fontWeight: 800, flexShrink: 0 };
|
||||
const cardTitle = { fontSize: 15, fontWeight: 700, color: "#0f172a" };
|
||||
const cardSub = { fontSize: 12.5, color: "#94a3b8", margin: "2px 0 14px 36px" };
|
||||
const fieldLabel = { fontSize: 12, fontWeight: 700, color: "#64748b", marginBottom: 7,
|
||||
textTransform: "uppercase", letterSpacing: ".02em", display: "block" };
|
||||
|
||||
return (
|
||||
<div style={{ display: "flex", flexDirection: "column", gap: 16, maxWidth: 680 }}>
|
||||
<div style={card}>
|
||||
<div style={cardHead}>
|
||||
<span style={step}>1</span>
|
||||
<span style={cardTitle}>Elige el asesor</span>
|
||||
</div>
|
||||
<div style={cardSub}>
|
||||
Se descargará su base de leads (un número por teléfono, el más antiguo),
|
||||
con sede, programa, fecha y última etiqueta.
|
||||
</div>
|
||||
<label style={fieldLabel}>👤 Asesor</label>
|
||||
<Select value={asesorSel}
|
||||
options={[{ value: "", label: "— Elige un asesor —" },
|
||||
...asesores.map((a) => ({ value: a.nombre, label: a.nombre }))]}
|
||||
onChange={(v) => { setAsesorSel(v); setMsg(""); }}
|
||||
minWidth={0} />
|
||||
</div>
|
||||
|
||||
<div style={card}>
|
||||
<div style={cardHead}>
|
||||
<span style={step}>2</span>
|
||||
<span style={cardTitle}>Etiquetas (opcional)</span>
|
||||
<span style={{ marginLeft: "auto", fontSize: 12, color: "#94a3b8", fontWeight: 600 }}>
|
||||
{etiqSel.length} seleccionada{etiqSel.length === 1 ? "" : "s"}
|
||||
</span>
|
||||
</div>
|
||||
<div style={cardSub}>
|
||||
Filtra la base por la última etiqueta de cada número. Si no eliges ninguna,
|
||||
se incluyen todas.
|
||||
</div>
|
||||
<label style={fieldLabel}>🏷️ Etiquetas de Chatwoot</label>
|
||||
<MultiSelectEtiquetas opciones={etiquetas} seleccion={etiqSel} onToggle={toggleEtiqueta} />
|
||||
</div>
|
||||
|
||||
<button onClick={exportar} disabled={!puede}
|
||||
style={{ width: "100%", padding: "13px", borderRadius: 11, border: "none",
|
||||
background: puede ? "#1e3a5f" : "#cbd5e1", color: "#fff", fontWeight: 700, fontSize: 14.5,
|
||||
cursor: puede ? "pointer" : "default" }}>
|
||||
{cargando ? "Generando Excel…" : "⬇ Exportar base a Excel"}
|
||||
</button>
|
||||
|
||||
{msg && (
|
||||
<div style={{ fontSize: 13, fontWeight: 600,
|
||||
color: msg.startsWith("✓") ? "#15803d" : "#b91c1c" }}>{msg}</div>
|
||||
)}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user