# Lesson 8: project - predict late invoice payments and score new invoices into Excel
import pandas as pd, joblib
from sklearn.compose import ColumnTransformer
from sklearn.pipeline import Pipeline
from sklearn.preprocessing import OneHotEncoder
from sklearn.ensemble import RandomForestClassifier
from sklearn.model_selection import train_test_split
from sklearn.metrics import recall_score, precision_score, roc_auc_score

hist = pd.read_csv("invoices.csv")
feats = ["amount", "credit_days", "past_late_count", "customer_size", "invoice_month"]
X, y = hist[feats], hist["paid_late"]
print(f"{len(hist)} past invoices, {y.mean():.1%} paid late")

prep = ColumnTransformer([("cat", OneHotEncoder(handle_unknown="ignore"), ["customer_size"])], remainder="passthrough")
pipe = Pipeline([("prep", prep), ("model", RandomForestClassifier(n_estimators=300, max_depth=6, min_samples_leaf=5, random_state=0))])
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.25, random_state=3, stratify=y)
pipe.fit(X_train, y_train)
prob = pipe.predict_proba(X_test)[:, 1]
print(f"AUC {roc_auc_score(y_test, prob):.3f}, precision {precision_score(y_test, prob >= .5):.1%}, recall {recall_score(y_test, prob >= .5):.1%} at 50%")

pipe.fit(X, y)                                        # final model on all history
joblib.dump(pipe, "late_payment_model.joblib")

new = pd.read_csv("new_invoices.csv")
new["late_risk"] = pipe.predict_proba(new[feats])[:, 1].round(2)
new["action"] = pd.cut(new["late_risk"], [-0.01, 0.3, 0.6, 1], labels=["Normal", "Reminder before due", "Call now"])
new = new.sort_values("late_risk", ascending=False)
new.to_excel("invoice_risk.xlsx", index=False)
print("\nTop 5 risky invoices:")
print(new.head(5)[["invoice_no", "amount", "past_late_count", "late_risk", "action"]].to_string(index=False))
print("\nActions:", new["action"].value_counts().to_dict())
print("Saved invoice_risk.xlsx and late_payment_model.joblib")
