A general purpose price oracle leveraging ABCI++.
$ go install github.com/skip-mev/slinky
The slinky repository is composed of the following core packages:
- abci - This package contains the vote extension, proposal, and preblock handlers that are used to broadcast oracle data to the network and to store it in the blockchain.
- oracle - This package contains the main oracle that aggregates external data sources before broadcasting it to the network. You can reference the provider documentation here to get a high level overview of how the oracle works.
- providers - This package contains a collection of websocket and API based data providers that are used by the oracle to collect external data.
- x/oracle - This package contains a Cosmos SDK module that allows you to store oracle data on a blockchain.
- x/alerts - This package contains a Cosmos SDK module that allows network participants to create alerts when oracle data that is in violation of some condition is broadcast to the network and stored on the blockchain.
- x/sla - This package contains a Cosmos SDK module that allows you to create service level agreements (SLAs) that can be used to incentivize network participants to consistently, reliably provide data with high uptime.
- x/marketmap - This package contains a Cosmos SDK module that allows for market configuration to be stored and updated on a blockchain.
To run the oracle, run the following command.
$ make start-oracle
This will:
- Start a blockchain with a single validator node. It may take a few minutes to build and reach a point where vote extensions can be submitted.
- Start the oracle side-car that will aggregate prices from external data providers and broadcast them to the network. To check the current aggregated prices on the side-car, you can run
curl localhost:8080/slinky/oracle/v1/prices
. - Host a prometheus instance that will scrape metrics from the oracle side-car. Navigate to http://localhost:9090 to see all network traffic and metrics pertaining to the oracle sidecar. Navigate to http://localhost:8001 to see all application-side oracle metrics.
- Host a profiler that will allow you to profile the oracle side-car. Navigate to http://localhost:6060 to see the profiler.
After a few minutes, run the following commands to see the prices written to the blockchain:
# access the blockchain container
$ docker exec -it slinky-blockchain-1 bash
# query the price of bitcoin in USD on the node
$ (slinky-blockchain-1) ./build/slinkyd q oracle price BITCOIN USD
Result:
decimals: "8"
id: "0"
nonce: "44"
price:
block_height: "46"
block_timestamp: "2024-01-29T01:43:48.735542Z"
price: "4221100000000"
To stop the oracle, run the following command:
$ make stop-oracle
- metrics relevant to the oracle service's health + operation are here
- metrics relevant to the network's (that is running the instance slinky) performance are here
Note: These are numbers based on 14 providers and 9 currency pairs over a 24 hour period.
- ~5 milliseconds between price updates across all providers and price feeds.
- ~14 million total price updates.
- ~60 go routines are running at any given time.
- ~7x improvement in performance of websocket providers over API providers.
To test these numbers yourself, spin up the the oracle server following the instructions above and then navigate to http://localhost:9090. From here, you can run the prometheus queries defined in this readme to get insight into the oracle's performance.