import { supabase } from "@/integrations/supabase/client"; export type VarMap = Record; export type LoadedContext = { client?: any; cases?: any; clientFields: { key: string; label: string; value: string }[]; caseFields: { key: string; label: string; value: string }[]; }; export type VarChip = { token: string; label: string; value: string }; export async function loadPleadingContext( clientId: string | null, caseId: string | null, ): Promise { const result: LoadedContext = { clientFields: [], caseFields: [] }; if (clientId) { const { data: client } = await supabase.from("clients").select("*").eq("id", clientId).maybeSingle(); if (client) result.client = client; const [{ data: defs }, { data: vals }] = await Promise.all([ supabase.from("custom_client_fields").select("id, key, label").eq("active", true).order("sort_order"), supabase.from("client_field_values").select("field_id, value").eq("client_id", clientId), ]); const valMap = new Map((vals || []).map((v: any) => [v.field_id, v.value || ""])); result.clientFields = (defs || []).map((d: any) => ({ key: d.key, label: d.label, value: valMap.get(d.id) || "", })); } if (caseId) { const { data: caseRow } = await supabase.from("cases").select("*").eq("id", caseId).maybeSingle(); if (caseRow) result.cases = caseRow; const [{ data: defs }, { data: vals }] = await Promise.all([ supabase.from("custom_case_fields").select("id, key, label").eq("active", true).order("sort_order"), supabase.from("case_field_values").select("field_id, value").eq("case_id", caseId), ]); const valMap = new Map((vals || []).map((v: any) => [v.field_id, v.value || ""])); result.caseFields = (defs || []).map((d: any) => ({ key: d.key, label: d.label, value: valMap.get(d.id) || "", })); } return result; } function fmtAddress(o: any): string { if (!o) return ""; const parts = [ o.address_line1, o.address_line2, [o.city, o.state, o.postal_code].filter(Boolean).join(", "), ].filter(Boolean); return parts.join("\n"); } export function buildVarMap(ctx: LoadedContext): VarMap { const m: VarMap = {}; const c = ctx.client; if (c) { m["client.name"] = c.name || ""; m["clientName"] = c.name || ""; m["client.address"] = fmtAddress(c); m["clientAddress"] = fmtAddress(c); m["client.address_line1"] = c.address_line1 || ""; m["clientAddressLine1"] = c.address_line1 || ""; m["client.address_line2"] = c.address_line2 || ""; m["clientAddressLine2"] = c.address_line2 || ""; m["client.city"] = c.city || ""; m["client.state"] = c.state || ""; m["client.postal_code"] = c.postal_code || ""; m["client.contact_name"] = c.primary_contact_name || ""; m["clientContactName"] = c.primary_contact_name || ""; m["client.contact_email"] = c.primary_contact_email || ""; m["clientContactEmail"] = c.primary_contact_email || ""; m["client.contact_phone"] = c.primary_contact_phone || ""; m["clientContactPhone"] = c.primary_contact_phone || ""; m["client.management_company"] = c.management_company || ""; m["managementCompany"] = c.management_company || ""; } const k = ctx.cases; if (k) { m["case.number"] = k.case_number || ""; m["caseNumber"] = k.case_number || ""; m["case.title"] = k.title || ""; m["caseTitle"] = k.title || ""; m["case.caption"] = k.case_caption || ""; m["caseCaption"] = k.case_caption || ""; m["case.court"] = k.court || ""; m["court"] = k.court || ""; m["case.court_case_number"] = k.court_case_number || ""; m["courtCaseNumber"] = k.court_case_number || ""; m["case.judge"] = k.judge || ""; m["judge"] = k.judge || ""; m["case.jurisdiction"] = k.jurisdiction || ""; m["jurisdiction"] = k.jurisdiction || ""; m["case.opposing_party"] = k.opposing_party || ""; m["opposingParty"] = k.opposing_party || ""; m["case.opposing_counsel"] = k.opposing_counsel || ""; m["opposingCounsel"] = k.opposing_counsel || ""; m["case.opposing_counsel_firm"] = k.opposing_counsel_firm || ""; m["opposingCounselFirm"] = k.opposing_counsel_firm || ""; m["case.opposing_counsel_email"] = k.opposing_counsel_email || ""; m["opposingCounselEmail"] = k.opposing_counsel_email || ""; m["case.opposing_counsel_phone"] = k.opposing_counsel_phone || ""; m["opposingCounselPhone"] = k.opposing_counsel_phone || ""; m["case.filing_date"] = k.filing_date || ""; m["filingDate"] = k.filing_date || ""; m["case.next_hearing_date"] = k.next_hearing_date || ""; m["nextHearingDate"] = k.next_hearing_date || ""; } ctx.clientFields.forEach((f) => { m[`client.field.${f.key}`] = f.value; m[`client.custom.${f.key}`] = f.value; }); ctx.caseFields.forEach((f) => { m[`case.field.${f.key}`] = f.value; m[`case.custom.${f.key}`] = f.value; m[`custom.${f.key}`] = f.value; }); return m; } export function buildChips(ctx: LoadedContext): VarChip[] { const m = buildVarMap(ctx); const out: VarChip[] = []; const labelMap: Record = { "client.name": "Client name", clientName: "Client name", "client.address": "Client address (full)", clientAddress: "Client address (full)", "client.contact_name": "Client primary contact", clientContactName: "Client primary contact", "client.contact_email": "Client contact email", clientContactEmail: "Client contact email", "client.contact_phone": "Client contact phone", clientContactPhone: "Client contact phone", "client.management_company": "Management company", managementCompany: "Management company", "case.number": "Case number", caseNumber: "Case number", "case.title": "Case title", caseTitle: "Case title", "case.caption": "Case caption", caseCaption: "Case caption", "case.court": "Court", court: "Court", "case.court_case_number": "Court case number", courtCaseNumber: "Court case number", "case.judge": "Judge", judge: "Judge", "case.opposing_party": "Opposing party", opposingParty: "Opposing party", "case.opposing_counsel": "Opposing counsel", opposingCounsel: "Opposing counsel", "case.opposing_counsel_firm": "Opposing counsel firm", opposingCounselFirm: "Opposing counsel firm", "case.filing_date": "Filing date", filingDate: "Filing date", "case.next_hearing_date": "Next hearing date", nextHearingDate: "Next hearing date", }; for (const key of Object.keys(m)) { let label = labelMap[key]; if (!label) { if (key.startsWith("client.field.")) label = `Client · ${key.replace("client.field.", "")}`; else if (key.startsWith("client.custom.")) label = `Client · ${key.replace("client.custom.", "")}`; else if (key.startsWith("case.field.")) label = `Case · ${key.replace("case.field.", "")}`; else if (key.startsWith("case.custom.")) label = `Case · ${key.replace("case.custom.", "")}`; else if (key.startsWith("custom.")) label = `Case · ${key.replace("custom.", "")}`; else label = key; } out.push({ token: `{{${key}}}`, label, value: m[key] }); } return out; } const TOKEN_RE = /\{\{\s*([a-zA-Z0-9_.]+)\s*\}\}/g; export function applyVars(text: string, map: VarMap): string { if (!text) return text; return text.replace(TOKEN_RE, (_, key) => (key in map ? map[key] : `{{${key}}}`)); } export function applyVarsToHtml(html: string, map: VarMap): string { return applyVars(html, map); }