diff --git a/requirements.txt b/requirements.txt index f675a57..cfe4602 100644 --- a/requirements.txt +++ b/requirements.txt @@ -3,3 +3,4 @@ uvicorn[standard] python-multipart python-docx pendulum +openpyxl diff --git a/scripts/build-excel-maps-from-old-app.py b/scripts/build-excel-maps-from-old-app.py new file mode 100644 index 0000000..7176736 --- /dev/null +++ b/scripts/build-excel-maps-from-old-app.py @@ -0,0 +1,137 @@ +import json +import re +from pathlib import Path + +OLD_APP = Path("/mnt/storage/sftp/mcelwain/repository/word-doc-generator") +OLD_CONSTANTS_CANDIDATES = [ + OLD_APP / "public" / "constants.js", + OLD_APP / "constants.js", +] + +OUT_DIR = Path("tools/doc_generator/content/excel_maps") +OUT_FILE = OUT_DIR / "legacy_excel_maps.json" + +CELL_RE = re.compile(r"([A-Za-z_][A-Za-z0-9_]*)\s*:\s*['\"]([A-Z]{1,3}[0-9]{1,5})['\"]") + + +def find_constants_file(): + for path in OLD_CONSTANTS_CANDIDATES: + if path.exists(): + return path + raise SystemExit("Could not find old constants.js") + + +def extract_object_blocks(text): + """ + Finds JS object-ish assignment/export blocks that contain Excel cell mappings. + This is intentionally simple and robust for the old constants.js style. + """ + blocks = [] + + # Match things like: + # const fieldToCellMap = { ... }; + # export const fieldToCellMap = { ... }; + # let someMap = { ... }; + pattern = re.compile( + r"(?:export\s+)?(?:const|let|var)\s+([A-Za-z_][A-Za-z0-9_]*)\s*=\s*\{", + re.MULTILINE, + ) + + for match in pattern.finditer(text): + name = match.group(1) + start = match.end() - 1 + + depth = 0 + end = None + + for i in range(start, len(text)): + char = text[i] + if char == "{": + depth += 1 + elif char == "}": + depth -= 1 + if depth == 0: + end = i + 1 + break + + if end: + block = text[start:end] + cells = dict(CELL_RE.findall(block)) + if cells: + blocks.append((name, cells)) + + return blocks + + +def label_from_name(name): + label = re.sub(r"([a-z])([A-Z])", r"\1 \2", name) + label = label.replace("_", " ").replace("-", " ") + label = re.sub(r"\s+", " ", label).strip() + return label.title() + + +def normalize_id(name): + value = re.sub(r"([a-z])([A-Z])", r"\1_\2", name) + value = re.sub(r"[^A-Za-z0-9]+", "_", value).strip("_").lower() + return value or "excel_map" + + +def discover_excel_templates(): + templates = [] + + for path in sorted(OLD_APP.rglob("*.xlsx")): + if ".git" in path.parts or "node_modules" in path.parts: + continue + + rel = path.relative_to(OLD_APP).as_posix() + templates.append({ + "label": rel, + "legacyPath": str(path), + "filename": path.name + }) + + return templates + + +def main(): + constants_path = find_constants_file() + text = constants_path.read_text(encoding="utf-8", errors="ignore") + + blocks = extract_object_blocks(text) + excel_templates = discover_excel_templates() + + maps = [] + + for name, cells in blocks: + map_id = normalize_id(name) + + maps.append({ + "id": map_id, + "sourceName": name, + "label": label_from_name(name), + "description": f"Generated from {constants_path.relative_to(OLD_APP)} object {name}.", + "template": excel_templates[0]["filename"] if excel_templates else "", + "legacyTemplateCandidates": excel_templates, + "fields": dict(sorted(cells.items(), key=lambda item: item[1])) + }) + + OUT_DIR.mkdir(parents=True, exist_ok=True) + OUT_FILE.write_text(json.dumps({ + "id": "legacy_excel_maps", + "source": str(constants_path), + "maps": maps + }, indent=2), encoding="utf-8") + + print(f"Wrote {OUT_FILE}") + print(f"Source: {constants_path}") + print(f"Excel templates found: {len(excel_templates)}") + for t in excel_templates: + print(f"- {t['legacyPath']}") + + print(f"Maps found: {len(maps)}") + for item in maps: + print(f"- {item['id']}: {len(item['fields'])} fields") + + +if __name__ == "__main__": + main() diff --git a/scripts/build-legal-profile-from-old-app.py b/scripts/build-legal-profile-from-old-app.py new file mode 100644 index 0000000..ecdbf22 --- /dev/null +++ b/scripts/build-legal-profile-from-old-app.py @@ -0,0 +1,192 @@ +import json +import re +import subprocess +from pathlib import Path + +OLD_APP = Path("/mnt/storage/sftp/mcelwain/repository/word-doc-generator") +DRAFT_PROFILE = Path("diagnostics/legacy_word_doc_generator_profile_draft.json") +OUT_PROFILE = Path("tools/doc_generator/content/document_types/legal_profile.json") +TEMPLATES_OUT = Path("tools/doc_generator/content/templates/legacy") + +OLD_PUBLIC = OLD_APP / "public" + + +def run_node_list_extractor(): + js = f""" +import {{ pathToFileURL }} from 'url'; + +const files = [ + 'casePlaintiffInfo.js', + 'opposingCounselInfo.js', + 'judgeInfo.js', + 'caseFilingAttorneyInfo.js', + 'filingAttorneyInfo.js', + 'debtCollectorInfo.js' +]; + +const base = {json.dumps(str(OLD_PUBLIC))}; +const result = {{}}; + +for (const file of files) {{ + try {{ + const mod = await import(pathToFileURL(`${{base}}/${{file}}`).href); + for (const [exportName, value] of Object.entries(mod)) {{ + if (value && typeof value === 'object' && !Array.isArray(value)) {{ + result[exportName] = Object.keys(value).sort(); + }} + }} + }} catch (err) {{ + // Some optional info files may not exist. + }} +}} + +console.log(JSON.stringify(result)); +""" + try: + completed = subprocess.run( + ["node", "--input-type=module", "-e", js], + check=True, + capture_output=True, + text=True, + ) + return json.loads(completed.stdout) + except Exception: + return {} + + +def nice_label(name): + label = re.sub(r"([a-z])([A-Z])", r"\1 \2", name) + label = label.replace("_", " ").replace("-", " ") + label = re.sub(r"\bSsn\b", "SSN", label.title()) + label = label.replace("Dob", "DOB") + return label + + +def apply_legal_field_metadata(field): + name = field["name"] + lower = name.lower() + + # Normalize generated labels. + field["label"] = nice_label(name) + + # Autocomplete fields. + if name == "casePlaintiff": + field["type"] = "autocomplete" + field["list"] = "plaintiffs" + elif name == "caseOpposingCounsel": + field["type"] = "autocomplete" + field["list"] = "opposingCounsel" + elif name == "caseDivisionJudge": + field["type"] = "autocomplete" + field["list"] = "judges" + elif name == "caseFilingAttorney": + field["type"] = "autocomplete" + field["list"] = "filingAttorneys" + elif re.fullmatch(r"debtCollector\d+Name", name): + field["type"] = "autocomplete" + field["list"] = "debtCollectors" + elif lower.endswith("state") or name in {"caseState", "homeState", "client2homeState"}: + field["type"] = "autocomplete" + field["list"] = "states" + elif name == "caseDesignation": + field["type"] = "autocomplete" + field["list"] = "caseDesignations" + + # Long text fields. + if name in {"notes", "caseAppearanceInfo", "paymentOptions", "paymentOptions1", "paymentOptions2", "paymentOptions3", "paymentOptions4", "paymentOptions5"}: + field["type"] = "textarea" + + return field + + +def walk_sections(sections): + for section in sections: + section["collapsible"] = section.get("heading") not in { + "Client Information", + "Case Information", + } + section["defaultOpen"] = section.get("heading") in { + "Client Information", + "Case Information", + } + + section["fields"] = [ + apply_legal_field_metadata(field) + for field in section.get("fields", []) + ] + + for subsection in section.get("subsections", []): + walk_sections([subsection]) + + +def discover_templates(): + templates = [] + + for path in sorted(TEMPLATES_OUT.rglob("*.docx")): + rel = path.relative_to(Path("tools/doc_generator/content/templates")).as_posix() + template_id = re.sub(r"[^a-zA-Z0-9]+", "_", path.stem).strip("_").lower() + + label = path.relative_to(TEMPLATES_OUT).as_posix() + label = label.replace(".docx", "") + label = label.replace("/", " / ") + label = label.replace("_", " ") + + templates.append({ + "id": template_id, + "label": label, + "template": rel, + "outputFilename": f"{template_id}_{{caseNumber}}_{{timestamp_YYYY-MM-DD_HH-mm-ss}}.docx" + }) + + return templates + + +def main(): + if not DRAFT_PROFILE.exists(): + raise SystemExit(f"Missing {DRAFT_PROFILE}. Run review-old-word-doc-generator.py first.") + + draft = json.loads(DRAFT_PROFILE.read_text(encoding="utf-8")) + + lists_raw = run_node_list_extractor() + + lists = { + "plaintiffs": lists_raw.get("casePlaintiffInfo", []), + "opposingCounsel": lists_raw.get("caseOpposingCounselInfo", []) or lists_raw.get("opposingCounselInfo", []), + "judges": lists_raw.get("judgeInfo", []), + "filingAttorneys": lists_raw.get("caseFilingAttorneyInfo", []) or lists_raw.get("filingAttorneyInfo", []), + "debtCollectors": lists_raw.get("debtCollectorInfo", []), + "states": ["MO", "KS"], + "caseDesignations": [ + "Associate Circuit", + "Circuit", + "Limited Actions", + "Small Claims" + ] + } + + sections = draft["sections"] + walk_sections(sections) + + templates = discover_templates() + + profile = { + "id": "legal_profile", + "name": "Legal Profile", + "description": "Consumer debt defense legal profile generated from the legacy word-doc-generator app.", + "template": templates[0]["template"] if templates else "legacy/Canned-Emails.docx", + "outputFilename": "legal_{caseNumber}_{timestamp_YYYY-MM-DD_HH-mm-ss}.docx", + "lists": lists, + "templates": templates, + "sections": sections + } + + OUT_PROFILE.parent.mkdir(parents=True, exist_ok=True) + OUT_PROFILE.write_text(json.dumps(profile, indent=2), encoding="utf-8") + + print(f"Wrote {OUT_PROFILE}") + print(f"Lists: {', '.join(f'{k}={len(v)}' for k, v in lists.items())}") + print(f"Templates: {len(templates)}") + + +if __name__ == "__main__": + main() diff --git a/scripts/build-legal-profile-from-old-html.py b/scripts/build-legal-profile-from-old-html.py new file mode 100644 index 0000000..5c8a2fd --- /dev/null +++ b/scripts/build-legal-profile-from-old-html.py @@ -0,0 +1,337 @@ +import json +import re +import subprocess +from pathlib import Path + +OLD_APP = Path("/mnt/storage/sftp/mcelwain/repository/word-doc-generator") +OLD_PUBLIC = OLD_APP / "public" +OLD_HTML = OLD_PUBLIC / "index.html" + +OUT_PROFILE = Path("tools/doc_generator/content/document_types/legal_profile.json") +TEMPLATES_OUT = Path("tools/doc_generator/content/templates/legacy") + +TAG_RE = re.compile(r'<(input|select|textarea)\b[^>]*>', re.IGNORECASE | re.DOTALL) +ATTR_RE = re.compile(r'([a-zA-Z_:][-a-zA-Z0-9_:.]*)=["\']([^"\']*)["\']') +LABEL_RE = re.compile( + r']*for=["\']([^"\']+)["\'][^>]*>(.*?)', + re.IGNORECASE | re.DOTALL +) + +EXCLUDE_FIELD_NAMES = { + "letterTemplateFile", + "discoTemplateFile", + "excelFile", + "csvFile", + "templateFile", + "file", + "SSNLastFour", + "SSN2LastFour", + "caseAccLastFour", + "casePlaintiffFileName", + "caseAnswerDateString", + "caseAnswerDateYYYY-MM-DD", + "caseAnswerDateYyyyMmDd", + "caseAnswerFiledDateString", + "caseFilingDateString", + "caseDispositionDateString", + "discoCosDateString", + "discoResponseCosDateString", +} + +EXCLUDE_PATTERNS = [ + r"^settlementPaymentDate\d{2}$", + r"^settlementPaymentAmount\d{2}$", + r"^settlementRemaingBalance\d{2}$", + r"^settlementRemainingBalance\d{2}$", + r"^debtCollector\d+AccLastFour$", +] + + +def attrs_from_tag(tag): + return dict(ATTR_RE.findall(tag)) + + +def clean_html_label(value): + value = re.sub(r"<[^>]+>", "", value) + value = value.replace(":", "") + value = re.sub(r"\s+", " ", value).strip() + return value + + +def nice_label(name): + label = re.sub(r"([a-z])([A-Z])", r"\1 \2", name) + label = label.replace("_", " ").replace("-", " ") + label = label.title() + label = label.replace("Ssn", "SSN") + label = label.replace("Dob", "DOB") + label = label.replace("Mm Dd Yyyy", "MM DD YYYY") + return label + + +def should_exclude(name): + if not name: + return True + if name in EXCLUDE_FIELD_NAMES: + return True + if name.endswith("TemplateFile"): + return True + return any(re.match(pattern, name) for pattern in EXCLUDE_PATTERNS) + + +def run_node_list_extractor(): + js = f""" +import {{ pathToFileURL }} from 'url'; + +const files = [ + 'casePlaintiffInfo.js', + 'opposingCounselInfo.js', + 'judgeInfo.js', + 'caseFilingAttorneyInfo.js', + 'filingAttorneyInfo.js', + 'debtCollectorInfo.js' +]; + +const base = {json.dumps(str(OLD_PUBLIC))}; +const result = {{}}; + +for (const file of files) {{ + try {{ + const mod = await import(pathToFileURL(`${{base}}/${{file}}`).href); + for (const [exportName, value] of Object.entries(mod)) {{ + if (value && typeof value === 'object' && !Array.isArray(value)) {{ + result[exportName] = Object.keys(value).sort(); + }} + }} + }} catch (err) {{}} +}} + +console.log(JSON.stringify(result)); +""" + try: + completed = subprocess.run( + ["node", "--input-type=module", "-e", js], + check=True, + capture_output=True, + text=True, + ) + return json.loads(completed.stdout) + except Exception: + return {} + + +def field_type(name, tag_name, attrs): + lower = name.lower() + + if tag_name.lower() == "textarea": + return "textarea" + + html_type = attrs.get("type", "").lower() + if html_type in {"date", "email", "tel", "number"}: + return html_type + + if "date" in lower or lower == "dob": + return "date" + if "email" in lower: + return "email" + if "phone" in lower or "fax" in lower: + return "tel" + if list_name_for_field(name): + return "autocomplete" + + return "text" + + +def list_name_for_field(name): + if name == "casePlaintiff": + return "plaintiffs" + if name == "caseOpposingCounsel": + return "opposingCounsel" + if name == "caseDivisionJudge": + return "judges" + if name == "caseFilingAttorney": + return "filingAttorneys" + if name in {"caseState", "homeState", "client2homeState"}: + return "states" + if name == "caseDesignation": + return "caseDesignations" + if re.fullmatch(r"debtCollector\d+Name", name): + return "debtCollectors" + return None + + +def section_for(name): + lower = name.lower() + + if lower.startswith("client2"): + return "Client 2 Information" + if lower.startswith("client") or lower in { + "ssn", "dob", "alias", "email", + "homeaddress", "homecity", "homestate", "homezip", "homecounty", + "homephone", "cellphone" + }: + return "Client Information" + if lower.startswith("case"): + return "Case Information" + if lower.startswith("disco"): + return "Discovery Information" + if lower.startswith("settlement"): + return "Settlement Information" + if lower.startswith("installment") or lower.startswith("fee") or lower in { + "nameoncard", "cardnumber", "securitycode", "expiration", + "billingaddress", "billingzip" + }: + return "Fee / Payment Information" + if lower.startswith("debtcollector") or name == "numCollectors": + return "Debt Collector Information" + if lower == "notes": + return "Notes" + + return "Other Fields" + + +def discover_templates(): + templates = [] + + for path in sorted(TEMPLATES_OUT.rglob("*.docx")): + rel = path.relative_to(Path("tools/doc_generator/content/templates")).as_posix() + template_id = re.sub(r"[^a-zA-Z0-9]+", "_", path.stem).strip("_").lower() + + label = path.relative_to(TEMPLATES_OUT).as_posix() + label = label.replace(".docx", "") + label = label.replace("/", " / ") + label = label.replace("_", " ") + + templates.append({ + "id": template_id, + "label": label, + "template": rel, + "outputFilename": f"{template_id}_{{caseNumber}}_{{timestamp_YYYY-MM-DD_HH-mm-ss}}.docx" + }) + + return templates + + +html = OLD_HTML.read_text(encoding="utf-8", errors="ignore") + +labels = { + field_id: clean_html_label(label) + for field_id, label in LABEL_RE.findall(html) +} + +fields_seen = [] +field_meta = {} + +for match in TAG_RE.finditer(html): + tag_name = match.group(1) + tag = match.group(0) + attrs = attrs_from_tag(tag) + + name = attrs.get("name") or attrs.get("id") + if should_exclude(name): + continue + + if name not in fields_seen: + fields_seen.append(name) + field_meta[name] = (tag_name, attrs) + +grouped = {} + +for name in fields_seen: + tag_name, attrs = field_meta[name] + ftype = field_type(name, tag_name, attrs) + + field = { + "name": name, + "label": labels.get(name) or nice_label(name), + "type": ftype, + "required": False + } + + list_name = list_name_for_field(name) + if list_name: + field["list"] = list_name + + grouped.setdefault(section_for(name), []).append(field) + +preferred_order = [ + "Client Information", + "Client 2 Information", + "Case Information", + "Discovery Information", + "Settlement Information", + "Fee / Payment Information", + "Debt Collector Information", + "Notes", + "Other Fields", +] + +sections = [] + +for heading in preferred_order: + fields = grouped.get(heading) + if not fields: + continue + + sections.append({ + "heading": heading, + "collapsible": heading not in {"Client Information", "Case Information"}, + "defaultOpen": heading in {"Client Information", "Case Information"}, + "fields": fields + }) + +lists_raw = run_node_list_extractor() + +lists = { + "plaintiffs": lists_raw.get("casePlaintiffInfo", []), + "opposingCounsel": lists_raw.get("caseOpposingCounselInfo", []) or lists_raw.get("opposingCounselInfo", []), + "judges": lists_raw.get("judgeInfo", []), + "filingAttorneys": lists_raw.get("caseFilingAttorneyInfo", []) or lists_raw.get("filingAttorneyInfo", []), + "debtCollectors": lists_raw.get("debtCollectorInfo", []), + "states": ["MO", "KS"], + "caseDesignations": [ + "Associate Circuit", + "Circuit", + "Limited Actions", + "Small Claims" + ] +} + +templates = discover_templates() + +profile = { + "id": "legal_profile", + "name": "Legal Profile", + "description": "Consumer debt defense legal profile based on the legacy app form fields. Additional template fields are calculated at generation time.", + "template": templates[0]["template"] if templates else "legacy/Canned-Emails.docx", + "outputFilename": "legal_{caseNumber}_{timestamp_YYYY-MM-DD_HH-mm-ss}.docx", + "lists": lists, + "templates": templates, + "calculations": [ + { + "script": "legacy_legal", + "runOn": "generate", + "description": "Generate old-template compatible calculated fields.", + "outputsDynamic": { + "settlementSchedule": { + "countField": "settlementInstallmentNo", + "indexFormat": "decimal2", + "maxCount": 120, + "fields": [ + "settlementPaymentDate", + "settlementPaymentAmount", + "settlementRemaingBalance", + "settlementRemainingBalance" + ] + } + } + } + ], + "sections": sections +} + +OUT_PROFILE.write_text(json.dumps(profile, indent=2), encoding="utf-8") + +print(f"Wrote {OUT_PROFILE}") +print(f"Visible HTML fields: {len(fields_seen)}") +for section in sections: + print(f"- {section['heading']}: {len(section['fields'])}") diff --git a/scripts/legacy-excel-datafile.py b/scripts/legacy-excel-datafile.py new file mode 100644 index 0000000..1a18533 --- /dev/null +++ b/scripts/legacy-excel-datafile.py @@ -0,0 +1,106 @@ +import argparse +import csv +import json +import zipfile +import xml.etree.ElementTree as ET +from pathlib import Path + +MAP_FILE = Path("tools/doc_generator/content/excel_maps/legacy_excel_maps.json") + +NS = { + "main": "http://schemas.openxmlformats.org/spreadsheetml/2006/main", + "rel": "http://schemas.openxmlformats.org/officeDocument/2006/relationships", +} + + +def load_map(map_id): + data = json.loads(MAP_FILE.read_text(encoding="utf-8")) + for item in data["maps"]: + if item["id"] == map_id: + return item + raise SystemExit(f"Map not found: {map_id}") + + +def col_row(cell): + col = "".join(ch for ch in cell if ch.isalpha()) + row = "".join(ch for ch in cell if ch.isdigit()) + return col, int(row) + + +def shared_strings(z): + try: + xml = z.read("xl/sharedStrings.xml") + except KeyError: + return [] + + root = ET.fromstring(xml) + values = [] + + for si in root.findall("main:si", NS): + parts = [] + for t in si.findall(".//main:t", NS): + parts.append(t.text or "") + values.append("".join(parts)) + + return values + + +def read_xlsx_cells(path): + values = {} + + with zipfile.ZipFile(path) as z: + strings = shared_strings(z) + + # MVP: first worksheet only. + sheet_xml = z.read("xl/worksheets/sheet1.xml") + root = ET.fromstring(sheet_xml) + + for cell in root.findall(".//main:c", NS): + ref = cell.attrib.get("r") + cell_type = cell.attrib.get("t") + v = cell.find("main:v", NS) + + if not ref or v is None: + continue + + raw = v.text or "" + + if cell_type == "s": + try: + values[ref] = strings[int(raw)] + except Exception: + values[ref] = raw + else: + values[ref] = raw + + return values + + +def export_csv(map_id, xlsx_path, csv_path): + mapping = load_map(map_id) + cells = read_xlsx_cells(xlsx_path) + + row = {} + for field, cell in mapping["fields"].items(): + row[field] = cells.get(cell, "") + + with open(csv_path, "w", newline="", encoding="utf-8") as f: + writer = csv.DictWriter(f, fieldnames=list(mapping["fields"].keys())) + writer.writeheader() + writer.writerow(row) + + print(f"Exported {csv_path}") + + +def main(): + parser = argparse.ArgumentParser(description="Export legacy Excel workbook cells to new app CSV datafile.") + parser.add_argument("map_id", help="Map id from legacy_excel_maps.json") + parser.add_argument("xlsx", help="Legacy Excel workbook to read") + parser.add_argument("csv", help="CSV datafile to write") + args = parser.parse_args() + + export_csv(args.map_id, Path(args.xlsx), Path(args.csv)) + + +if __name__ == "__main__": + main() diff --git a/scripts/rebuild-template-labels.py b/scripts/rebuild-template-labels.py new file mode 100644 index 0000000..f11b9cc --- /dev/null +++ b/scripts/rebuild-template-labels.py @@ -0,0 +1,112 @@ +import json +import re +from pathlib import Path + +PROFILE = Path("tools/doc_generator/content/document_types/legal_profile.json") +TEMPLATES_ROOT = Path("tools/doc_generator/content/templates") +LEGACY_ROOT = TEMPLATES_ROOT / "legacy" + +CATEGORY_RULES = [ + ("discovery", ["disco", "discovery", "interrog", "request-for-production", "rfp", "admission"]), + ("answers", ["answer", "entry-of-appearance"]), + ("settlement", ["settlement", "stip", "payment"]), + ("client", ["client", "engagement", "fee", "contract"]), + ("motions", ["motion", "dismiss", "compel", "summary"]), + ("letters", ["letter", "email", "canned"]), + ("pleadings", ["petition", "complaint", "counterclaim"]), +] + + +def title_case(value): + value = value.replace("_", " ").replace("-", " ") + value = re.sub(r"\s+", " ", value).strip() + + replacements = { + "disco": "discovery", + "rfp": "request for production", + "cos": "certificate of service", + "oc": "opposing counsel", + "atty": "attorney", + "mo": "Missouri", + "ks": "Kansas", + } + + words = [] + for word in value.split(): + lower = word.lower() + words.append(replacements.get(lower, lower)) + + return " ".join(words) + + +def slug(value): + value = title_case(value).lower() + value = re.sub(r"[^a-z0-9]+", "_", value) + return value.strip("_") or "template" + + +def category_for(relative_path): + text = relative_path.as_posix().lower() + for category, needles in CATEGORY_RULES: + if any(needle in text for needle in needles): + return category + return "general" + + +def label_for(path): + rel = path.relative_to(LEGACY_ROOT) + parts = list(rel.parts) + parts[-1] = Path(parts[-1]).stem + + clean_parts = [title_case(part) for part in parts] + return " / ".join(clean_parts) + + +def main(): + data = json.loads(PROFILE.read_text(encoding="utf-8")) + + templates = [] + used_ids = set() + + for path in sorted(LEGACY_ROOT.rglob("*.docx")): + rel_from_templates = path.relative_to(TEMPLATES_ROOT).as_posix() + rel_from_legacy = path.relative_to(LEGACY_ROOT) + + category = category_for(rel_from_legacy) + base_id = f"{category}_{slug(rel_from_legacy.with_suffix('').as_posix())}" + template_id = base_id + + n = 2 + while template_id in used_ids: + template_id = f"{base_id}_{n}" + n += 1 + + used_ids.add(template_id) + + templates.append({ + "id": template_id, + "category": category, + "label": label_for(path), + "template": rel_from_templates, + "outputFilename": f"{template_id}_{{caseNumber}}_{{timestamp_YYYY-MM-DD_HH-mm-ss}}.docx" + }) + + templates.sort(key=lambda item: (item["category"], item["label"])) + + data["templates"] = templates + + if templates: + data["defaultTemplateId"] = templates[0]["id"] + data["template"] = templates[0]["template"] + + PROFILE.write_text(json.dumps(data, indent=2), encoding="utf-8") + + print(f"Updated {PROFILE}") + print(f"Templates: {len(templates)}") + for category in sorted({item["category"] for item in templates}): + count = sum(1 for item in templates if item["category"] == category) + print(f"- {category}: {count}") + + +if __name__ == "__main__": + main() diff --git a/scripts/review-old-word-doc-generator.py b/scripts/review-old-word-doc-generator.py new file mode 100644 index 0000000..2412d08 --- /dev/null +++ b/scripts/review-old-word-doc-generator.py @@ -0,0 +1,251 @@ +import json +import re +from pathlib import Path + +try: + from docx import Document +except Exception: + Document = None + +OLD_APP = Path("/mnt/storage/sftp/mcelwain/repository/word-doc-generator") +OUT_DIR = Path("diagnostics") +OUT_DIR.mkdir(parents=True, exist_ok=True) + +PLACEHOLDER_RE = re.compile(r"\{([A-Za-z0-9_:\-]+)\}") + + +def read_text(path): + try: + return path.read_text(encoding="utf-8", errors="ignore") + except Exception: + return "" + + +def find_placeholders_in_text(text): + return sorted(set(PLACEHOLDER_RE.findall(text))) + + +def find_placeholders_in_docx(path): + if Document is None: + return [] + + found = set() + try: + doc = Document(path) + except Exception: + return [] + + def scan_paragraphs(paragraphs): + for p in paragraphs: + found.update(find_placeholders_in_text(p.text)) + + def scan_table(table): + for row in table.rows: + for cell in row.cells: + scan_paragraphs(cell.paragraphs) + for nested in cell.tables: + scan_table(nested) + + scan_paragraphs(doc.paragraphs) + for table in doc.tables: + scan_table(table) + + return sorted(found) + + +def categorize_field(name): + lower = name.lower() + + if lower.startswith("client2"): + return "Client 2 Information" + if lower.startswith("client") or lower in {"dob", "ssn", "ssnlastfour", "alias", "email"}: + return "Client Information" + if lower.startswith("case"): + return "Case Information" + if lower.startswith("settlement"): + return "Settlement Information" + if lower.startswith("installment") or lower.startswith("fee") or lower in {"nameoncard", "cardnumber", "securitycode", "expiration", "billingaddress", "billingzip"}: + return "Fee / Payment Information" + if lower.startswith("debtcollector"): + return "Debt Collector Information" + if lower.startswith("disco"): + return "Discovery Information" + if lower in {"today", "currentdate", "currentdatemm-dd-yyyy"}: + return "Date Fields" + if lower == "notes": + return "Notes" + + return "Other Fields" + + +def field_type(name): + lower = name.lower() + if "notes" in lower or "appearanceinfo" in lower or "paymentoptions" in lower: + return "textarea" + if "date" in lower or lower in {"dob"}: + return "date" + if "email" in lower: + return "email" + if "phone" in lower or "fax" in lower: + return "tel" + return "text" + + +def make_sections(fields): + grouped = {} + for name in fields: + grouped.setdefault(categorize_field(name), []).append(name) + + preferred_order = [ + "Date Fields", + "Client Information", + "Client 2 Information", + "Case Information", + "Discovery Information", + "Settlement Information", + "Fee / Payment Information", + "Debt Collector Information", + "Notes", + "Other Fields", + ] + + sections = [] + for heading in preferred_order: + names = grouped.get(heading) + if not names: + continue + + sections.append({ + "heading": heading, + "collapsible": heading not in {"Client Information", "Case Information"}, + "defaultOpen": heading in {"Client Information", "Case Information"}, + "fields": [ + { + "name": name, + "label": re.sub(r"([a-z])([A-Z])", r"\1 \2", name).replace("_", " ").strip().title(), + "type": field_type(name), + "required": False + } + for name in sorted(names) + ] + }) + + return sections + + +js_files = sorted(OLD_APP.rglob("*.js")) +html_files = sorted(OLD_APP.rglob("*.html")) +css_files = sorted(OLD_APP.rglob("*.css")) +docx_files = sorted(OLD_APP.rglob("*.docx")) +xlsx_files = sorted(OLD_APP.rglob("*.xlsx")) + +all_text_placeholders = set() +function_hits = [] + +function_terms = { + "DOCX generation": ["docx", "Docxtemplater", "generateDocument", "generateDoc"], + "Excel generation": ["xlsx", "generateExcel", "template.xlsx"], + "vCard generation": ["vcard", "vCard", "BEGIN:VCARD"], + "Calendar / ICS generation": ["ics", "BEGIN:VCALENDAR", "VEVENT"], + "Client folder generation": ["generateClientFolder", "client folder"], + "Settlement calculations": ["settlementPayment", "settlementInstallment", "remainingBalance"], +} + +for path in js_files + html_files: + text = read_text(path) + all_text_placeholders.update(find_placeholders_in_text(text)) + + for label, terms in function_terms.items(): + if any(term in text for term in terms): + function_hits.append((label, str(path.relative_to(OLD_APP)))) + +template_rows = [] +all_template_placeholders = set() + +for path in docx_files: + placeholders = find_placeholders_in_docx(path) + all_template_placeholders.update(placeholders) + template_rows.append({ + "template": str(path.relative_to(OLD_APP)), + "placeholder_count": len(placeholders), + "placeholders": placeholders, + }) + +all_fields = sorted(all_text_placeholders | all_template_placeholders) + +profile = { + "id": "legacy_word_doc_generator", + "name": "Legacy Word Doc Generator Profile", + "description": "Draft profile generated from the legacy word-doc-generator app.", + "template": "REPLACE_WITH_SELECTED_TEMPLATE.docx", + "outputFilename": "legacy_document_{timestamp_YYYY-MM-DD_HH-mm-ss}.docx", + "sourceApp": str(OLD_APP), + "sections": make_sections(all_fields), + "legacyFeatures": sorted(set(label for label, _ in function_hits)), + "templatesFound": template_rows, +} + +profile_path = OUT_DIR / "legacy_word_doc_generator_profile_draft.json" +profile_path.write_text(json.dumps(profile, indent=2), encoding="utf-8") + +report = [] +report.append("# Legacy Word Doc Generator Review") +report.append("") +report.append(f"Source app: `{OLD_APP}`") +report.append("") +report.append("## Files Found") +report.append("") +report.append(f"- JS files: {len(js_files)}") +report.append(f"- HTML files: {len(html_files)}") +report.append(f"- CSS files: {len(css_files)}") +report.append(f"- DOCX templates: {len(docx_files)}") +report.append(f"- XLSX files: {len(xlsx_files)}") +report.append("") +report.append("## Legacy Features Detected") +report.append("") + +if function_hits: + seen = set() + for label, rel in function_hits: + key = (label, rel) + if key in seen: + continue + seen.add(key) + report.append(f"- {label}: `{rel}`") +else: + report.append("- No major legacy feature signatures detected.") + +report.append("") +report.append("## Templates Found") +report.append("") + +if template_rows: + for row in template_rows: + report.append(f"### `{row['template']}`") + report.append(f"- Placeholder count: {row['placeholder_count']}") + if row["placeholders"]: + report.append("- Placeholders:") + for name in row["placeholders"]: + report.append(f" - `{{{name}}}`") + report.append("") +else: + report.append("- No DOCX templates found.") + +report.append("") +report.append("## All Fields Detected") +report.append("") +for name in all_fields: + report.append(f"- `{{{name}}}`") + +report.append("") +report.append("## Draft Profile") +report.append("") +report.append(f"Generated: `{profile_path}`") +report.append("") + +report_path = OUT_DIR / "legacy_word_doc_generator_review.md" +report_path.write_text("\n".join(report), encoding="utf-8") + +print(f"Wrote {report_path}") +print(f"Wrote {profile_path}") +print(f"Detected {len(all_fields)} unique fields/placeholders") diff --git a/tools/doc_generator/content/templates/legacy/Canned-Emails.docx b/tools/doc_generator/content/templates/legacy/Canned-Emails.docx new file mode 100755 index 0000000..2530e0d Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Canned-Emails.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Abbot-Osborn-Jacobs_MO-DB-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Abbot-Osborn-Jacobs_MO-DB-disco.docx new file mode 100755 index 0000000..7faf11f Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Abbot-Osborn-Jacobs_MO-DB-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Allen-Withrow_MO-OC-disco-RFAs.docx b/tools/doc_generator/content/templates/legacy/Discovery/Allen-Withrow_MO-OC-disco-RFAs.docx new file mode 100755 index 0000000..65af23e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Allen-Withrow_MO-OC-disco-RFAs.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Allen-Withrow_MO-OC-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Allen-Withrow_MO-OC-disco.docx new file mode 100755 index 0000000..95e3df3 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Allen-Withrow_MO-OC-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-CC.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-CC.docx new file mode 100755 index 0000000..e424209 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-CC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-CC_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-CC_Ryan.docx new file mode 100755 index 0000000..dbcffe6 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-CC_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-Loan.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-Loan.docx new file mode 100755 index 0000000..0980e2e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-Loan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-Loan_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-Loan_Ryan.docx new file mode 100755 index 0000000..c9469ae Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-DB-Loan_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-CC.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-CC.docx new file mode 100755 index 0000000..acc4a59 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-CC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-CC_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-CC_Ryan.docx new file mode 100755 index 0000000..8fca278 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-CC_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-Deficiency.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-Deficiency.docx new file mode 100755 index 0000000..5703658 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-Deficiency.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-Deficiency_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-Deficiency_Ryan.docx new file mode 100755 index 0000000..f620a93 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-KS-disco-OC-Deficiency_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-MO-disco-DB-CC.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-MO-disco-DB-CC.docx new file mode 100755 index 0000000..69e5dba Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-MO-disco-DB-CC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BQ-MO-disco-OC-CC.docx b/tools/doc_generator/content/templates/legacy/Discovery/BQ-MO-disco-OC-CC.docx new file mode 100755 index 0000000..3abdc71 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BQ-MO-disco-OC-CC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Berman-Rabin_MO-OC-CC.docx b/tools/doc_generator/content/templates/legacy/Discovery/Berman-Rabin_MO-OC-CC.docx new file mode 100755 index 0000000..e605872 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Berman-Rabin_MO-OC-CC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Berman-Rabin_MO-OC-Loan-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Berman-Rabin_MO-OC-Loan-disco.docx new file mode 100755 index 0000000..2cac803 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Berman-Rabin_MO-OC-Loan-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco-RFAs.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco-RFAs.docx new file mode 100755 index 0000000..07c6ff7 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco-RFAs.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco-RFAs_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco-RFAs_Ryan.docx new file mode 100755 index 0000000..af739d6 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco-RFAs_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco.docx new file mode 100755 index 0000000..f22ad22 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco_Ryan.docx new file mode 100755 index 0000000..e83eb63 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-DB-CC-disco_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-OC-CC-disco-RFAs.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-OC-CC-disco-RFAs.docx new file mode 100755 index 0000000..e4c1c96 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-OC-CC-disco-RFAs.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-OC-CC-disco-RFAs_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-OC-CC-disco-RFAs_Ryan.docx new file mode 100755 index 0000000..3b691b5 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-OC-CC-disco-RFAs_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-disco - Copy.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-disco - Copy.docx new file mode 100755 index 0000000..e7a1dd3 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-disco - Copy.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-disco.docx new file mode 100755 index 0000000..04046b6 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-disco_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-disco_Ryan.docx new file mode 100755 index 0000000..660d6dd Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittKS-disco_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-DB-CC-disco-RFAs.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-DB-CC-disco-RFAs.docx new file mode 100755 index 0000000..d67da6d Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-DB-CC-disco-RFAs.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-DB-CC-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-DB-CC-disco.docx new file mode 100755 index 0000000..a541eea Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-DB-CC-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-DB-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-DB-disco.docx new file mode 100755 index 0000000..1f0e30a Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-DB-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-OC-CC-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-OC-CC-disco.docx new file mode 100755 index 0000000..ea69c48 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-OC-CC-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-disco-DB-Loan-DRAFT.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-disco-DB-Loan-DRAFT.docx new file mode 100755 index 0000000..3c74fb8 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-disco-DB-Loan-DRAFT.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-disco-DB-Loan-RFAs.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-disco-DB-Loan-RFAs.docx new file mode 100755 index 0000000..b437421 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-disco-DB-Loan-RFAs.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-disco.docx new file mode 100755 index 0000000..1b72561 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/BlittMO-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Burns-Walsh-KS-DB-CC.docx b/tools/doc_generator/content/templates/legacy/Discovery/Burns-Walsh-KS-DB-CC.docx new file mode 100755 index 0000000..c2d8c87 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Burns-Walsh-KS-DB-CC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Burns-Walsh-KS-DB-CC_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/Burns-Walsh-KS-DB-CC_Ryan.docx new file mode 100755 index 0000000..bc0716f Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Burns-Walsh-KS-DB-CC_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Couch-Lambert_KS-OC-CC.docx b/tools/doc_generator/content/templates/legacy/Discovery/Couch-Lambert_KS-OC-CC.docx new file mode 100755 index 0000000..fbca9cb Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Couch-Lambert_KS-OC-CC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Couch-Lambert_KS-OC-CC_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/Couch-Lambert_KS-OC-CC_Ryan.docx new file mode 100755 index 0000000..34418d1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Couch-Lambert_KS-OC-CC_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Couch-Lambert_MO-OC-CC.docx b/tools/doc_generator/content/templates/legacy/Discovery/Couch-Lambert_MO-OC-CC.docx new file mode 100755 index 0000000..cfd5c2b Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Couch-Lambert_MO-OC-CC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Disco-Example-Responses.docx b/tools/doc_generator/content/templates/legacy/Discovery/Disco-Example-Responses.docx new file mode 100755 index 0000000..e585466 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Disco-Example-Responses.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff.docx b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff.docx new file mode 100755 index 0000000..8a7ef82 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_Balance-Inquiry.docx b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_Balance-Inquiry.docx new file mode 100755 index 0000000..306d42f Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_Balance-Inquiry.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_Debt-buyer-Balance-Inquiry_ROGs_RPDs.pdf.docx b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_Debt-buyer-Balance-Inquiry_ROGs_RPDs.pdf.docx new file mode 100755 index 0000000..1f717e9 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_Debt-buyer-Balance-Inquiry_ROGs_RPDs.pdf.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_ROGs-RPDs.docx b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_ROGs-RPDs.docx new file mode 100755 index 0000000..543c41c Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_ROGs-RPDs.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_ROGs-RPDs_Westlake_MO.docx b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_ROGs-RPDs_Westlake_MO.docx new file mode 100755 index 0000000..759cb1d Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Discovery-to-Plaintiff_ROGs-RPDs_Westlake_MO.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Faber-Brand-MO-DB-Auto-Deficiency-RFAs.docx b/tools/doc_generator/content/templates/legacy/Discovery/Faber-Brand-MO-DB-Auto-Deficiency-RFAs.docx new file mode 100755 index 0000000..2a373b9 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Faber-Brand-MO-DB-Auto-Deficiency-RFAs.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Faber-Brand-MO-DB-Loan-RFAs.docx b/tools/doc_generator/content/templates/legacy/Discovery/Faber-Brand-MO-DB-Loan-RFAs.docx new file mode 100755 index 0000000..e1afcd6 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Faber-Brand-MO-DB-Loan-RFAs.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Faber-Brand-MO-DB-Loan.docx b/tools/doc_generator/content/templates/legacy/Discovery/Faber-Brand-MO-DB-Loan.docx new file mode 100755 index 0000000..f9eea4e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Faber-Brand-MO-DB-Loan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/KF-KS-OC-CC.docx b/tools/doc_generator/content/templates/legacy/Discovery/KF-KS-OC-CC.docx new file mode 100755 index 0000000..0584c59 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/KF-KS-OC-CC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/KF-KS-OC-CC_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/KF-KS-OC-CC_Ryan.docx new file mode 100755 index 0000000..41a16b7 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/KF-KS-OC-CC_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-DB.docx b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-DB.docx new file mode 100755 index 0000000..028f6e5 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-DB.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-DB_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-DB_Ryan.docx new file mode 100755 index 0000000..c6a2607 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-DB_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-OC.docx b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-OC.docx new file mode 100755 index 0000000..2e1af78 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-OC_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-OC_Ryan.docx new file mode 100755 index 0000000..5072bff Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-KS-disco-OC_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-MO-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-MO-disco.docx new file mode 100755 index 0000000..e330964 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Mandarich-MO-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco.docx new file mode 100755 index 0000000..0b7a2a1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco_Ryan.docx new file mode 100755 index 0000000..9a6e8c8 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco_w-o-Signature.docx b/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco_w-o-Signature.docx new file mode 100755 index 0000000..7637750 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco_w-o-Signature.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco_w-o-Signature_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco_w-o-Signature_Ryan.docx new file mode 100755 index 0000000..9580a0e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/PRA-KS-disco_w-o-Signature_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/PRA-MO-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/PRA-MO-disco.docx new file mode 100755 index 0000000..f430de1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/PRA-MO-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/PRA-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/PRA-disco.docx new file mode 100755 index 0000000..0678baa Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/PRA-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-DB-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-DB-disco.docx new file mode 100755 index 0000000..d72702e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-DB-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-DB-disco_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-DB-disco_Ryan.docx new file mode 100755 index 0000000..bf3660b Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-DB-disco_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-Loan-OC.docx b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-Loan-OC.docx new file mode 100755 index 0000000..89f0e95 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-Loan-OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-Loan-OC_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-Loan-OC_Ryan.docx new file mode 100755 index 0000000..a67fe62 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-Loan-OC_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-OC-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-OC-disco.docx new file mode 100755 index 0000000..03fef75 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-OC-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-OC-disco_Ryan.docx b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-OC-disco_Ryan.docx new file mode 100755 index 0000000..bf9c79c Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-KS-OC-disco_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Pappas-MO-DB-Consumer-Installment-Loan-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-MO-DB-Consumer-Installment-Loan-disco.docx new file mode 100755 index 0000000..3c8423b Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-MO-DB-Consumer-Installment-Loan-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Pappas-MO-DB-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-MO-DB-disco.docx new file mode 100755 index 0000000..04ebbd8 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-MO-DB-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Pappas-MO-OC-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-MO-OC-disco.docx new file mode 100755 index 0000000..9b2fecd Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Pappas-MO-OC-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Discovery/Southlaw-MO-OC-disco.docx b/tools/doc_generator/content/templates/legacy/Discovery/Southlaw-MO-OC-disco.docx new file mode 100755 index 0000000..8f9edd1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Discovery/Southlaw-MO-OC-disco.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Annual-Credit-Report-Request-Envelope.docx b/tools/doc_generator/content/templates/legacy/Letters/Annual-Credit-Report-Request-Envelope.docx new file mode 100644 index 0000000..95292ab Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Annual-Credit-Report-Request-Envelope.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Annual-Credit-Report-Request-Form.docx b/tools/doc_generator/content/templates/legacy/Letters/Annual-Credit-Report-Request-Form.docx new file mode 100644 index 0000000..83a4202 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Annual-Credit-Report-Request-Form.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Envelope_Client.docx b/tools/doc_generator/content/templates/legacy/Letters/Envelope_Client.docx new file mode 100755 index 0000000..6d1fc65 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Envelope_Client.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Envelope_Client_without_Sender.docx b/tools/doc_generator/content/templates/legacy/Letters/Envelope_Client_without_Sender.docx new file mode 100644 index 0000000..7852f84 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Envelope_Client_without_Sender.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Envelope_OC.docx b/tools/doc_generator/content/templates/legacy/Letters/Envelope_OC.docx new file mode 100644 index 0000000..5a9a508 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Envelope_OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Intake-Cover-Letter_James.docx b/tools/doc_generator/content/templates/legacy/Letters/Intake-Cover-Letter_James.docx new file mode 100755 index 0000000..2fb8fe2 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Intake-Cover-Letter_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Intake-Cover-Letter_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/Intake-Cover-Letter_Ryan.docx new file mode 100755 index 0000000..96f38f1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Intake-Cover-Letter_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Intake_case-expectations-long.docx b/tools/doc_generator/content/templates/legacy/Letters/Intake_case-expectations-long.docx new file mode 100644 index 0000000..878201b Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Intake_case-expectations-long.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Intake_case-expectations.docx b/tools/doc_generator/content/templates/legacy/Letters/Intake_case-expectations.docx new file mode 100644 index 0000000..dcc0f79 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Intake_case-expectations.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Intake_general-information.docx b/tools/doc_generator/content/templates/legacy/Letters/Intake_general-information.docx new file mode 100644 index 0000000..5df41a5 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Intake_general-information.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Intake_welcome-letter.docx b/tools/doc_generator/content/templates/legacy/Letters/Intake_welcome-letter.docx new file mode 100644 index 0000000..51262bc Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Intake_welcome-letter.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Garnishment-Notice_James.docx b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Garnishment-Notice_James.docx new file mode 100755 index 0000000..0cef1af Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Garnishment-Notice_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Garnishment-Notice_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Garnishment-Notice_Ryan.docx new file mode 100755 index 0000000..6343c0b Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Garnishment-Notice_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Missed-Payment_James.docx b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Missed-Payment_James.docx new file mode 100755 index 0000000..ae11b6e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Missed-Payment_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Missed-Payment_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Missed-Payment_Ryan.docx new file mode 100755 index 0000000..27d2c96 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Missed-Payment_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Returned-Check_James.docx b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Returned-Check_James.docx new file mode 100755 index 0000000..e9ac6c7 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Returned-Check_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Returned-Check_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Returned-Check_Ryan.docx new file mode 100755 index 0000000..ff1d6b4 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/Post-Judgment_Returned-Check_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/authorization-disclosure-no-payment.docx b/tools/doc_generator/content/templates/legacy/Letters/authorization-disclosure-no-payment.docx new file mode 100644 index 0000000..7f5a22b Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/authorization-disclosure-no-payment.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/authorization-disclosure.docx b/tools/doc_generator/content/templates/legacy/Letters/authorization-disclosure.docx new file mode 100644 index 0000000..19aaa53 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/authorization-disclosure.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_CJ_Information-Sheet.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_CJ_Information-Sheet.docx new file mode 100644 index 0000000..c1ec0a1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_CJ_Information-Sheet.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_CJ_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_CJ_Ryan.docx new file mode 100755 index 0000000..ff7837e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_CJ_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_CJ_with-interest-costs.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_CJ_with-interest-costs.docx new file mode 100755 index 0000000..24d8693 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_CJ_with-interest-costs.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_James.docx new file mode 100755 index 0000000..1e5b13c Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_Ryan.docx new file mode 100644 index 0000000..8e8fbfb Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_without-enclosures_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_without-enclosures_James.docx new file mode 100755 index 0000000..6e5c354 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_without-enclosures_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_without-enclosures_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_without-enclosures_Ryan.docx new file mode 100644 index 0000000..502fb8b Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB-by-Court_without-enclosures_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB_James.docx new file mode 100755 index 0000000..90086e7 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB_Ryan.docx new file mode 100644 index 0000000..5989d5f Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-DB_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Hardship_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Hardship_James.docx new file mode 100755 index 0000000..944bfe8 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Hardship_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Hardship_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Hardship_Ryan.docx new file mode 100644 index 0000000..05aa96e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Hardship_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_James.docx new file mode 100755 index 0000000..3e3784b Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_Ryan.docx new file mode 100755 index 0000000..198d8df Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_without-enclosures_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_without-enclosures_James.docx new file mode 100755 index 0000000..744791f Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_without-enclosures_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_without-enclosures_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_without-enclosures_Ryan.docx new file mode 100755 index 0000000..0a83546 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-OC-by-Court_without-enclosures_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Trial_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Trial_James.docx new file mode 100755 index 0000000..b3fa8c8 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Trial_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Trial_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Trial_Ryan.docx new file mode 100755 index 0000000..0ec5757 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-Trial_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-generic_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-generic_James.docx new file mode 100755 index 0000000..391a31a Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-generic_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-generic_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-generic_Ryan.docx new file mode 100644 index 0000000..92dc4dc Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP-generic_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP_James.docx new file mode 100755 index 0000000..08fbdd3 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP_Ryan.docx new file mode 100755 index 0000000..6416eb6 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWOP_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWP_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWP_James.docx new file mode 100755 index 0000000..eaf2f1e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWP_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_DWP_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWP_Ryan.docx new file mode 100755 index 0000000..2c20b1f Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_DWP_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_FCRA-Notice-CJ.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_FCRA-Notice-CJ.docx new file mode 100644 index 0000000..2d8696c Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_FCRA-Notice-CJ.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_FCRA-Notice-Rule-17.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_FCRA-Notice-Rule-17.docx new file mode 100644 index 0000000..f216d5e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_FCRA-Notice-Rule-17.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_MO-Traffic-Ticket_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_MO-Traffic-Ticket_James.docx new file mode 100755 index 0000000..d8f4573 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_MO-Traffic-Ticket_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_MO-Traffic-Ticket_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_MO-Traffic-Ticket_Ryan.docx new file mode 100755 index 0000000..9e95bb3 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_MO-Traffic-Ticket_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_PRA-Mutual-Release_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_PRA-Mutual-Release_James.docx new file mode 100755 index 0000000..77b1ab1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_PRA-Mutual-Release_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_PRA-Mutual-Release_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_PRA-Mutual-Release_Ryan.docx new file mode 100755 index 0000000..7cd5c2d Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_PRA-Mutual-Release_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_Rule-17_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_Rule-17_James.docx new file mode 100755 index 0000000..995e7a2 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_Rule-17_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_Rule-17_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_Rule-17_Ryan.docx new file mode 100755 index 0000000..abfb612 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_Rule-17_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP-no-due-date_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP-no-due-date_James.docx new file mode 100755 index 0000000..e8f15c3 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP-no-due-date_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP-no-due-date_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP-no-due-date_Ryan.docx new file mode 100755 index 0000000..787d64f Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP-no-due-date_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP_James.docx new file mode 100755 index 0000000..ca536f5 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP_Ryan.docx new file mode 100755 index 0000000..80a44b1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-DWP_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-Mutual-Release-DWP_James.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-Mutual-Release-DWP_James.docx new file mode 100755 index 0000000..89dc727 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-Mutual-Release-DWP_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-Mutual-Release-DWP_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-Mutual-Release-DWP_Ryan.docx new file mode 100755 index 0000000..5005521 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/closeout_Settlement-Payment-Mutual-Release-DWP_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/payment-receipt_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/payment-receipt_Ryan.docx new file mode 100644 index 0000000..57b6271 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/payment-receipt_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/representation-termination_James.docx b/tools/doc_generator/content/templates/legacy/Letters/representation-termination_James.docx new file mode 100755 index 0000000..099ef0e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/representation-termination_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/representation-termination_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/representation-termination_Ryan.docx new file mode 100755 index 0000000..2b147f2 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/representation-termination_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/unable-to-contact_James.docx b/tools/doc_generator/content/templates/legacy/Letters/unable-to-contact_James.docx new file mode 100755 index 0000000..39692c1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/unable-to-contact_James.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Letters/unable-to-contact_Ryan.docx b/tools/doc_generator/content/templates/legacy/Letters/unable-to-contact_Ryan.docx new file mode 100755 index 0000000..aaee339 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Letters/unable-to-contact_Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_Answer-Account-Stated-DB.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Answer-Account-Stated-DB.docx new file mode 100755 index 0000000..09acaa5 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Answer-Account-Stated-DB.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_Answer.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Answer.docx new file mode 100755 index 0000000..d3c8a2e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Answer.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_Answer_Account-Stated-OC.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Answer_Account-Stated-OC.docx new file mode 100755 index 0000000..ef47c24 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Answer_Account-Stated-OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_EoA-Ryan.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_EoA-Ryan.docx new file mode 100755 index 0000000..d88fcb5 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_EoA-Ryan.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_JOCO_Motion-to-Withdraw.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_JOCO_Motion-to-Withdraw.docx new file mode 100755 index 0000000..30c9ae7 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_JOCO_Motion-to-Withdraw.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_Journal-Entry-DWOP.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Journal-Entry-DWOP.docx new file mode 100755 index 0000000..4b52eaf Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Journal-Entry-DWOP.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_MSAJ.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_MSAJ.docx new file mode 100755 index 0000000..341d500 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_MSAJ.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_Motion-to-File-Out-of-Time.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Motion-to-File-Out-of-Time.docx new file mode 100755 index 0000000..6b51754 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Motion-to-File-Out-of-Time.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_Motion-to-Withdraw.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Motion-to-Withdraw.docx new file mode 100755 index 0000000..1db0609 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Motion-to-Withdraw.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_NoH.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_NoH.docx new file mode 100755 index 0000000..bd67b63 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_NoH.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_Response-to-MSJ_Late-Response_Auto-Deficiency-Blitt.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Response-to-MSJ_Late-Response_Auto-Deficiency-Blitt.docx new file mode 100755 index 0000000..e7635e8 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Response-to-MSJ_Late-Response_Auto-Deficiency-Blitt.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_Response-to-MSJ_Late-Responses-Blitt.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Response-to-MSJ_Late-Responses-Blitt.docx new file mode 100755 index 0000000..3b17f7e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Response-to-MSJ_Late-Responses-Blitt.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/KS_Service_Waiver.docx b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Service_Waiver.docx new file mode 100755 index 0000000..75ef975 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/KS_Service_Waiver.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Account-Stated_Credit-Card_DB.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Account-Stated_Credit-Card_DB.docx new file mode 100755 index 0000000..e45d3a3 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Account-Stated_Credit-Card_DB.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Account-Stated_Credit-Card_OC.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Account-Stated_Credit-Card_OC.docx new file mode 100755 index 0000000..e709c61 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Account-Stated_Credit-Card_OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Account-Stated_Medical_OC.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Account-Stated_Medical_OC.docx new file mode 100755 index 0000000..2426f26 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Account-Stated_Medical_OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Auto-Deficiency_OC.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Auto-Deficiency_OC.docx new file mode 100755 index 0000000..e9033e5 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Auto-Deficiency_OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Credit-Card_OC.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Credit-Card_OC.docx new file mode 100755 index 0000000..d136381 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Credit-Card_OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Payday.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Payday.docx new file mode 100755 index 0000000..182aedd Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Payday.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Promissory-Note_DB.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Promissory-Note_DB.docx new file mode 100755 index 0000000..5f1995c Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Promissory-Note_DB.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Promissory-Note_OC.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Promissory-Note_OC.docx new file mode 100755 index 0000000..687030f Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_ADs_Breach-of-Contract_Promissory-Note_OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Answer-ADs_Account-Stated_Credit-Card_OC.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Answer-ADs_Account-Stated_Credit-Card_OC.docx new file mode 100755 index 0000000..e5212e9 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Answer-ADs_Account-Stated_Credit-Card_OC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-MSAJ.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-MSAJ.docx new file mode 100755 index 0000000..119cf60 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-MSAJ.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-Order-to-Continue-Hearing.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-Order-to-Continue-Hearing.docx new file mode 100755 index 0000000..5cbfd94 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-Order-to-Continue-Hearing.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-Order-to-Continue-Trial.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-Order-to-Continue-Trial.docx new file mode 100755 index 0000000..5a573b2 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-Order-to-Continue-Trial.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-to-Continue-Hearing.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-to-Continue-Hearing.docx new file mode 100755 index 0000000..68ffc4a Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-to-Continue-Hearing.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-to-Continue-Trial.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-to-Continue-Trial.docx new file mode 100755 index 0000000..f5991f7 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Joint-Motion-to-Continue-Trial.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_MSAJ.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_MSAJ.docx new file mode 100755 index 0000000..7790170 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_MSAJ.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-File-Out-of-Time.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-File-Out-of-Time.docx new file mode 100755 index 0000000..a0c8011 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-File-Out-of-Time.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Quash-Garnishment-Exempt-Income.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Quash-Garnishment-Exempt-Income.docx new file mode 100755 index 0000000..1d47fd4 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Quash-Garnishment-Exempt-Income.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Quash-Garnishment.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Quash-Garnishment.docx new file mode 100755 index 0000000..b48384e Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Quash-Garnishment.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Transfer-Venue.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Transfer-Venue.docx new file mode 100755 index 0000000..26a3e28 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Transfer-Venue.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Withdraw_Services-Terminated.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Withdraw_Services-Terminated.docx new file mode 100755 index 0000000..89bba36 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Withdraw_Services-Terminated.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Withdraw_Unable-to-Contact.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Withdraw_Unable-to-Contact.docx new file mode 100755 index 0000000..a019012 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Motion-to-Withdraw_Unable-to-Contact.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Mutual-DWP.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Mutual-DWP.docx new file mode 100755 index 0000000..d39f0be Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Mutual-DWP.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_NoH-to-Plaintiff.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_NoH-to-Plaintiff.docx new file mode 100755 index 0000000..a94b254 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_NoH-to-Plaintiff.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Proposed-Consent-Judgment.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Proposed-Consent-Judgment.docx new file mode 100755 index 0000000..18f2a74 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Proposed-Consent-Judgment.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Proposed-Consent-Judgment_Blitt.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Proposed-Consent-Judgment_Blitt.docx new file mode 100755 index 0000000..4dd18fb Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Proposed-Consent-Judgment_Blitt.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Proposed-Consent-Judgment_Pappas.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Proposed-Consent-Judgment_Pappas.docx new file mode 100755 index 0000000..6e72a40 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Proposed-Consent-Judgment_Pappas.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Rule-17-Structured-Settlement-Memo.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Rule-17-Structured-Settlement-Memo.docx new file mode 100755 index 0000000..4be4303 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Rule-17-Structured-Settlement-Memo.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_SoC.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_SoC.docx new file mode 100755 index 0000000..5a0c0a5 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_SoC.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Traffic_Amended Plea-Agreement.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Traffic_Amended Plea-Agreement.docx new file mode 100755 index 0000000..d3b1b44 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Traffic_Amended Plea-Agreement.docx differ diff --git a/tools/doc_generator/content/templates/legacy/Pleadings/MO_Traffic_Request-for-Plea.docx b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Traffic_Request-for-Plea.docx new file mode 100755 index 0000000..0d072cc Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/Pleadings/MO_Traffic_Request-for-Plea.docx differ diff --git a/tools/doc_generator/content/templates/legacy/authorization-disclosure-no-payment.docx b/tools/doc_generator/content/templates/legacy/authorization-disclosure-no-payment.docx new file mode 100755 index 0000000..7f5a22b Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/authorization-disclosure-no-payment.docx differ diff --git a/tools/doc_generator/content/templates/legacy/authorization-disclosure.docx b/tools/doc_generator/content/templates/legacy/authorization-disclosure.docx new file mode 100755 index 0000000..19aaa53 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/authorization-disclosure.docx differ diff --git a/tools/doc_generator/content/templates/legacy/cert-mailing.docx b/tools/doc_generator/content/templates/legacy/cert-mailing.docx new file mode 100644 index 0000000..8932b1f Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/cert-mailing.docx differ diff --git a/tools/doc_generator/content/templates/legacy/closeout.docx b/tools/doc_generator/content/templates/legacy/closeout.docx new file mode 100755 index 0000000..8fa5d06 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/closeout.docx differ diff --git a/tools/doc_generator/content/templates/legacy/defenses.docx b/tools/doc_generator/content/templates/legacy/defenses.docx new file mode 100755 index 0000000..18d4b59 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/defenses.docx differ diff --git a/tools/doc_generator/content/templates/legacy/dispute-envelopes.docx b/tools/doc_generator/content/templates/legacy/dispute-envelopes.docx new file mode 100644 index 0000000..17e4ec9 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/dispute-envelopes.docx differ diff --git a/tools/doc_generator/content/templates/legacy/entry.docx b/tools/doc_generator/content/templates/legacy/entry.docx new file mode 100755 index 0000000..3691bfc Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/entry.docx differ diff --git a/tools/doc_generator/content/templates/legacy/isc-body.docx b/tools/doc_generator/content/templates/legacy/isc-body.docx new file mode 100644 index 0000000..9a94195 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/isc-body.docx differ diff --git a/tools/doc_generator/content/templates/legacy/letter.docx b/tools/doc_generator/content/templates/legacy/letter.docx new file mode 100644 index 0000000..4df592a Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/letter.docx differ diff --git a/tools/doc_generator/content/templates/legacy/notes.docx b/tools/doc_generator/content/templates/legacy/notes.docx new file mode 100644 index 0000000..529bbf8 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/notes.docx differ diff --git a/tools/doc_generator/content/templates/legacy/retainer.docx b/tools/doc_generator/content/templates/legacy/retainer.docx new file mode 100644 index 0000000..34562fa Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/retainer.docx differ diff --git a/tools/doc_generator/content/templates/legacy/spreadsheets.docx b/tools/doc_generator/content/templates/legacy/spreadsheets.docx new file mode 100644 index 0000000..9fac1bf Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/spreadsheets.docx differ diff --git a/tools/doc_generator/content/templates/legacy/waiver.docx b/tools/doc_generator/content/templates/legacy/waiver.docx new file mode 100755 index 0000000..a140f96 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/waiver.docx differ diff --git a/tools/doc_generator/content/templates/legacy/~$entry.docx b/tools/doc_generator/content/templates/legacy/~$entry.docx new file mode 100644 index 0000000..365acc8 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/~$entry.docx differ diff --git a/tools/doc_generator/content/templates/legacy/~$nned-Emails.docx b/tools/doc_generator/content/templates/legacy/~$nned-Emails.docx new file mode 100644 index 0000000..18ce7e2 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/~$nned-Emails.docx differ diff --git a/tools/doc_generator/content/templates/legacy/~$notes.docx b/tools/doc_generator/content/templates/legacy/~$notes.docx new file mode 100644 index 0000000..6da20a1 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/~$notes.docx differ diff --git a/tools/doc_generator/content/templates/legacy/~$oseout.docx b/tools/doc_generator/content/templates/legacy/~$oseout.docx new file mode 100644 index 0000000..9483271 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/~$oseout.docx differ diff --git a/tools/doc_generator/content/templates/legacy/~$readsheets.docx b/tools/doc_generator/content/templates/legacy/~$readsheets.docx new file mode 100644 index 0000000..f4bc9f6 Binary files /dev/null and b/tools/doc_generator/content/templates/legacy/~$readsheets.docx differ diff --git a/tools/doc_generator/logic/calculations/__init__.py b/tools/doc_generator/logic/calculations/__init__.py new file mode 100644 index 0000000..3532156 --- /dev/null +++ b/tools/doc_generator/logic/calculations/__init__.py @@ -0,0 +1,18 @@ +from tools.doc_generator.logic.calculations.legacy_legal import apply_legacy_legal_calculations + +CALCULATION_HANDLERS = { + "legacy_legal": apply_legacy_legal_calculations, +} + + +def apply_calculations(document_type: dict, data: dict) -> dict: + calculated = dict(data) + + for calculation in document_type.get("calculations", []): + script = calculation.get("script") + handler = CALCULATION_HANDLERS.get(script) + + if handler: + calculated = handler(calculated, calculation) + + return calculated diff --git a/tools/doc_generator/logic/calculations/legacy_legal.py b/tools/doc_generator/logic/calculations/legacy_legal.py new file mode 100644 index 0000000..3fd89ba --- /dev/null +++ b/tools/doc_generator/logic/calculations/legacy_legal.py @@ -0,0 +1,135 @@ +from __future__ import annotations + +from datetime import datetime +from decimal import Decimal, InvalidOperation, ROUND_HALF_UP + +import pendulum + + +def clean_money(value) -> Decimal: + text = str(value or "").replace("$", "").replace(",", "").strip() + if not text: + return Decimal("0") + try: + return Decimal(text) + except InvalidOperation: + return Decimal("0") + + +def clean_int(value) -> int: + try: + return max(0, int(str(value or "0").strip())) + except ValueError: + return 0 + + +def money(value: Decimal) -> str: + value = value.quantize(Decimal("0.01"), rounding=ROUND_HALF_UP) + return f"${value:,.2f}" + + +def parse_date(value): + text = str(value or "").strip() + if not text: + return None + + for fmt in ("YYYY-MM-DD", "MM/DD/YYYY", "MM-DD-YYYY"): + try: + return pendulum.from_format(text, fmt) + except Exception: + pass + + try: + return pendulum.parse(text) + except Exception: + return None + + +def format_date(value) -> str: + if not value: + return "" + return value.format("MMMM Do, YYYY") + + +def add_months(date_value, months: int): + if not date_value: + return None + return date_value.add(months=months) + + +def add_last_four_fields(data: dict) -> dict: + # Existing old-template compatibility. + for key, value in list(data.items()): + if not key.endswith("Account"): + continue + + base = key[:-len("Account")] + digits = "".join(ch for ch in str(value or "") if ch.isdigit()) + data[f"{base}AccLastFour"] = digits[-4:] if len(digits) >= 4 else digits + + ssn = "".join(ch for ch in str(data.get("SSN", "")) if ch.isdigit()) + if ssn: + data["SSNLastFour"] = ssn[-4:] + + ssn2 = "".join(ch for ch in str(data.get("client2SSN", "")) if ch.isdigit()) + if ssn2: + data["SSN2LastFour"] = ssn2[-4:] + + return data + + +def add_case_filename_fields(data: dict) -> dict: + plaintiff = str(data.get("casePlaintiff", "") or "") + data["casePlaintiffFileName"] = plaintiff.replace(" ", "-").replace(",", "").replace(".", "") + return data + + +def add_settlement_schedule(data: dict, calculation: dict) -> dict: + config = (calculation.get("outputsDynamic") or {}).get("settlementSchedule", {}) + + count_field = config.get("countField", "settlementInstallmentNo") + count = clean_int(data.get(count_field)) + + # Safety cap. Old app used many fixed fields; 120 is plenty for MVP. + count = min(count, int(config.get("maxCount", 120))) + + settlement_amount = clean_money(data.get("settlementAmount")) + installment_amount = clean_money(data.get("settlementInstallmentAmount")) + first_payment_date = parse_date(data.get("settlementFirstPaymentDate")) + + if count <= 0: + return data + + if installment_amount == 0 and settlement_amount > 0: + installment_amount = (settlement_amount / Decimal(count)).quantize(Decimal("0.01"), rounding=ROUND_HALF_UP) + + remaining = settlement_amount + + for i in range(count): + suffix = f"{i:02d}" + payment_date = add_months(first_payment_date, i) + + payment = installment_amount + if settlement_amount > 0: + if i == count - 1: + payment = remaining + remaining = max(Decimal("0"), remaining - payment) + + data[f"settlementPaymentDate{suffix}"] = format_date(payment_date) + data[f"settlementPaymentAmount{suffix}"] = money(payment) + data[f"settlementRemaingBalance{suffix}"] = money(remaining) + + # Correct spelling alias for future templates. + data[f"settlementRemainingBalance{suffix}"] = money(remaining) + + return data + + +def apply_legacy_legal_calculations(data: dict, calculation: dict) -> dict: + data = dict(data) + + data = add_last_four_fields(data) + data = add_case_filename_fields(data) + data = add_settlement_schedule(data, calculation) + + return data diff --git a/tools/doc_generator/logic/renderer.py b/tools/doc_generator/logic/renderer.py index 13bdddc..639140a 100644 --- a/tools/doc_generator/logic/renderer.py +++ b/tools/doc_generator/logic/renderer.py @@ -4,6 +4,7 @@ from pathlib import Path from docx import Document from tools.doc_generator.logic.core_fields import merge_core_fields +from tools.doc_generator.logic.calculations import apply_calculations from tools.doc_generator.logic.document_types import get_document_type BASE_DIR = Path(__file__).resolve().parent.parent @@ -11,6 +12,7 @@ CONTENT_DIR = BASE_DIR / "content" TEMPLATES_DIR = CONTENT_DIR / "templates" PROJECT_ROOT = BASE_DIR.parent.parent EXPORTS_DIR = PROJECT_ROOT / "exports" +UPLOADED_TEMPLATES_DIR = PROJECT_ROOT / "inputs" / "uploads" / "templates" def safe_filename(value: str) -> str: @@ -22,17 +24,51 @@ def safe_filename(value: str) -> str: def render_filename(pattern: str, data: dict) -> str: filename = pattern - for key, value in data.items(): filename = filename.replace("{" + key + "}", safe_filename(value)) - return safe_filename(filename) +def choose_template(document_type_id: str, document_type: dict, template_id: str | None): + templates = document_type.get("templates") or [] + + # Uploaded template ids are formatted as uploaded: + if template_id and template_id.startswith("uploaded:"): + filename = safe_filename(template_id.removeprefix("uploaded:")) + path = UPLOADED_TEMPLATES_DIR / document_type_id / filename + return { + "templatePath": path, + "outputFilename": f"{Path(filename).stem}_{{caseNumber}}_{{timestamp_YYYY-MM-DD_HH-mm-ss}}.docx", + } + + selected = None + + if template_id: + selected = next((item for item in templates if item.get("id") == template_id), None) + + if selected is None: + default_id = document_type.get("defaultTemplateId") + selected = next((item for item in templates if item.get("id") == default_id), None) + + if selected is None and templates: + selected = templates[0] + + if selected: + return { + "templatePath": TEMPLATES_DIR / selected["template"], + "outputFilename": selected.get("outputFilename") or document_type.get("outputFilename", f"{document_type_id}.docx"), + } + + return { + "templatePath": TEMPLATES_DIR / document_type["template"], + "outputFilename": document_type.get("outputFilename", f"{document_type_id}.docx"), + } + + def replace_placeholders_in_paragraph(paragraph, data: dict): full_text = "".join(run.text for run in paragraph.runs) - new_text = full_text + for key, value in data.items(): new_text = new_text.replace("{" + key + "}", "" if value is None else str(value)) @@ -58,18 +94,20 @@ def replace_placeholders_in_table(table, data: dict): replace_placeholders_in_table(nested_table, data) -def generate_docx(document_type_id: str, data: dict) -> Path: +def generate_docx(document_type_id: str, data: dict, template_id: str | None = None) -> Path: data = merge_core_fields(data) document_type = get_document_type(document_type_id) + data = apply_calculations(document_type, data) - template_path = TEMPLATES_DIR / document_type["template"] + selected_template = choose_template(document_type_id, document_type, template_id) + template_path = selected_template["templatePath"] if not template_path.exists(): raise FileNotFoundError(f"Template not found: {template_path}") EXPORTS_DIR.mkdir(parents=True, exist_ok=True) - output_pattern = document_type.get("outputFilename", f"{document_type_id}.docx") + output_pattern = selected_template.get("outputFilename") or document_type.get("outputFilename", f"{document_type_id}.docx") output_filename = render_filename(output_pattern, data) if not output_filename.lower().endswith(".docx"): @@ -86,5 +124,4 @@ def generate_docx(document_type_id: str, data: dict) -> Path: replace_placeholders_in_table(table, data) document.save(output_path) - return output_path