I am trying to create a function in Swift that accepts an integer as a param and returns a double in the locale currency e.g:
input : 1250
output : £12.50
input: 12500
output: £125.00
I noticed there is a third party library that supports this but unfortunately the repo is archived. The type of units used is the smallest type of currency which is minorUnits.
Network Call
/// GET - Retrive a feed of transactions during a certain period
static func get(accountUID: String, categoryUID: String, queryStartDate: String, queryEndDate: String , completionHandler: @escaping ([FeedItem], Error?) -> Void) {
let sessionObject : URLSession = URLSession.shared
let taskObject = sessionObject.dataTask(with: URLS().feedURLObject(accountUID,categoryUID,queryStartDate,queryEndDate)) { (Data, Response, Error) in
guard Error == nil else {
return
}
guard let Data = Data else {
return
}
do {
let feed = try JSONDecoder().decode(Feed.self, from: Data).feedItems.filter({ (item) -> Bool in
item.direction == Direction.out
})
completionHandler(feed, nil)
} catch let error {
print(error.localizedDescription)
}
}
taskObject.resume()
}
Model Feed Struct Amount
struct Amount: Codable {
let currency: Currency
let minorUnits: Int}
Single Item JSON response
FeedItem(feedItemUid: "0651afe9-f568-4623-ad26-31974e26015c", categoryUid: "a68f9445-4d59-44e5-9c3f-dce2df0f53d2", amount: Banking_App.Amount(currency: Banking_App.Currency.gbp, minorUnits: 551), sourceAmount: Banking_App.Amount(currency: Banking_App.Currency.gbp, minorUnits: 551), direction: Banking_App.Direction.out, updatedAt: "2020-02-04T14:09:49.072Z", transactionTime: "2020-02-04T14:09:48.743Z", settlementTime: "2020-02-04T14:09:48.992Z", source: Banking_App.Source.fasterPaymentsOut, status: Banking_App.Status.settled, counterPartyType: Banking_App.CounterPartyType.payee, counterPartyUid: Optional("fed4d40b-9ccc-411d-81c7-870164876d04"), counterPartyName: Banking_App.CounterPartyName.mickeyMouse, counterPartySubEntityUid: Optional("d6d444c0-942f-4f85-b076-d30c2f745a6f"), counterPartySubEntityName: Banking_App.CounterPartySubEntityName.ukAccount, counterPartySubEntityIdentifier: "204514", counterPartySubEntitySubIdentifier: "00000825", reference: Banking_App.Reference.externalPayment, country: Banking_App.Country.gb, spendingCategory: Banking_App.SpendingCategory.payments)
Thanks
Currency codes are defined in the standard ISO 4217 and as part of the standard is the number of decimal digits used for each currency and since swift's NumberFormatter has a style for this ISO standard we can use it for this case.
Create an instance and set the style
let currencyFormatter = NumberFormatter()
currencyFormatter.numberStyle = .currencyISOCode
Set the currency code
currencyFormatter.currencyCode = "SEK"
Now currencyFormatter.minimumFractionDigit
and currencyFormatter.maximumFractionDigits
will both contain the number of decimals define for the given currency
So now we can put this together in a function for instance
func convertMinorUnits(_ units: Int, currencyCode: String) -> Decimal {
let currencyFormatter = NumberFormatter()
currencyFormatter.numberStyle = .currencyISOCode
currencyFormatter.currencyCode = currencyCode.uppercased()
return Decimal(units) / pow(10, currencyFormatter.minimumFractionDigits)
}
example
print(convertMinorUnits(551, currencyCode: "GBP")
5.51
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With