new-site/scripts/document_gen/templates/cpni_wireless_mvno_generator.py
justin f8cd37ac8c Initial commit — Performance West telecom compliance platform
Includes: API (Express/TypeScript), Astro site, Python workers,
document generators, FCC compliance tools, Canada CRTC formation,
Ansible infrastructure, and deployment scripts.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-27 06:54:22 -05:00

273 lines
11 KiB
Python

"""
Generate the FCC CPNI Annual Certification Letter — Wireless MVNO variant.
An MVNO does not own spectrum or a radio-access network; it resells a
host MNO's wireless service under its own brand. The MVNO directly
controls retail billing records, device-ordering records, and customer
support authentication flows. Everything touching the radio network
(location signaling, HLR / HSS attach records) is held by the host MNO
under its own CPNI certification. This variant clarifies the dividing
line and reinforces delegation + flow-down language.
"""
from __future__ import annotations
import logging
from datetime import datetime
from pathlib import Path
from typing import Optional
LOG = logging.getLogger("document_gen.cpni_wireless_mvno")
try:
from docx import Document
from docx.shared import Pt, Inches, RGBColor
from docx.enum.text import WD_ALIGN_PARAGRAPH
except ImportError:
LOG.warning("python-docx not installed — CPNI Wireless MVNO generation unavailable")
Document = None # type: ignore[assignment,misc]
_NAVY = RGBColor(0x1A, 0x27, 0x44) if Document else None
VARIANT_ID = "wireless_mvno"
VARIANT_LABEL = "Wireless (CMRS) — MVNO"
MAX_FORFEITURE_PER_VIOLATION = "$251,322"
MAX_FORFEITURE_CAP = "$2,513,215"
def _sp(p, after=6, before=0):
p.paragraph_format.space_after = Pt(after)
if before:
p.paragraph_format.space_before = Pt(before)
def _h(doc, text):
p = doc.add_paragraph(); r = p.add_run(text)
r.font.size = Pt(12); r.bold = True; r.font.color.rgb = _NAVY
_sp(p, after=4, before=8)
def _b(doc, text, bold=False, size=10):
p = doc.add_paragraph(); p.alignment = WD_ALIGN_PARAGRAPH.LEFT
r = p.add_run(text); r.font.size = Pt(size); r.bold = bold
_sp(p, after=6)
def _cb(doc, text, checked=True):
mark = "\u2611" if checked else "\u2610"
p = doc.add_paragraph()
r = p.add_run(f" {mark} {text}"); r.font.size = Pt(10)
_sp(p, after=3)
def generate_cpni_wireless_mvno(
output_path: str,
entity_name: str,
frn: str = "",
filer_id_499: str = "",
officer_name: str = "",
officer_title: str = "Chief Executive Officer",
complaints_count: int = 0,
complaints_description: str = "",
has_data_broker_inquiries: bool = False,
data_broker_description: str = "",
reporting_year: int = 0,
host_mno_name: str = "",
address_street: str = "",
address_city: str = "",
address_state: str = "",
address_zip: str = "",
contact_email: str = "",
contact_phone: str = "",
breaches: list[dict] | None = None,
**_: dict,
) -> Optional[str]:
if Document is None:
LOG.error("python-docx not installed")
return None
if reporting_year == 0:
reporting_year = datetime.now().year - 1
breaches = breaches or []
host = host_mno_name or "its host Mobile Network Operator"
doc = Document()
for s in doc.sections:
s.top_margin = Inches(1); s.bottom_margin = Inches(1)
s.left_margin = Inches(1.25); s.right_margin = Inches(1.25)
today = datetime.now().strftime("%B %d, %Y")
signer = officer_name or "Authorized Officer"
title = officer_title or "Officer"
tp = doc.add_paragraph(); tp.alignment = WD_ALIGN_PARAGRAPH.CENTER
t = tp.add_run("CPNI Annual Certification Letter")
t.font.size = Pt(14); t.bold = True; t.font.color.rgb = _NAVY
_sp(tp, after=2)
sp = doc.add_paragraph(); sp.alignment = WD_ALIGN_PARAGRAPH.CENTER
s = sp.add_run(
f"Wireless (CMRS) — MVNO \u2014 47 CFR \u00a7 64.2009 "
f"\u2014 Calendar Year {reporting_year}"
)
s.font.size = Pt(10); s.font.color.rgb = RGBColor(0x55, 0x55, 0x55)
_sp(sp, after=8)
_h(doc, "1. Provider Information")
lines = [f"Company Name: {entity_name}", f"Variant: {VARIANT_LABEL}"]
if frn: lines.append(f"FCC Registration Number (FRN): {frn}")
if filer_id_499: lines.append(f"FCC Form 499 Filer ID: {filer_id_499}")
addr = ", ".join(filter(None, [address_street, address_city]))
if address_state or address_zip:
addr += f", {address_state} {address_zip}".strip()
if addr.strip(", "):
lines.append(f"Address: {addr.strip(', ')}")
if contact_phone: lines.append(f"Telephone: {contact_phone}")
if contact_email: lines.append(f"Email: {contact_email}")
lines.append(f"Certifying Officer: {signer}, {title}")
lines.append(f"Host MNO: {host}")
lines.append(f"Date of Filing: {today}")
lines.append(f"Filing Deadline: March 2, {reporting_year + 1}")
_b(doc, "\n".join(lines))
_h(doc, "2. Officer Statement of Personal Knowledge")
_b(doc, (
f"I, {signer}, {title} of {entity_name}, state that I have personal "
f"knowledge of the matters certified herein. I have reviewed "
f"{entity_name}'s CPNI procedures, the CPNI-related portions of "
f"the MVNO wholesale agreement with {host}, and supervisory logs "
f"covering the reporting period."
))
_h(doc, "3. Certification of Compliance")
_b(doc, (
f"Pursuant to 47 CFR \u00a7 64.2009(e), {entity_name} hereby submits "
f"its annual certification of compliance with the CPNI rules at "
f"47 CFR \u00a7\u00a7 64.2001 through 64.2011 for the period "
f"January 1, {reporting_year} through December 31, {reporting_year}."
))
_h(doc, "4. How Our Procedures Ensure Compliance")
_b(doc, (
f"As a Mobile Virtual Network Operator (MVNO) that does not own "
f"spectrum or a radio-access network, {entity_name}'s CPNI "
f"responsibilities divide into (A) CPNI that {entity_name} directly "
f"controls and (B) CPNI that is held, transported, or generated by "
f"{host} and made available to {entity_name} pursuant to the MVNO "
f"agreement. Both are protected."
))
_b(doc, f"(A) CPNI directly controlled by {entity_name}:", bold=True)
_cb(doc, (
"Retail customer records, billing data, plan-change history, and "
"customer-support interaction logs are held in systems owned and "
"administered by {entity_name} and are subject to password-based "
"authentication, opt-in consent for marketing use, quarterly "
"supervisory review, and annual training per 47 CFR \u00a7\u00a7 "
"64.2005\u201364.2010."
).replace("{entity_name}", entity_name))
_cb(doc, (
"SIM / eSIM port-out and device-swap orders received by "
"{entity_name} require multi-factor authentication of the "
"subscriber plus notification to the address of record before the "
"order is submitted to {host} for execution (47 CFR \u00a7 64.2010)."
).replace("{entity_name}", entity_name).replace("{host}", host))
_b(doc, f"(B) CPNI delegated to or held by {host}:", bold=True)
_cb(doc, (
"Radio-access network signaling, HLR / HSS / UDM records, "
"per-device location information, and lawful-intercept records "
"are held by the host MNO and are governed by that host MNO's own "
"CPNI certification and safeguards. {entity_name} does NOT have "
"direct access to these data stores."
).replace("{entity_name}", entity_name))
_cb(doc, (
f"The MVNO wholesale agreement between {entity_name} and {host} "
f"expressly requires {host} to protect all CPNI generated through "
f"{entity_name}'s subscribers consistent with 47 CFR "
f"\u00a7\u00a7 64.2001\u201364.2011, to provide breach notice to "
f"{entity_name} within a commercially reasonable time, and to "
f"limit use of such CPNI to the provision of service to "
f"{entity_name} and its subscribers."
))
_cb(doc, (
f"{entity_name} reviews {host}'s annual CPNI certification and "
f"any published breach notices, and maintains a file of the "
f"current executed MVNO agreement."
))
_h(doc, "5. Customer Complaints")
if complaints_count == 0:
_b(doc, (
f"{entity_name} has NOT received any customer complaints during "
f"the reporting period concerning the unauthorized release or "
f"use of CPNI. Zero (0) complaints were logged."
))
else:
desc = complaints_description or "Each complaint was investigated and resolved."
_b(doc, (
f"{entity_name} HAS received {complaints_count} customer "
f"complaint{'s' if complaints_count != 1 else ''} during the "
f"reporting period. {desc}"
))
_h(doc, "6. Data Broker Inquiries and Pretexting")
if not has_data_broker_inquiries:
_b(doc, (
f"{entity_name} has NOT received any inquiries, communications, "
f"or attempts by data brokers or other unauthorized parties "
f"seeking the unauthorized release of CPNI."
))
else:
desc = data_broker_description or "Each was refused, documented, and escalated."
_b(doc, (
f"{entity_name} HAS received data broker or pretexting-style "
f"inquiries during the reporting period. {desc}"
))
_h(doc, "7. Breach Log Summary")
if not breaches:
_b(doc, (
f"{entity_name} experienced no CPNI breaches during the "
f"reporting period. No 47 CFR \u00a7 64.2011 notifications "
f"were required."
))
else:
_b(doc, (
f"{entity_name} experienced {len(breaches)} CPNI breach"
f"{'es' if len(breaches) != 1 else ''} during the reporting "
f"period; each was reported within 7 business days."
))
_h(doc, "8. Penalties, Truthfulness, and Perjury Acknowledgment")
_b(doc, (
f"{entity_name} and the undersigned acknowledge that CPNI rule "
f"violations may subject the carrier to forfeitures up to "
f"{MAX_FORFEITURE_PER_VIOLATION} per violation and up to "
f"{MAX_FORFEITURE_CAP} for any single act or failure to act."
))
_b(doc, (
"Pursuant to 47 CFR \u00a7 1.17, the undersigned represents that no "
"material factual information has been withheld and all statements "
"are truthful, accurate, and complete."
))
_b(doc, (
"Willful false statements are punishable under Title 18, U.S.C. "
"\u00a7 1001, and by forfeiture under 47 U.S.C. \u00a7 503."
))
_h(doc, "9. Signature of Certifying Officer")
_b(doc, (
"I declare under penalty of perjury under the laws of the United "
"States of America that the foregoing is true and correct."
))
p = doc.add_paragraph(); _sp(p, after=0)
sig = doc.add_paragraph(); sig.add_run("_" * 45).font.size = Pt(10); _sp(sig, after=2)
nm = doc.add_paragraph(); nr = nm.add_run(signer); nr.bold = True
nr.font.size = Pt(10); _sp(nm, after=2)
tpp = doc.add_paragraph(); tpp.add_run(f"{title}, {entity_name}").font.size = Pt(10)
_sp(tpp, after=2)
dp = doc.add_paragraph(); dp.add_run(f"Date: {today}").font.size = Pt(10)
_sp(dp, after=2)
out = Path(output_path)
out.parent.mkdir(parents=True, exist_ok=True)
doc.save(str(out))
LOG.info("CPNI Wireless MVNO certification letter generated: %s", out)
return str(out)