Files
clientflow_backend/tests/test_v4920_reconciliation_multiple_purchases.py
2026-06-09 22:55:58 +01:00

113 lines
4.5 KiB
Python

"""v4.9.20: fiscal customer identity is not purchase identity."""
import sys
import types
if "sqlalchemy" not in sys.modules:
sqlalchemy = types.ModuleType("sqlalchemy")
sqlalchemy.text = lambda sql: sql
sys.modules["sqlalchemy"] = sqlalchemy
if "app.db" not in sys.modules:
app_db = types.ModuleType("app.db")
app_db.engine = object()
sys.modules["app.db"] = app_db
if "app.action_catalog" not in sys.modules:
action_catalog = types.ModuleType("app.action_catalog")
action_catalog.get_action_config = lambda code: {"route": "rever", "action": code, "action_required": True, "safe_to_post": False}
sys.modules["app.action_catalog"] = action_catalog
from app import reconciliation_service as svc
def _jasmin_doc(id_, external_type, number, date, amount):
return {
"id": id_,
"source_system": "jasmin",
"external_type": external_type,
"title": f"Documento Jasmin · {number}",
"customer_name": "ACZCO BRAGA ENERGY, LDA",
"customer_tax_id": "517249200",
"document_number": number,
"document_date": date,
"amount": amount,
"currency": "EUR",
"operation_suggestions": [],
}
def test_same_company_two_jasmin_quotes_stay_as_two_purchase_candidates(monkeypatch):
monkeypatch.setattr(
svc,
"list_reconciliation_items",
lambda *, status, limit, days: [
_jasmin_doc("quote-154", "jasmin_quotation", "ORC.ORC2026.154", "2026-06-03", "638.60"),
_jasmin_doc("quote-160", "jasmin_quotation", "ORC.ORC2026.160", "2026-06-06", "190.00"),
],
)
candidates = svc.list_reconciliation_process_candidates(status="open", days=7, limit=10)
assert len(candidates) == 2
keys = {candidate["operation_key"] for candidate in candidates}
assert "jasmin_quotation:ORC.ORC2026.154" in keys
assert "jasmin_quotation:ORC.ORC2026.160" in keys
assert {tuple(candidate["item_ids"]) for candidate in candidates} == {("quote-154",), ("quote-160",)}
def test_quote_and_invoice_with_same_amount_and_near_date_can_form_one_purchase(monkeypatch):
monkeypatch.setattr(
svc,
"list_reconciliation_items",
lambda *, status, limit, days: [
_jasmin_doc("quote-154", "jasmin_quotation", "ORC.ORC2026.154", "2026-06-03", "638.60"),
_jasmin_doc("invoice-80", "jasmin_invoice", "FA2026.80", "2026-06-05", "638.60"),
_jasmin_doc("quote-160", "jasmin_quotation", "ORC.ORC2026.160", "2026-06-20", "190.00"),
],
)
candidates = svc.list_reconciliation_process_candidates(status="open", days=30, limit=10)
grouped = {candidate["operation_key"]: set(candidate["item_ids"]) for candidate in candidates}
assert grouped["jasmin_quotation:ORC.ORC2026.154"] == {"quote-154", "invoice-80"}
assert grouped["jasmin_quotation:ORC.ORC2026.160"] == {"quote-160"}
def test_payment_proof_assigns_only_when_order_match_is_unambiguous(monkeypatch):
order_a = {
"id": "sale-279",
"source_system": "odoo",
"external_type": "odoo_sale_order",
"title": "Venda Odoo sem oportunidade · S00279",
"customer_name": "ACZCO BRAGA ENERGY, LDA",
"customer_tax_id": "517249200",
"document_number": "S00279",
"document_date": "2026-06-05",
"amount": "638.60",
"currency": "EUR",
"payload": {"record": {"name": "S00279", "invoice_status": "to invoice"}},
"operation_suggestions": [],
}
order_b = {**order_a, "id": "sale-280", "document_number": "S00280", "amount": "190.00", "payload": {"record": {"name": "S00280", "invoice_status": "to invoice"}}}
proof = {
"id": "proof-279",
"source_system": "email",
"external_type": "payment_proof",
"title": "Comprovativo recebido",
"customer_name": "ACZCO BRAGA ENERGY, LDA",
"customer_tax_id": "517249200",
"document_number": "comprovativo-279",
"document_date": "2026-06-06",
"amount": "638.60",
"currency": "EUR",
"operation_suggestions": [],
}
monkeypatch.setattr(svc, "list_reconciliation_items", lambda *, status, limit, days: [order_a, order_b, proof])
candidates = svc.list_reconciliation_process_candidates(status="open", days=7, limit=10)
grouped = {candidate["operation_key"]: set(candidate["item_ids"]) for candidate in candidates}
assert grouped["odoo_sale_order:S00279"] == {"sale-279", "proof-279"}
assert grouped["odoo_sale_order:S00280"] == {"sale-280"}