mirror of
https://github.com/maybe-finance/maybe.git
synced 2025-08-05 13:35:21 +02:00
Multi-Currency Part 2 (#543)
* Support all currencies, handle outside DB * Remove currencies from seed * Fix account balance namespace * Set default currency on authentication * Cache currency instances * Implement multi-currency syncs with tests * Series fallback, passing tests * Fix conflicts * Make value group concrete class that works with currency values * Fix migration conflict * Update tests to expect multi-currency results * Update account list to use group method * Namespace updates * Fetch unknown exchange rates from API * Fix date range bug * Ensure demo data works without external API * Enforce cascades only at DB level
This commit is contained in:
parent
de0cba9fed
commit
110855d077
55 changed files with 1226 additions and 714 deletions
|
@ -1,16 +1,42 @@
|
|||
class ExchangeRate < ApplicationRecord
|
||||
validates :base_currency, :converted_currency, presence: true
|
||||
|
||||
def self.convert(from, to, amount)
|
||||
return amount unless EXCHANGE_RATE_ENABLED
|
||||
|
||||
rate = ExchangeRate.find_by(base_currency: from, converted_currency: to)
|
||||
|
||||
# TODO: Handle the case where the rate is not found
|
||||
if rate.nil?
|
||||
amount # Silently handle the error by returning the original amount
|
||||
else
|
||||
class << self
|
||||
def convert(from, to, amount)
|
||||
rate = ExchangeRate.find_by(base_currency: from, converted_currency: to, date: Date.current)
|
||||
return nil if rate.nil?
|
||||
amount * rate.rate
|
||||
end
|
||||
|
||||
def get_rate(from, to, date)
|
||||
_from = Money::Currency.new(from)
|
||||
_to = Money::Currency.new(to)
|
||||
find_by! base_currency: _from.iso_code, converted_currency: _to.iso_code, date: date
|
||||
rescue
|
||||
logger.warn "Exchange rate not found for #{_from.iso_code} to #{_to.iso_code} on #{date}"
|
||||
nil
|
||||
end
|
||||
|
||||
def get_rate_series(from, to, date_range)
|
||||
where(base_currency: from, converted_currency: to, date: date_range).order(:date)
|
||||
end
|
||||
|
||||
# TODO: Replace with generic provider
|
||||
# See https://github.com/maybe-finance/maybe/pull/556
|
||||
def fetch_rate_from_provider(from, to, date)
|
||||
response = Faraday.get("https://api.synthfinance.com/rates/historical") do |req|
|
||||
req.headers["Authorization"] = "Bearer #{ENV["SYNTH_API_KEY"]}"
|
||||
req.params["date"] = date.to_s
|
||||
req.params["from"] = from
|
||||
req.params["to"] = to
|
||||
end
|
||||
|
||||
if response.success?
|
||||
rates = JSON.parse(response.body)
|
||||
rates.dig("data", "rates", to)
|
||||
else
|
||||
nil
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue