Officer suggestions: use FCC data (RMD contact, CORES address) instead of entity_cache

Entity cache has no RA/officer data yet. Instead, fetch the FCC lookup
(quick mode) and offer RMD contact name + address and CORES principal
address as clickable suggestions to auto-fill Officer 1.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
justin 2026-04-29 01:02:18 -05:00
parent 6a0162f0a9
commit acf63eb819

View file

@ -121,52 +121,71 @@
};
}
// Fetch matching corporate records for officer suggestions
async function loadOfficerSuggestions(entityName: string) {
if (!entityName) return;
// Auto-fill Officer 1 from FCC data if available but not yet filled
async function prefillFromFCC(entity: any) {
if (!entity?.frn) return;
const API = (window as any).__PW_API || "";
const suggestDiv = g<HTMLElement>("pw-officer-suggestions");
const listDiv = g<HTMLElement>("pw-officer-suggest-list");
const f = officerFields(1);
// If Officer 1 already has a name, don't overwrite
if (f.n.value.trim()) return;
try {
// Search entity_cache for matching corporations across all states
const resp = await fetch(`${API}/api/v1/corp/search?q=${encodeURIComponent(entityName)}&limit=5`);
const resp = await fetch(`${API}/api/v1/fcc/lookup?frn=${entity.frn}&quick=1`);
if (!resp.ok) return;
const data = await resp.json();
const results = data.results || [];
const d = await resp.json();
if (results.length === 0) return;
const suggestions: Array<{name: string; title: string; source: string; address?: string; city?: string; state?: string; zip?: string}> = [];
// RMD contact
if (d.rmd?.contact_name) {
const addrLines = (d.rmd.business_address || "").split("\n").map((s: string) => s.trim()).filter(Boolean);
const lastLine = addrLines[addrLines.length - 1] || "";
const stateZipMatch = lastLine.match(/([A-Z]{2})\s+(\d{5})/);
suggestions.push({
name: d.rmd.contact_name,
title: "Contact (from RMD filing)",
source: "FCC RMD",
address: addrLines.length > 1 ? addrLines.slice(0, -1).join(", ") : addrLines[0],
city: stateZipMatch ? lastLine.replace(stateZipMatch[0], "").replace(/,?\s*$/, "").trim() : "",
state: stateZipMatch ? stateZipMatch[1] : "",
zip: stateZipMatch ? stateZipMatch[2] : "",
});
}
// CORES address (entity-level, not a person name)
if (d.cores?.address && d.cores.city) {
suggestions.push({
name: "",
title: "Principal address (from CORES)",
source: "FCC CORES",
address: d.cores.address,
city: d.cores.city,
state: d.cores.state || "",
zip: d.cores.zip || "",
});
}
if (suggestions.length === 0) return;
listDiv.innerHTML = "";
for (const r of results) {
for (const s of suggestions) {
const btn = document.createElement("button");
btn.type = "button";
btn.className = "pw-suggest-btn";
const ra = r.registered_agent || "";
const addr = r.principal_address || "";
btn.innerHTML = `
<span class="sg-name">${r.entity_name}</span>
<span class="sg-detail">${r.state || ""} · ${r.entity_type || ""} · ${r.status || ""}</span>
${ra ? `<span class="sg-detail">RA: ${ra}</span>` : ""}
${addr ? `<span class="sg-detail">${addr}</span>` : ""}
${s.name ? `<span class="sg-name">${s.name}</span>` : ""}
<span class="sg-detail">${s.title}</span>
${s.address ? `<span class="sg-detail">${[s.address, s.city, s.state, s.zip].filter(Boolean).join(", ")}</span>` : ""}
`;
btn.addEventListener("click", () => {
// Auto-fill Officer 1 from this record
const f = officerFields(1);
if (ra && !f.n.value.trim()) {
f.n.value = ra;
}
// Parse address if available
if (addr) {
const parts = addr.split(",").map((s: string) => s.trim());
if (parts.length >= 1 && !f.street.value.trim()) f.street.value = parts[0];
if (parts.length >= 2 && !f.city.value.trim()) f.city.value = parts[parts.length - 2] || parts[1];
if (parts.length >= 3) {
const stateZip = parts[parts.length - 1].trim().split(/\s+/);
if (stateZip[0] && !f.state.value.trim()) f.state.value = stateZip[0];
if (stateZip[1] && !f.zip.value.trim()) f.zip.value = stateZip[1];
}
}
if (s.name) f.n.value = s.name;
if (s.address) f.street.value = s.address;
if (s.city) f.city.value = s.city;
if (s.state) f.state.value = s.state;
if (s.zip) f.zip.value = s.zip;
suggestDiv.hidden = true;
});
listDiv.appendChild(btn);
@ -197,10 +216,9 @@
f.zip.value = oc.zip || (i === 1 ? (s.entity?.address_zip || "") : "");
}
// Load corporate record suggestions — always show if we have a legal name
const legalName = s.entity?.legal_name || s.intake_data?.entity_legal_name || "";
if (legalName) {
loadOfficerSuggestions(legalName);
// Show FCC-sourced suggestions if Officer 1 is empty
if (s.entity?.frn) {
prefillFromFCC(s.entity);
}
});