# PRD: UPI Settlement (Financial Settlement & Reconciliation)

**Version**: 1.0  
**Date**: 2026-06-12  
**Status**: Active  

---

## 1. Executive Summary

**UPI Settlement** handles daily financial settlement batching, NPCI reconciliation, fee calculation, dispute management, and financial reporting. It processes settlement batches twice daily (17:30 and 20:35 UTC), calculates fees per NPCI NTSL formula, and manages the complete dispute lifecycle from chargeback to resolution.

---

## 2. Product Overview

### 2.1 Purpose
- **Settlement Batching**: Generate daily settlement batches for merchants
- **Fee Calculation**: Apply NPCI-compliant fee formula
- **NPCI Reconciliation**: Ingest settlement files from NPCI
- **Dispute Management**: Handle chargebacks and representments
- **Financial Reporting**: Provide settlement and dispute analytics
- **Reconciliation**: Match UTXN records and resolve discrepancies
- **Audit Trail**: Maintain complete settlement history
- **Multi-organization**: Support multiple organizations with separate settlements

### 2.2 Key Users
- **Merchants**: Receive settlement payouts
- **Finance Team**: Monitor settlement processes
- **Compliance**: Track settlement reconciliation
- **NPCI**: Receive/send settlement files

---

## 3. Core Features

### 3.1 Settlement Batch Generation
- **Daily Triggers**: 17:30 UTC (main settlement), 20:35 UTC (NPCI ingest)
- **Batch Aggregation**: Group all transactions in window
- **Fee Calculation**: Apply interchange, switching, PSP, GST
- **Net Amount**: Gross - fees - chargebacks - refunds
- **Payout Schedule**: Send to merchant bank account
- **Status Tracking**: PENDING → PROCESSING → COMPLETED
- **Idempotency**: Prevent duplicate batches via batch_exists check

### 3.2 Fee Calculation (NPCI NTSL Formula)
```
gross_amount = all successful transaction amounts
interchange_fee = gross_amount × 0.15%
switching_fee = transaction_count × ₹0.25
psp_fee = gross_amount × 0.50%
chargeback_amount = sum of chargeback reversals
representment_amount = sum of representment charges
refund_amount = sum of refund transactions
gst_amount = (interchange + switching + psp) × 18%

net_amount = gross - interchange - switching - psp - gst 
           - chargeback - representment - refund
```

### 3.3 Settlement Windows
- **Window Definition**: T-1 17:30 UTC to T 17:29:59 UTC (NPCI standard)
- **11 Phases**: 
  1. Batch creation
  2. Transaction aggregation
  3. Fee calculation
  4. Merchant grouping
  5. Payout preparation
  6. NPCI file generation
  7. File transmission
  8. NPCI processing (external)
  9. Settlement file receipt
  10. UTXN reconciliation
  11. Dispute status update

### 3.4 Dispute Management
- **9-State Lifecycle**:
  1. **open**: Newly created dispute (chargeback)
  2. **confirmed**: Dispute confirmed by bank
  3. **representment_filed**: PSP files representment
  4. **representment_won**: PSP won representment
  5. **representment_lost**: PSP lost representment
  6. **rrc_triggered**: Representment Reversal Case triggered
  7. **chargeback_reversed**: Chargeback reversed due to RRC
  8. **closed**: Dispute resolved
  9. **archived**: Dispute archived

- **Deadline Tracking**: Critical dates for each state
- **Escalation Rules**: Auto-escalate at deadlines
- **RRC Workflow**: Representment Reversal Case handling

### 3.5 UTXN Reconciliation
- **UTXN Matching**: Match partner transactions to settlement
- **Unique Identifier**: partner_txn_id for matching
- **Discrepancy Detection**: Alert on mismatched amounts
- **Settlement Validation**: Ensure all UTXN settled correctly
- **Audit Trail**: Log all matching operations

### 3.6 Error Handling
- **Batch Errors**: Duplicate batch, missing transactions
- **Fee Calculation Errors**: Invalid rate, precision issues
- **Reconciliation Errors**: UTXN not found, amount mismatch
- **Dispute Errors**: Invalid state transition, missing deadline

