You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

64 lines
2.4 KiB

17 hours ago
# -*- coding: utf-8 -*-
"""票 11 ⑤:API-SUMMARY.md 的 URL 与代码 @*Mapping 对账。
基准 = dump_api_out.txtdump_api.py 现场生成
文档侧提取所有 (GET|POST) + /api/... 组合表格行与行内代码通吃剥查询串后集合比对
用法py -3 -X utf8 .scratch/customer-rework/recon_urls.py
"""
import io
import re
import sys
from pathlib import Path
sys.stdout = io.TextIOWrapper(sys.stdout.buffer, encoding="utf-8")
ROOT = Path(r"e:\code\crm-backend-matt")
DUMP = ROOT / ".scratch" / "customer-rework" / "dump_api_out.txt"
DOC = ROOT / ".scratch" / "customer-module" / "API-SUMMARY.md"
PAIR = re.compile(r"(GET|POST)[^/\n]*?(/api/[A-Za-z0-9/_\-]+)")
def norm(p: str) -> str:
return p.split("?", 1)[0].rstrip("/")
code_set = set()
cur_module = ""
cur_ctrl = ""
# 客户域文档范围:crm-customer 全部 + crm-rule 客户规则族(交接篇 §2.1:其余族勿抄进客户 API-SUMMARY)
RULE_SCOPE_ALLOW = {"CustomerReminderRuleController.java", "CustomerDedupRuleController.java"}
excluded = set()
for line in DUMP.read_text(encoding="utf-8").splitlines():
if line.startswith("######## MODULE"):
cur_module = line.split()[-1]
continue
if line.startswith("==== "):
cur_ctrl = line.split()[1]
continue
m = re.match(r"(GET|POST|PUT|DELETE|ANY)\s+(/api/\S+?)\s\s", line)
if not m or m.group(1) not in ("GET", "POST"):
continue
if cur_module == "crm-rule" and cur_ctrl not in RULE_SCOPE_ALLOW:
excluded.add(f"{cur_ctrl}: {m.group(1)} {norm(m.group(2))}")
continue
code_set.add((m.group(1), norm(m.group(2))))
doc_text = DOC.read_text(encoding="utf-8")
doc_set = set()
for m in PAIR.finditer(doc_text):
doc_set.add((m.group(1), norm(m.group(2))))
missing_in_doc = sorted(code_set - doc_set)
stale_in_doc = sorted(doc_set - code_set)
print(f"code endpoints in customer-domain scope (GET/POST): {len(code_set)}")
print(f"excluded (crm-rule non-customer families, out of doc scope): {len(excluded)}")
print(f"doc endpoints (unique verb+path): {len(doc_set)}")
print(f"--- in code, missing from doc ({len(missing_in_doc)}):")
for v, p in missing_in_doc:
print(f" {v} {p}")
print(f"--- in doc, not in code ({len(stale_in_doc)}):")
for v, p in stale_in_doc:
print(f" {v} {p}")
print("RECONCILE:", "OK zero diff" if not missing_in_doc and not stale_in_doc else "DIFF FOUND")