import pandas as pd from datetime import datetime from services.contractors import get_contractors def _find_column(df, aliases): for name in aliases: if name in df.columns: return name return None def import_excel(file, conn): contractors = { name: contractor_id for contractor_id, name in get_contractors(conn) } cursor = conn.cursor() df = pd.read_excel(file) required = { "contractor": _find_column(df, ["Контрагент"]), "doc_type": _find_column(df, ["Вид документа", "Тип документа"]), "doc_date": _find_column(df, ["Дата", "Дата документа"]), "doc_number": _find_column(df, ["Номер", "Номер документа"]), "amount": _find_column(df, ["Сумма"]), "state": _find_column(df, ["Состояние ЭДО", "Состояние", "Статус"]), } missing = [key for key, col in required.items() if col is None] if missing: raise ValueError( f"В файле не найдены обязательные колонки: {', '.join(missing)}" ) imported = 0 updated = 0 skipped = 0 now = datetime.now().strftime("%Y-%m-%d %H:%M:%S") for _, row in df.iterrows(): contr = str(row[required["contractor"]]).strip() if contr not in contractors: skipped += 1 continue contractor_id = contractors[contr] doc_type = row[required["doc_type"]] doc_date = row[required["doc_date"]] number = row[required["doc_number"]] summ = row[required["amount"]] state = row[required["state"]] amount = float(summ) if pd.notna(summ) else 0 cursor.execute( """ SELECT id FROM documents_1c WHERE contractor_id = ? AND doc_type = ? AND doc_date = ? AND doc_number = ? AND amount = ? """, ( contractor_id, str(doc_type), str(doc_date), str(number), amount, ), ) document = cursor.fetchone() if document: cursor.execute( """ UPDATE documents_1c SET state = ?, updated_at = ? WHERE id = ? """, (str(state), now, document[0]), ) updated += 1 else: cursor.execute( """ INSERT INTO documents_1c ( contractor_id, doc_type, doc_date, doc_number, amount, state, comment, created_at, updated_at ) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?) """, ( contractor_id, str(doc_type), str(doc_date), str(number), amount, str(state), "", now, now, ), ) imported += 1 conn.commit() return imported, updated, skipped