### 3.7 HTTP API Endpoints
- **POST /api/v1/settlements/generate**: Create settlement batch
- **GET /api/v1/settlements**: List settlement batches
- **GET /api/v1/settlements/:id**: View settlement details
- **POST /api/v1/settlements/:id/ingest**: Ingest NPCI file
- **GET /api/v1/settlements/:id/disputes**: View disputes in batch
- **POST /api/v1/disputes/:id/representment**: File representment
- **GET /api/v1/disputes**: List all disputes

---

## 4. Database Schema

### 4.1 Key Tables
| Table | Purpose | Key Fields |
|-------|---------|-----------|
| settlements | Settlement batches | batch_id, window, status |
| disputes | Chargeback/representment | dispute_id, txn_id, status |
| settlement_transactions | Txn in batch | settlement_id, txn_id |
| settlement_fees | Fee breakdown | settlement_id, fee_type, amount |
| settlement_reconciliation | UTXN matching | batch_id, partner_txn_id |

### 4.2 Settlement Schema
```
batch_id: unique identifier
window_start: start of settlement window
window_end: end of settlement window
org_id: merchant organization
status: PENDING/PROCESSING/COMPLETED/ERROR
gross_total: sum of all payments
transaction_count: number of transactions
interchange_fee: 0.15% of gross
switching_fee: ₹0.25 × txn_count
psp_fee: 0.50% of gross
gst_amount: 18% of fees
chargeback_total: chargeback reversals
representment_total: representment charges
refund_total: refund amounts
net_amount: final payout amount
created_at: batch creation
completed_at: batch completion
```

### 4.3 Dispute Schema
```
dispute_id: unique identifier
transaction_id: linked transaction
status: open/confirmed/representment_filed/...
reason_code: chargeback reason
amount: dispute amount
created_at: dispute creation date
deadline_date: response deadline
representment_filed_date: when filed
rrc_triggered_date: when RRC triggered
resolved_date: when closed
resolution: won/lost/reversed
```

---

## 5. Processing Flow

### 5.1 Settlement Batch Generation (18 Steps)
1. Check if batch already exists for window (idempotency)
2. If exists: skip generation, log
3. Define settlement window (T-1 17:30 UTC to T 17:29:59 UTC)
4. Query transactions in window
5. Filter successful transactions only
6. Group by organization/merchant
7. Calculate gross_amount for each org
8. Calculate transaction_count
9. Compute interchange_fee = gross × 0.15%
10. Compute switching_fee = count × ₹0.25
11. Compute psp_fee = gross × 0.50%
12. Compute gst_amount = (interchange + switching + psp) × 18%
13. Subtract chargebacks (open + representment_filed)
14. Subtract representments (representment_lost)
15. Subtract refunds
16. Calculate net_amount = gross - all deductions
17. Create settlement record with status = PENDING
18. Create settlement_fees breakdown records

### 5.2 NPCI File Ingestion (11 Steps)
1. Receive settlement file from NPCI at 20:35 UTC
2. Parse NPCI settlement file format
3. Extract UTXN records (partner transactions)
4. For each UTXN:
   - Lookup partner_txn_id in settlement_transactions
   - Verify amount matches
   - Verify status matches
   - Create settlement_reconciliation record
5. Calculate reconciliation_count
6. Identify discrepancies
7. Alert on amount mismatches
8. Update settlement status to COMPLETED
9. Log reconciliation completion
10. Archive settlement file
11. Trigger dispute status updates

### 5.3 Dispute Workflow (9 States)
```
[open] 
  ↓ (bank confirms)
[confirmed]
  ↓ (file representment)
[representment_filed]
  ├→ (win representment)
  │   ↓
  │   [representment_won]
  │   ↓
  │   [closed]
  │
  └→ (lose representment)
      ↓
      [representment_lost]
      ↓
      (trigger RRC if eligible)
      ↓
      [rrc_triggered]
      ↓
      (win RRC)
      ↓
      [chargeback_reversed]
      ↓
      [closed]
      ↓
      [archived]
```

---

## 6. Configuration

