Files
Thijooree-iOS/Thijooree iOS/API/Models/BankModels.swift
T

152 lines
4.4 KiB
Swift

import Foundation
// MARK: - Unified bank data models
// These aggregate MIB, BML, and Fahipay responses into a common schema.
// All types are Codable for cache serialisation and Hashable for use in SwiftUI ForEach.
struct BankAccount: Identifiable, Codable, Hashable {
let id: String // Synthetic: "\(bank)_\(accountNumber)_\(loginTag)"
let bank: String // "MIB" | "BML" | "FAHIPAY"
let profileName: String
let profileType: String
let productCode: String
let accountNumber: String
let accountBriefName: String
let currencyName: String // "MVR" | "USD" | ...
let accountTypeName: String
let availableBalance: Double
let currentBalance: Double
let blockedAmount: Double
let mvrBalance: Double? // Converted balance when currency != MVR
let statusDesc: String
let profileImageHash: String?
let loginTag: String // loginId that owns this account
let profileId: String?
let internalId: String?
var isActive: Bool {
statusDesc.lowercased().contains("active")
}
var formattedAvailableBalance: String {
"\(currencyName) \(Self.balanceFormatter.string(from: NSNumber(value: availableBalance)) ?? "0.00")"
}
private static let balanceFormatter: NumberFormatter = {
let f = NumberFormatter()
f.numberStyle = .decimal
f.minimumFractionDigits = 2
f.maximumFractionDigits = 2
return f
}()
}
struct BankContact: Identifiable, Codable, Hashable {
let id: String // Unique composite across banks
let benefNo: String
let benefName: String
let benefNickName: String?
let benefAccount: String
let benefType: String // "MIB" | "LOCAL" | "SWIFT" | "BML" | "FAHIPAY"
let bankColor: String?
let benefBankName: String?
let bankCode: String?
let benefStatus: String
let transferCyDesc: String?
let customerImgHash: String?
let benefCategoryId: String?
let profileId: String?
let source: String // "MIB" | "BML" | "FAHIPAY"
var displayName: String {
if let nick = benefNickName, !nick.isEmpty { return nick }
return benefName
}
}
struct BankTransaction: Identifiable, Codable, Hashable {
let id: String
let date: Date
let description: String
let amount: Double // Positive = credit, negative = debit
let currency: String
let counterpartyName: String?
let reference: String?
let accountNumber: String
let accountDisplayName: String
let source: String // "MIB" | "BML" | "BML_CARD" | "FAHIPAY"
let iconUrl: String?
var isCredit: Bool { amount >= 0 }
var formattedAmount: String {
let sign = isCredit ? "+" : "-"
let abs = Self.amountFormatter.string(from: NSNumber(value: Swift.abs(amount))) ?? "0.00"
return "\(sign) \(currency) \(abs)"
}
private static let amountFormatter: NumberFormatter = {
let f = NumberFormatter()
f.numberStyle = .decimal
f.minimumFractionDigits = 2
f.maximumFractionDigits = 2
return f
}()
}
struct BankContactCategory: Identifiable, Codable, Hashable {
let id: String
let categoryName: String
let numBenef: Int
let source: String // "MIB" | "FAHIPAY"
}
struct BankNotification: Identifiable, Codable, Hashable {
let id: String
let title: String
let body: String
let date: Date
var isRead: Bool
let source: String
}
// MARK: - Transfer
struct TransferResult: Codable {
let success: Bool
let transactionId: String?
let reference: String?
let date: Date?
let errorMessage: String?
}
struct TransferReceiptData: Sendable, Equatable {
let fromAccountNumber: String
let fromBankName: String
let toAccountNumber: String
let toAccountName: String
let amount: Double
let currency: String
let reference: String
let date: String
let message: String
}
struct RecentPick: Identifiable, Codable, Hashable {
let id: String
let benefName: String
let benefAccount: String
let transferNetwork: String // TransferNetwork.rawValue
let bankName: String?
let lastUsed: Date
}
// MARK: - Connectivity
enum ConnectivityError: String, CaseIterable, Codable {
case noInternet = "NO_INTERNET"
case mib = "MIB"
case bml = "BML"
case fahipay = "FAHIPAY"
}