#!/usr/bin/env python3
# -*- coding: utf-8 -*-
import json, sys, os
from collections import defaultdict
W = '/Users/liuxinyuan/Desktop/Hermes输出-工作类'
TS = open(f'{W}/.q3scratch/.ownerfix_ts').read().strip()
BAK = f'{W}/_bak_ownerfix_{TS}/三部门逐月_2026.json'
NEW = f'{W}/数据/三部门逐月_2026.json'
d = json.load(open(NEW, encoding='utf-8'))
b = json.load(open(BAK, encoding='utf-8'))

def cust_by(name, J):
    m = defaultdict(float)
    for c in J.get('customers') or []:
        m[c.get('sales')] += c.get('amt') or 0
    return round(m.get(name, 0), 2)

def sp_by(name, J):
    m = defaultdict(float)
    for r in J.get('salespersons') or []:
        m[r['sp']] += r.get('amt') or 0
    return round(m.get(name, 0), 2)

print('=== 雅为世纪 rows (new) ===')
for c in d['customers']:
    if c.get('cust') == '深圳市雅为世纪科技有限公司':
        print(' ', c)
        assert c['sales'] == '陈溪子', 'NOT 陈溪子!'

print('\n=== 归属额 变更前后 ===')
for nm in ('刘子研', '陈溪子'):
    oc, nc = cust_by(nm, b), cust_by(nm, d)
    os_, ns = sp_by(nm, b), sp_by(nm, d)
    print(f'  {nm}: customers {oc} -> {nc} ({nc-oc:+.2f}) | salespersons {os_} -> {ns} ({ns-os_:+.2f})')
    print(f'       两口径差(客户-销售员) {round(oc-os_,2):+.2f} -> {round(nc-ns,2):+.2f}')

print('\n=== 守恒 ===')
sc = round(sum(c.get('amt') or 0 for c in d['customers']), 2)
sg = round(sum(c.get('amt') or 0 for c in d['customers_grp']), 2)
s25 = round(sum(c.get('amt_2025') or 0 for c in d['customers']), 2)
g25 = round(sum(c.get('amt_2025') or 0 for c in d['customers_grp']), 2)
print(f'  Σcustomers={sc}  Σcustomers_grp={sg}  |  Σamt_2025={s25}  grp_2025={g25}')
assert abs(sc - sg) < 0.05 and abs(s25 - g25) < 0.05

print('\n=== 逐人 diff（其他销售员必须零变化）===')
allsales = {c.get('sales') for c in b['customers']} | {c.get('sales') for c in d['customers']}
allsp = {r['sp'] for r in b['salespersons']} | {r['sp'] for r in d['salespersons']}
changed = []
for nm in sorted(x for x in allsales if x):
    if abs(cust_by(nm, b) - cust_by(nm, d)) > 0.005:
        changed.append(('customers', nm, cust_by(nm, b), cust_by(nm, d)))
for nm in sorted(x for x in allsp if x):
    if abs(sp_by(nm, b) - sp_by(nm, d)) > 0.005:
        changed.append(('salespersons', nm, sp_by(nm, b), sp_by(nm, d)))
for t, nm, o, n in changed:
    print(f'  [{t}] {nm}: {o} -> {n} ({n-o:+.2f})')
others = [x for x in changed if x[1] not in ('刘子研', '陈溪子')]
print('  非 刘子研/陈溪子 的变动条目数:', len(others), '->', others)

print('\n=== customers_grp sales_list/mixed 重建检查 ===')
rows = [c for c in d['customers_grp']]
print('  grp rows:', len(rows), '| mixed rows:', sum(1 for c in rows if c.get('mixed')))
# 雅为世纪无集团 → 出现在 customers_grp 以自身名为 key
yaw = [c for c in rows if c.get('cust') == '深圳市雅为世纪科技有限公司']
for c in yaw:
    print('  ', c)
    assert c['sales_list'] == ['陈溪子'], c['sales_list']
    assert c['mixed'] is False

print('\n=== meta.customer_owner_override ===')
print(json.dumps(d['meta'].get('customer_owner_override'), ensure_ascii=False, indent=1))
print('\nALL ASSERTIONS PASSED')
