-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathmain.py
More file actions
141 lines (118 loc) · 5.35 KB
/
Copy pathmain.py
File metadata and controls
141 lines (118 loc) · 5.35 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
import argparse
import os
import pandas as pd
import json
from datetime import datetime
from tools.llm_client import LLMClient
from tools.logging import system_logger
from agents.ingestion import ingestion_agent
from agents.validation import validation_agent
from agents.approval import approval_agent
from agents.payment import payment_agent
def main(invoice_path):
print(f"\nProcessing Pdf: {os.path.basename(invoice_path)}")
invoice_id = os.path.splitext(os.path.basename(invoice_path))[0].upper()
# 2. Check for duplicates
if is_duplicate_invoice(invoice_id):
error_msg = f"REJECTED: Invoice {invoice_id} has already been processed."
print(f"⚠️ {error_msg}")
# Log the duplicate attempt
log_payload = {
"invoice_id": invoice_id,
"status": "REJECTED",
"reason": "Duplicate Invoice ID",
"timestamp": datetime.now().strftime("%Y-%m-%d %H:%M:%S")
}
system_logger.warning(f"Duplicate attempt: {invoice_id}", extra={'transaction_data': log_payload})
# Update Excel so the audit trail shows the blocked attempt
update_excel_report()
return # Stop the program here
# 3. If NOT a duplicate, proceed with normal processing
llm = LLMClient()
data = ingestion_agent(invoice_path, llm)
data["invoice_id"] = invoice_id
# Showing the raw ID from the PDF
raw_item_names = [i.get('name', 'Unknown') for i in data.get('items', [])]
print(f"Item identified as: {', '.join(raw_item_names)}")
# RUN VALIDATION
v_status, v_meta, v_reason = validation_agent(data, llm)
# Only show "Fixed item name" if validation actually passed or made valid corrections
if v_status and v_meta.get("corrections"):
fixed_names = [c['corrected'] for c in v_meta["corrections"]]
print(f"Fixed item name: {', '.join(fixed_names)}")
# RUN APPROVAL (Only if validation passed)
if v_status:
a_status, a_meta = approval_agent(data, v_status, llm)
final_report = payment_agent(data, a_status, a_meta, v_meta)
else:
# If validation failed, pass the v_reason into the payment agent or report
final_report = payment_agent(data, False, None, v_meta)
# Force the specific reason into the final report so payment_agent doesn't overwrite it
final_report['reason'] = v_reason
# 1. Define the Reason for success if it's missing
if final_report.get('status') == "PAID" and not final_report.get('reason'):
final_report['reason'] = "Transaction approved and processed successfully."
# FINAL FORMATTED OUTPUT
print(f"Invoice ID: {final_report.get('invoice_id')}")
print(f"Status: {final_report.get('status')}")
print(f"Payment_status: {final_report.get('payment_status')}")
# Now this will show the success message or the rejection reason
print(f"Reason: {final_report.get('reason', v_reason)}")
log_payload = {
"invoice_id": final_report.get('invoice_id'),
"vendor": data.get('vendor'),
"amount": data.get('amount'),
"status": final_report.get('status'),
"payment_status": final_report.get('payment_status'),
"reason": final_report.get('reason') # This is now populated for success!
}
# Save to the single JSON file
if final_report.get('status') == "PAID":
system_logger.info(f"Transaction Success: {log_payload['invoice_id']}",
extra={'transaction_data': log_payload})
else:
system_logger.warning(f"Transaction Rejected: {log_payload['invoice_id']}",
extra={'transaction_data': log_payload})
# AUTOMATIC EXCEL UPDATE
update_excel_report()
def update_excel_report():
log_file = 'logs/transaction_history.json'
excel_file = 'logs/audit_report.xlsx'
records = []
if os.path.exists(log_file):
with open(log_file, 'r') as f:
for line in f:
line = line.strip()
if line: # Skip empty lines
try:
records.append(json.loads(line))
except json.JSONDecodeError:
continue # Skip lines that are partially written
if records:
# Convert the list of dictionaries to an Excel table
df = pd.DataFrame(records)
df.to_excel(excel_file, index=False)
print(f"✅ Successfully synced {len(records)} transactions to Excel.")
else:
print("Empty log file. Nothing to export.")
else:
print("Log file does not exist yet.")
def is_duplicate_invoice(invoice_id, log_file='logs/transaction_history.json'):
#"""Checks if the invoice_id already exists in the JSON Lines log file."""
if not os.path.exists(log_file):
return False
with open(log_file, 'r') as f:
for line in f:
try:
record = json.loads(line)
# Check if the stored invoice_id matches the current one
if record.get("invoice_id") == invoice_id:
return True
except json.JSONDecodeError:
continue
return False
if __name__ == "__main__":
parser = argparse.ArgumentParser()
parser.add_argument("--invoice", required=True)
args = parser.parse_args()
main(args.invoice)