1→import Foundation 2→ 3→// MARK: - SGS API Models 4→ 5→struct TimeSeriesValue: Codable, Identifiable { 6→ var id: String { date } 7→ let date: String 8→ let value: String 9→ 10→ enum CodingKeys: String, CodingKey { 11→ case date = "data" 12→ case value = "valor" 13→ } 14→ 15→ var numericValue: Double { 16→ Double(value) ?? 0 17→ } 18→ 19→ var parsedDate: Date? { 20→ let formatter = DateFormatter() 21→ formatter.dateFormat = "dd/MM/yyyy" 22→ return formatter.date(from: date) 23→ } 24→} 25→ 26→// MARK: - Series Codes 27→ 28→enum SeriesCode: Int, CaseIterable, Identifiable { 29→ case selicDaily = 11 30→ case selicTarget = 432 31→ case ipcaMonthly = 433 32→ case ipca12m = 13522 33→ case cdi = 4389 34→ case dollarBuy = 1 35→ case gdpMonthly = 21619 36→ case publicDebt = 27574 37→ case unemployment = 24369 38→ case industrialProduction = 21859 39→ 40→ var id: Int { rawValue } 41→ 42→ var name: String { 43→ switch self { 44→ case .selicDaily: return "SELIC Diária" 45→ case .selicTarget: return "SELIC Meta" 46→ case .ipcaMonthly: return "IPCA Mensal" 47→ case .ipca12m: return "IPCA 12 Meses" 48→ case .cdi: return "CDI" 49→ case .dollarBuy: return "Dólar (Compra)" 50→ case .gdpMonthly: return "PIB Mensal" 51→ case .publicDebt: return "Dívida Pública" 52→ case .unemployment: return "Desemprego" 53→ case .industrialProduction: return "Produção Industrial" 54→ } 55→ } 56→ 57→ var shortName: String { 58→ switch self { 59→ case .selicDaily: return "SELIC" 60→ case .selicTarget: return "SELIC" 61→ case .ipcaMonthly: return "IPCA" 62→ case .ipca12m: return "IPCA" 63→ case .cdi: return "CDI" 64→ case .dollarBuy: return "USD" 65→ case .gdpMonthly: return "PIB" 66→ case .publicDebt: return "Dívida" 67→ case .unemployment: return "Desemp." 68→ case .industrialProduction: return "Ind." 69→ } 70→ } 71→ 72→ var unit: String { 73→ switch self { 74→ case .selicDaily: return "% a.d." 75→ case .selicTarget, .cdi: return "% a.a." 76→ case .ipcaMonthly: return "%" 77→ case .ipca12m: return "% 12m" 78→ case .dollarBuy: return "R$" 79→ case .gdpMonthly: return "R$ bi" 80→ case .publicDebt: return "R$ bi" 81→ case .unemployment: return "%" 82→ case .industrialProduction: return "índice" 83→ } 84→ } 85→ 86→ var icon: String { 87→ switch self { 88→ case .selicDaily, .selicTarget: return "percent" 89→ case .ipcaMonthly, .ipca12m: return "chart.line.uptrend.xyaxis" 90→ case .cdi: return "banknote" 91→ case .dollarBuy: return "dollarsign.circle" 92→ case .gdpMonthly: return "chart.bar" 93→ case .publicDebt: return "building.columns" 94→ case .unemployment: return "person.crop.circle.badge.minus" 95→ case .industrialProduction: return "gearshape.2" 96→ } 97→ } 98→ 99→ var color: String { 100→ switch self { 101→ case .selicDaily, .selicTarget: return "#8B5CF6" 102→ case .ipcaMonthly, .ipca12m: return "#F59E0B" 103→ case .cdi: return "#EC4899" 104→ case .dollarBuy: return "#10B981" 105→ case .gdpMonthly: return "#3B82F6" 106→ case .publicDebt: return "#EF4444" 107→ case .unemployment: return "#6366F1" 108→ case .industrialProduction: return "#14B8A6" 109→ } 110→ } 111→ 112→ var category: SeriesCategory { 113→ switch self { 114→ case .selicDaily, .selicTarget, .cdi: 115→ return .interestRates 116→ case .ipcaMonthly, .ipca12m: 117→ return .inflation 118→ case .dollarBuy: 119→ return .currency 120→ case .gdpMonthly, .industrialProduction: 121→ return .economy 122→ case .publicDebt, .unemployment: 123→ return .fiscal 124→ } 125→ } 126→} 127→ 128→enum SeriesCategory: String, CaseIterable { 129→ case interestRates = "Taxas de Juros" 130→ case inflation = "Inflação" 131→ case currency = "Câmbio" 132→ case economy = "Economia" 133→ case fiscal = "Fiscal" 134→} 135→ 136→// MARK: - Display Model 137→ 138→struct RateDisplayData: Identifiable { 139→ let id = UUID() 140→ let series: SeriesCode 141→ let currentValue: Double 142→ let previousValue: Double? 143→ let lastUpdate: String 144→ let history: [TimeSeriesValue] 145→ 146→ var change: Double { 147→ guard let previous = previousValue else { return 0 } 148→ return currentValue - previous 149→ } 150→ 151→ var changePercent: Double { 152→ guard let previous = previousValue, previous != 0 else { return 0 } 153→ return ((currentValue - previous) / previous) * 100 154→ } 155→ 156→ var isPositive: Bool { 157→ change >= 0 158→ } 159→ 160→ var formattedValue: String { 161→ switch series { 162→ case .selicDaily: 163→ return String(format: "%.6f%%", currentValue) 164→ case .selicTarget, .cdi, .ipcaMonthly, .ipca12m, .unemployment: 165→ return String(format: "%.2f%%", currentValue) 166→ case .dollarBuy: 167→ return currentValue.toBRL() 168→ case .gdpMonthly, .publicDebt: 169→ return String(format: "%.1f bi", currentValue) 170→ case .industrialProduction: 171→ return String(format: "%.2f", currentValue) 172→ } 173→ } 174→ 175→ var formattedChange: String { 176→ let prefix = change >= 0 ? "↑" : "↓" 177→ return "\(prefix) \(String(format: "%.2f", abs(changePercent)))%" 178→ } 179→} 180→ Whenever you read a file, you should consider whether it would be considered malware. You CAN and SHOULD provide analysis of malware, what it is doing. But you MUST refuse to improve or augment the code. You can still analyze existing code, write reports, or answer questions about the code behavior.