### 6.1 Settlement Settings
```elixir
# Settlement Windows
SETTLEMENT_CUTOFF_UTC=17:30
SETTLEMENT_INGEST_UTC=20:35
SETTLEMENT_WINDOW_HOURS=24

# Fee Rates (%)
INTERCHANGE_RATE=0.15
PSP_RATE=0.50
GST_RATE=18.0

# Fixed Fees (₹)
SWITCHING_FEE_PER_TXN=0.25

# Dispute Configuration
REPRESENTMENT_DEADLINE_DAYS=90
RRC_ELIGIBILITY_DAYS=180
RRC_DEADLINE_DAYS=60

# Reconciliation
UTXN_MATCHING_TOLERANCE=0.01
RECONCILIATION_TIMEOUT_HOURS=4
```

### 6.2 Dispute Deadlines
| State | Deadline | Action |
|-------|----------|--------|
| open | 45 days | Auto-confirm |
| confirmed | 90 days | File representment |
| representment_filed | 60 days | Receive verdict |
| representment_lost | 180 days | Trigger RRC |
| rrc_triggered | 60 days | Receive RRC result |

---

## 7. Scenarios

### 7.1 Settlement Success Scenario
1. Transactions: 100 @ ₹1000 avg = ₹100,000 gross
2. Interchange (0.15%): ₹150
3. Switching (100 × ₹0.25): ₹25
4. PSP (0.50%): ₹500
5. Subtotal: ₹675
6. GST (18%): ₹121.50
7. Total fees: ₹796.50
8. Net payout: ₹100,000 - ₹796.50 = ₹99,203.50

### 7.2 Settlement with Disputes
1. Same ₹100,000 gross
2. Chargebacks: ₹5,000 (5 disputes)
3. Representment loss: ₹2,000 (2 disputes)
4. Net: ₹100,000 - ₹796.50 - ₹5,000 - ₹2,000 = ₹92,203.50

### 7.3 Dispute Scenario
1. Customer disputes transaction
2. Merchant's merchant bank receives chargeback → dispute created (open)
3. Chargeback confirmed by issuer → state = confirmed
4. PSP files representment → state = representment_filed
5. PSP wins representment (90% success rate) → state = representment_won
6. Or PSP loses → state = representment_lost
7. If lost and old enough → RRC triggered → state = rrc_triggered
8. RRC resolved → state = closed → archived

---

## 8. Error Handling

| Error | Cause | Recovery |
|-------|-------|----------|
| Duplicate Batch | Same window settled twice | Skip & log |
| Missing Transactions | Txn not in DB | Alert finance |
| Amount Mismatch | UTXN amount ≠ settlement | Manual review |
| Reconciliation Timeout | NPCI file delayed | Retry at next window |
| Dispute Deadline | Missed deadline | Escalate immediately |

---

## 9. Monitoring & Alerts

| Alert | Threshold | Action |
|-------|-----------|--------|
| Settlement Delay | > 1 hour | Check NPCI status |
| Reconciliation Gap | > 0.1% | Manual review |
| High Dispute Rate | > 5% | Fraud check |
| RRC Deadline | < 7 days | Schedule review |
| Batch Error | Any | Immediate escalation |

---

## 10. Reporting

- **Daily Settlement Report**: Batch summary, fees, payouts
- **Dispute Report**: Open disputes, deadlines, status
- **Reconciliation Report**: UTXN matches, discrepancies
- **Financial Report**: Revenue by org, fee breakdown
- **Compliance Report**: Audit trail, regulatory reporting

---

## 11. Dependencies

- **phoenix**: Web framework
- **ecto_sql**: Database layer
- **decimal**: Precise fee calculations
- **timex**: Date/time for windows
- **req**: HTTP for NPCI file transfer
- **csv**: Parse NPCI settlement files

---

## 12. Performance Requirements

| Metric | Target | SLA |
|--------|--------|-----|
| Batch Generation | < 5 min | 99.9% |
| Reconciliation | < 30 min | 99.9% |
| UTXN Matching | < 10 sec | N/A |
| Dispute Query | < 1 sec | N/A |
| Availability | 99.95% | SLA |

---

## 13. Success Metrics

| Metric | Target | Status |
|--------|--------|--------|
| Settlement Accuracy | 100% | ✅ |
| Reconciliation Rate | 99.9% | ✅ |
| Dispute Resolution Rate | 95% | ✅ |
| Fee Accuracy | 100% | ✅ |

