Vaibhav84 commited on
Commit
e07a9b8
·
1 Parent(s): 1c8d444
Files changed (2) hide show
  1. DataSetSample.xlsx +0 -0
  2. app.py +256 -2
DataSetSample.xlsx CHANGED
Binary files a/DataSetSample.xlsx and b/DataSetSample.xlsx differ
 
app.py CHANGED
@@ -3,12 +3,13 @@ from fastapi import FastAPI, File, HTTPException, status
3
  from fastapi.responses import JSONResponse
4
  from pydantic import BaseModel
5
  import json
6
- from typing import List, Dict, Any
7
  import pandas as pd
8
  import numpy as np
9
  from sklearn.metrics.pairwise import cosine_similarity
10
  from scipy import sparse
11
- from datetime import datetime
 
12
  import warnings
13
  import os
14
  import logging
@@ -524,3 +525,256 @@ async def get_customer_analysis(customer_id: str):
524
  status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
525
  detail=f"Error processing request: {str(e)}"
526
  )
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
3
  from fastapi.responses import JSONResponse
4
  from pydantic import BaseModel
5
  import json
6
+ from typing import List, Dict, Any, Optional
7
  import pandas as pd
8
  import numpy as np
9
  from sklearn.metrics.pairwise import cosine_similarity
10
  from scipy import sparse
11
+ from datetime import datetime, timedelta
12
+ from statistics import mean
13
  import warnings
14
  import os
15
  import logging
 
525
  status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
526
  detail=f"Error processing request: {str(e)}"
527
  )
