|
54 | 54 | Source,
|
55 | 55 | Vaa,
|
56 | 56 | },
|
57 |
| - std::io::{ |
58 |
| - Cursor, |
59 |
| - Read, |
| 57 | + std::{ |
| 58 | + collections::HashMap, |
| 59 | + io::{ |
| 60 | + Cursor, |
| 61 | + Read, |
| 62 | + }, |
60 | 63 | },
|
61 | 64 | };
|
62 | 65 |
|
@@ -511,6 +514,50 @@ impl Pyth {
|
511 | 514 | })
|
512 | 515 | }
|
513 | 516 |
|
| 517 | + /// Batch version of `get_price`. |
| 518 | + pub fn list_prices( |
| 519 | + &self, |
| 520 | + price_ids: Vec<PriceIdentifier>, |
| 521 | + ) -> HashMap<PriceIdentifier, Option<Price>> { |
| 522 | + self.list_prices_no_older_than(price_ids, self.stale_threshold) |
| 523 | + } |
| 524 | + |
| 525 | + /// Batch version of `get_price_unsafe`. |
| 526 | + pub fn list_prices_unsafe( |
| 527 | + &self, |
| 528 | + price_ids: Vec<PriceIdentifier>, |
| 529 | + ) -> HashMap<PriceIdentifier, Option<Price>> { |
| 530 | + self.list_prices_no_older_than(price_ids, u64::MAX) |
| 531 | + } |
| 532 | + |
| 533 | + /// Batch version of `get_price_no_older_than`. |
| 534 | + pub fn list_prices_no_older_than( |
| 535 | + &self, |
| 536 | + price_ids: Vec<PriceIdentifier>, |
| 537 | + age: Seconds, |
| 538 | + ) -> HashMap<PriceIdentifier, Option<Price>> { |
| 539 | + price_ids |
| 540 | + .into_iter() |
| 541 | + .map(|price_id| { |
| 542 | + if let Some(feed) = self.prices.get(&price_id) { |
| 543 | + let block_timestamp = env::block_timestamp() / 1_000_000_000; |
| 544 | + let price_timestamp = feed.price.publish_time; |
| 545 | + |
| 546 | + // - If Price older than STALENESS_THRESHOLD, set status to Unknown. |
| 547 | + // - If Price newer than now by more than STALENESS_THRESHOLD, set status to Unknown. |
| 548 | + // - Any other price around the current time is considered valid. |
| 549 | + if u64::abs_diff(block_timestamp, price_timestamp.try_into().unwrap()) > age { |
| 550 | + (price_id, None) |
| 551 | + } else { |
| 552 | + (price_id, Some(feed.price)) |
| 553 | + } |
| 554 | + } else { |
| 555 | + (price_id, None) |
| 556 | + } |
| 557 | + }) |
| 558 | + .collect() |
| 559 | + } |
| 560 | + |
514 | 561 | /// EMA version of `get_price`.
|
515 | 562 | pub fn get_ema_price(&self, price_id: PriceIdentifier) -> Option<Price> {
|
516 | 563 | self.get_ema_price_no_older_than(price_id, self.get_stale_threshold())
|
@@ -541,6 +588,50 @@ impl Pyth {
|
541 | 588 | Some(feed.ema_price)
|
542 | 589 | })
|
543 | 590 | }
|
| 591 | + |
| 592 | + /// EMA version of `list_prices`. |
| 593 | + pub fn list_ema_prices( |
| 594 | + &self, |
| 595 | + price_ids: Vec<PriceIdentifier>, |
| 596 | + ) -> HashMap<PriceIdentifier, Option<Price>> { |
| 597 | + self.list_ema_prices_no_older_than(price_ids, self.get_stale_threshold()) |
| 598 | + } |
| 599 | + |
| 600 | + /// EMA version of `list_prices_unsafe`. |
| 601 | + pub fn list_ema_prices_unsafe( |
| 602 | + &self, |
| 603 | + price_ids: Vec<PriceIdentifier>, |
| 604 | + ) -> HashMap<PriceIdentifier, Option<Price>> { |
| 605 | + self.list_ema_prices_no_older_than(price_ids, u64::MAX) |
| 606 | + } |
| 607 | + |
| 608 | + /// EMA version of `list_prices_no_older_than`. |
| 609 | + pub fn list_ema_prices_no_older_than( |
| 610 | + &self, |
| 611 | + price_ids: Vec<PriceIdentifier>, |
| 612 | + age: Seconds, |
| 613 | + ) -> HashMap<PriceIdentifier, Option<Price>> { |
| 614 | + price_ids |
| 615 | + .into_iter() |
| 616 | + .map(|price_id| { |
| 617 | + if let Some(feed) = self.prices.get(&price_id) { |
| 618 | + let block_timestamp = env::block_timestamp() / 1_000_000_000; |
| 619 | + let price_timestamp = feed.ema_price.publish_time; |
| 620 | + |
| 621 | + // - If Price older than STALENESS_THRESHOLD, set status to Unknown. |
| 622 | + // - If Price newer than now by more than STALENESS_THRESHOLD, set status to Unknown. |
| 623 | + // - Any other price around the current time is considered valid. |
| 624 | + if u64::abs_diff(block_timestamp, price_timestamp.try_into().unwrap()) > age { |
| 625 | + (price_id, None) |
| 626 | + } else { |
| 627 | + (price_id, Some(feed.ema_price)) |
| 628 | + } |
| 629 | + } else { |
| 630 | + (price_id, None) |
| 631 | + } |
| 632 | + }) |
| 633 | + .collect() |
| 634 | + } |
544 | 635 | }
|
545 | 636 |
|
546 | 637 | /// This second `impl Pyth` block contains only private methods that are called internally that
|
|
0 commit comments