Skip to content

Commit ec308e7

Browse files
perf(rates): avoid vec allocation in fallback source list
1 parent 547b12f commit ec308e7

1 file changed

Lines changed: 18 additions & 17 deletions

File tree

crates/portal-rates/src/lib.rs

Lines changed: 18 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ struct FiatUnit {
6969
// country: Option<String>,
7070
}
7171

72-
#[derive(Debug, Deserialize, Clone, PartialEq, Eq, Hash)]
72+
#[derive(Debug, Deserialize, Clone, Copy, PartialEq, Eq, Hash)]
7373
#[cfg_attr(feature = "bindings", derive(uniffi::Enum))]
7474
enum Source {
7575
Yadio,
@@ -267,30 +267,33 @@ impl MarketAPI {
267267
Ok(Some(parsed))
268268
}
269269

270-
fn fallback_sources(primary: &Source) -> Vec<Source> {
270+
fn fallback_sources(primary: &Source) -> &'static [Source] {
271+
const KRAKEN_FALLBACKS: [Source; 2] = [Source::CoinGecko, Source::CoinDesk];
272+
const COINGECKO_FALLBACKS: [Source; 2] = [Source::Kraken, Source::CoinDesk];
273+
const YADIO_FALLBACKS: [Source; 2] = [Source::CoinGecko, Source::YadioConvert];
274+
const COINGECKO_ONLY_FALLBACKS: [Source; 1] = [Source::CoinGecko];
275+
271276
match primary {
272-
Source::Kraken => vec![Source::CoinGecko, Source::CoinDesk],
273-
Source::CoinGecko => vec![Source::Kraken, Source::CoinDesk],
274-
Source::Yadio => vec![Source::CoinGecko, Source::YadioConvert],
275-
Source::Exir => vec![Source::CoinGecko],
277+
Source::Kraken => &KRAKEN_FALLBACKS,
278+
Source::CoinGecko => &COINGECKO_FALLBACKS,
279+
Source::Yadio => &YADIO_FALLBACKS,
280+
Source::Exir => &COINGECKO_ONLY_FALLBACKS,
276281
Source::YadioConvert
277282
| Source::Coinpaprika
278283
| Source::Bitstamp
279284
| Source::Coinbase
280285
| Source::BNR
281-
| Source::CoinDesk => vec![Source::CoinGecko],
286+
| Source::CoinDesk => &COINGECKO_ONLY_FALLBACKS,
282287
}
283288
}
284289

285290
async fn resolve_price_with_fallback(
286291
self: Arc<Self>,
287292
unit: &FiatUnit,
288293
) -> Result<(String, Source), RatesError> {
289-
let mut attempts = Vec::with_capacity(1 + Self::fallback_sources(&unit.source).len());
290-
attempts.push(unit.source.clone());
291-
attempts.extend(Self::fallback_sources(&unit.source));
292-
293-
for source in attempts {
294+
for source in std::iter::once(unit.source)
295+
.chain(Self::fallback_sources(&unit.source).iter().copied())
296+
{
294297
match self
295298
.clone()
296299
.fetch_price_for_source(&source, &unit.end_point_key)
@@ -327,11 +330,9 @@ impl MarketAPI {
327330
F: FnMut(&Source, &str) -> Fut,
328331
Fut: std::future::Future<Output = Result<Option<String>, RatesError>>,
329332
{
330-
let mut attempts = Vec::with_capacity(1 + Self::fallback_sources(&unit.source).len());
331-
attempts.push(unit.source.clone());
332-
attempts.extend(Self::fallback_sources(&unit.source));
333-
334-
for source in attempts {
333+
for source in std::iter::once(unit.source)
334+
.chain(Self::fallback_sources(&unit.source).iter().copied())
335+
{
335336
match fetcher(&source, &unit.end_point_key).await {
336337
Ok(Some(price_str)) => return Ok((price_str, source)),
337338
Ok(None) => {}

0 commit comments

Comments
 (0)