528
+ class CardRecommendation(BaseModel):
529
+ name: str
530
+ annual_fee: float
531
+ rewards_rate: float
532
+ benefits: str
533
+
534
+ class InvestmentRecommendation(BaseModel):
535
+ type: str
536
+ risk_level: str
537
+ expected_return: float
538
+ min_investment: float
539
+
540
+ class RealEstateRecommendation(BaseModel):
541
+ type: str
542
+ location: str
543
+ price: float
544
+ monthly_payment: float
545
+ roi_potential: float
546
+
547
+ class FinancialAnalysisResponse(BaseModel):
548
+ monthly_avg_spend: float
549
+ spend_trend: float
550
+ credit_score_range: str
551
+ credit_score_change: str
552
+ investment_potential: float
553
+ spending_categories: List[Dict[str, float]]
554
+ spending_insights: List[str]
555
+ recent_transactions: List[Dict[str, Any]]
556
+ card_recommendations: List[CardRecommendation]
557
+ investment_recommendations: List[InvestmentRecommendation]
558
+ real_estate_recommendations: List[RealEstateRecommendation]
559
+ financial_health_score: int
560
+ action_items: List[str]
561
+
562
+ @app.get("/financial-analysis/{customer_id}", response_model=FinancialAnalysisResponse)
563
+ async def get_financial_analysis(customer_id: str):
564
+ """
565
+ Get comprehensive financial analysis and recommendations for a customer
566
+
567
+ Parameters:
568
+ - customer_id: The ID of the customer
569
+
570
+ Returns:
571
+ - JSON object containing financial analysis and personalized recommendations
572
+ """
573
+ try:
574
+ # Validate customer
575
+ if customer_id not in purchase_history['Customer_Id'].unique():
576
+ raise HTTPException(
577
+ status_code=status.HTTP_404_NOT_FOUND,
578
+ detail="Customer not found"
579
+ )
580
+
581
+ # Get customer profile
582
+ customer_profile = customer_profiles[customer_profiles['Customer_Id'] == customer_id].iloc[0]
583
+ customer_transactions = purchase_history[purchase_history['Customer_Id'] == customer_id]
584
+
585
+ # Calculate basic financial metrics
586
+ current_month_spending = customer_transactions[
587
+ customer_transactions['Purchase_Date'] >= datetime.now() - timedelta(days=30)
588
+ ]['Amount (In Dollars)'].sum()
589
+
590
+ previous_month_spending = customer_transactions[
591
+ (customer_transactions['Purchase_Date'] >= datetime.now() - timedelta(days=60)) &
592
+ (customer_transactions['Purchase_Date'] < datetime.now() - timedelta(days=30))
593
+ ]['Amount (In Dollars)'].sum()
594
+
595
+ monthly_avg_spend = customer_transactions.groupby(
596
+ customer_transactions['Purchase_Date'].dt.to_period('M')
597
+ )['Amount (In Dollars)'].mean().mean()
598
+
599
+ # Calculate spend trend
600
+ spend_trend = ((current_month_spending - previous_month_spending) / previous_month_spending * 100) if previous_month_spending > 0 else 0
601
+
602
+ # Calculate spending categories
603
+ spending_categories = customer_transactions.groupby('Category')['Amount (In Dollars)'].sum().reset_index()
604
+ spending_categories_list = [
605
+ {"category": row['Category'], "amount": float(row['Amount (In Dollars)'])}
606
+ for _, row in spending_categories.iterrows()
607
+ ]
608
+
609
+ # Generate spending insights
610
+ spending_insights = []
611
+
612
+ # Category-based insights
613
+ for category in spending_categories.itertuples():
614
+ category_avg = category.Amount / len(customer_transactions['Purchase_Date'].dt.to_period('M').unique())
615
+ if category_avg > monthly_avg_spend * 0.3:
616
+ spending_insights.append(f"High spending in {category.Category}: ${category_avg:.2f}/month")
617
+
618
+ # Age-based recommendations
619
+ age = customer_profile['Age']
620
+ income = customer_profile['Income per year (in dollars)']
621
+
622
+ # Determine credit score range (simulated based on age and income)
623
+ base_score = min(max((age * 10 + income / 1000) / 2, 300), 850)
624
+ credit_score_range = f"{int(base_score-25)}-{int(base_score+25)}"
625
+ credit_score_change = "↑ improving" if age > 25 and income > 50000 else "stable"
626
+
627
+ # Calculate investment potential (simplified)
628
+ monthly_income = income / 12
629
+ investment_potential = max(0, monthly_income - monthly_avg_spend * 1.2)
630
+
631
+ # Generate recommendations based on age and income
632
+ card_recommendations = []
633
+ investment_recommendations = []
634
+ real_estate_recommendations = []
635
+
636
+ # Credit Card Recommendations
637
+ if income < 50000:
638
+ card_recommendations.append(CardRecommendation(
639
+ name="Cash Back Starter Card",
640
+ annual_fee=0,
641
+ rewards_rate=1.5,
642
+ benefits="No annual fee, 1.5% cash back on all purchases"
643
+ ))
644
+ elif income < 100000:
645
+ card_recommendations.append(CardRecommendation(
646
+ name="Premium Rewards Card",
647
+ annual_fee=95,
648
+ rewards_rate=2.5,
649
+ benefits="Travel insurance, cash back on all purchases, airport lounge access"
650
+ ))
651
+ else:
652
+ card_recommendations.append(CardRecommendation(
653
+ name="Elite Travel Card",
654
+ annual_fee=495,
655
+ rewards_rate=3.0,
656
+ benefits="Comprehensive travel benefits, concierge service, premium insurance"
657
+ ))
658
+
659
+ # Investment Recommendations
660
+ if age < 30:
661
+ investment_recommendations.extend([
662
+ InvestmentRecommendation(
663
+ type="Index Fund",
664
+ risk_level="High",
665
+ expected_return=10.0,
666
+ min_investment=1000.0
667
+ ),
668
+ InvestmentRecommendation(
669
+ type="Tech Growth ETF",
670
+ risk_level="High",
671
+ expected_return=12.0,
672
+ min_investment=2000.0
673
+ )
674
+ ])
675
+ elif age < 50:
676
+ investment_recommendations.extend([
677
+ InvestmentRecommendation(
678
+ type="Balanced Fund",
679
+ risk_level="Medium",
680
+ expected_return=8.0,
681
+ min_investment=5000.0
682
+ ),
683
+ InvestmentRecommendation(
684
+ type="Dividend Growth Stocks",
685
+ risk_level="Medium",
686
+ expected_return=7.0,
687
+ min_investment=10000.0
688
+ )
689
+ ])
690
+ else:
691
+ investment_recommendations.extend([
692
+ InvestmentRecommendation(
693
+ type="Bond Fund",
694
+ risk_level="Low",
695
+ expected_return=5.0,
696
+ min_investment=10000.0
697
+ ),
698
+ InvestmentRecommendation(
699
+ type="Income Fund",
700
+ risk_level="Low",
701
+ expected_return=4.0,
702
+ min_investment=25000.0
703
+ )
704
+ ])
705
+
706
+ # Real Estate Recommendations
707
+ if income > 75000:
708
+ mortgage_capacity = (income * 4) * 0.8 # 80% of 4x annual income
709
+ monthly_payment = (mortgage_capacity * 0.05) / 12 # Simplified mortgage calculation
710
+
711
+ real_estate_recommendations.extend([
712
+ RealEstateRecommendation(
713
+ type="Starter Home",
714
+ location="Suburban Area",
715
+ price=mortgage_capacity,
716
+ monthly_payment=monthly_payment,
717
+ roi_potential=5.0
718
+ )
719
+ ])
720
+
721
+ if income > 150000:
722
+ real_estate_recommendations.append(
723
+ RealEstateRecommendation(
724
+ type="Investment Property",
725
+ location="Urban Center",
726
+ price=mortgage_capacity * 0.7,
727
+ monthly_payment=monthly_payment * 0.7,
728
+ roi_potential=8.0
729
+ )
730
+ )
731
+
732
+ # Calculate financial health score
733
+ savings_ratio = max(0, min(1, (income - monthly_avg_spend * 12) / income))
734
+ diversity_score = len(spending_categories) / 10
735
+ stability_score = min(1, len(customer_transactions) / 100)
736
+
737
+ financial_health_score = int((savings_ratio * 0.4 + diversity_score * 0.3 + stability_score * 0.3) * 100)
738
+
739
+ # Generate action items
740
+ action_items = []
741
+ if savings_ratio < 0.2:
742
+ action_items.append("Increase monthly savings to at least 20% of income")
743
+ if monthly_avg_spend > monthly_income * 0.7:
744
+ action_items.append("Review monthly expenses to reduce spending")
745
+ if len(investment_recommendations) > 0:
746
+ action_items.append(f"Consider investing in {investment_recommendations[0].type}")
747
+
748
+ # Get recent transactions
749
+ recent_transactions = [
750
+ {
751
+ "date": row['Purchase_Date'].strftime('%Y-%m-%d'),
752
+ "amount": float(row['Amount (In Dollars)'])
753
+ }
754
+ for _, row in customer_transactions.sort_values('Purchase_Date', ascending=False).head(10).iterrows()
755
+ ]
756
+
757
+ return {
758
+ "monthly_avg_spend": float(monthly_avg_spend),
759
+ "spend_trend": float(spend_trend),
760
+ "credit_score_range": credit_score_range,
761
+ "credit_score_change": credit_score_change,
762
+ "investment_potential": float(investment_potential),
763
+ "spending_categories": spending_categories_list,
764
+ "spending_insights": spending_insights,
765
+ "recent_transactions": recent_transactions,
766
+ "card_recommendations": card_recommendations,
767
+ "investment_recommendations": investment_recommendations,
768
+ "real_estate_recommendations": real_estate_recommendations,
769
+ "financial_health_score": financial_health_score,
770
+ "action_items": action_items
771
+ }
772
+
773
+ except HTTPException:
774
+ raise
775
+ except Exception as e:
776
+ logger.error(f"Error processing financial analysis for customer {customer_id}: {str(e)}")
777
+ raise HTTPException(
778
+ status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
779
+ detail=f"Error processing request: {str(e)}"
780
+ )