import json,collections,unicodedata
|
from pathlib import Path
|
import xml.etree.ElementTree as ET
|
from decimal import Decimal
|
P=Path('scripts/quotation-import')
|
plan=json.loads((P/'local-plan.json').read_text(encoding='utf-8'))
|
db=ET.parse(P/'remote-snapshot.xml')
|
def rows(tag):return [{e.tag:e.text or '' for e in x} for x in db.findall('./'+tag+'/row')]
|
norm=lambda v:unicodedata.normalize('NFKC',v).casefold().strip()
|
materials={x['code']:x for x in rows('materials')}
|
units={x['name'].strip():x for x in rows('units')}
|
customers=collections.defaultdict(list)
|
for x in rows('customers'):
|
if x['deleted']=='0':customers[norm(x['name'])].append(x)
|
owners=[x for x in rows('users') if x['username']=='zhuli']
|
assert len(owners)==1 and owners[0]['nickname'].strip()=='朱莉' and owners[0]['status']=='0'
|
owner=owners[0]
|
new={x['code']:x for x in plan['new_products']}
|
matched=set();created=set()
|
for q in plan['quotes']:
|
matches=customers[norm(q['customer'])]
|
assert len(matches)<=1,(q['customer'],matches)
|
if matches:
|
q['customer']=matches[0]['name'];matched.add(q['customer'])
|
assert matches[0]['owner_user_id']==owner['id'],('Existing customer owner differs',q['customer'])
|
else:created.add(q['customer'])
|
for x in q['items']:
|
if x['name']=='黑果枸杞' and x['specification']=='120克(4g/罐×30)':
|
candidate=materials['TC0020']
|
assert '黑果枸杞' in candidate['name'] and '120' in (candidate['name']+candidate['specification'])
|
x['item_code']='TC0020'
|
code=x['item_code'];unit=units[x['unit']]
|
x['item_unit_id']=int(unit['id'])
|
if code in materials:
|
m=materials[code];assert m['status']=='0'
|
x.update(item_id=int(m['id']),item_name=m['name'],expected_base_unit=int(m['unit_measure_id']))
|
else:
|
assert code in new,code
|
x.update(item_id=0,expected_base_unit=int(unit['id']))
|
new[code]['unit_id']=int(unit['id'])
|
needed={x['item_code'] for q in plan['quotes'] for x in q['items'] if not x['item_id']}
|
plan['new_products']=[x for code,x in new.items() if code in needed]
|
plan.update(target='remote',owner_remote_id=int(owner['id']),matched_customers=len(matched),new_customers=len(created))
|
assert len(plan['quotes'])==345 and sum(len(q['items']) for q in plan['quotes'])==1702
|
assert sum(Decimal(q['total']) for q in plan['quotes'])==Decimal('15392805.71')
|
(P/'remote-plan.json').write_text(json.dumps(plan,ensure_ascii=False,indent=2),encoding='utf-8')
|
print('Remote prepared: 345 quotes, 1702 lines;',len(matched),'existing customers,',len(created),'new customers,',len(needed),'new products; owner',owner['username'],owner['id'])
|