osmosis-labs / isotonic

Smart Contracts for the Lendex Protocol
MIT License
1 stars 0 forks source link

Create (stub) Price Oracle #20

Closed ethanfrey closed 2 years ago

ethanfrey commented 2 years ago

Create a stub price oracle, which is controlled by a oracle_address (set on instantiate), and a maximum age for an entry (jn seconds)

This maintains a map of (sell: &str, buy: &str) -> { rate: Decimal, updated: Timestamp}.

The oracle address can set/update an entry via SetPrice{sell, buy, rate}. Timestamp is updated from env.block.time.

This PriceOracle exposes a query to get the price given buy and sell denoms. If it is missing, return a NoInfo error. It the last update was more than maximum age ago, return OutdatedOracle error. Otherwise return the rate.

Test this work and export some nice helpers for using in multitest in other contracts.

Note: the focus here should be on the interface. We will swap this out with real implementations in the future, mainly calling into a local Osmosis DEX, but maybe other strategies (eg. using off-chain oracles from CEX), so this should be configurable per denom.

hashedone commented 2 years ago

So am I understand correctly that the oracle is just common endpoint to push info about price change so others can check it in single place? How do we know that the price is actually correct? What if I (hostile user) just sets my incorrect price?

uint commented 2 years ago

So am I understand correctly that the oracle is just common endpoint to push info about price change so others can check it in single place? How do we know that the price is actually correct? What if I (hostile user) just sets my incorrect price?

Only oracle_address can update the prices. If you want to trust these prices, you have to trust the oracle (as in, the outside entity that controls oracle_address). It's not a trustless system.

ethanfrey commented 2 years ago

Tom has the correct understanding. We trust one party. Like I said, this is a stub.

"Real" oracles, like Chainlink or Band or Terra are basically a glorified multisig. We could build that. Or we could poll an on-chain DEX directly (if they have an accumulator, like Uniswap v2, to give time-averaged price feeds). That will be later, this stub is just for testing purposes to have something to fill in the interface, then we can improve it later.

hashedone commented 2 years ago

Ok, I somehow missed that anything had to be performed by oracle_address, now it is clear.

ethanfrey commented 2 years ago

BTW, this is unblocked by anything else... just a simple stub

uint commented 2 years ago

Do we want this contract to store some sort of queryable information about the asset it handles or the common token the prices are in? Or is it supposed to be simple and "dumb"? Ignore me, misunderstood things.