ccdata_api/lib.rs
1//! # CoinDesk API Wrapper
2//!
3//! `ccdata-api` is a wrapper for CoinDesk REST API endpoints (Formerly CCData). This crate supports non-exhausitve list of CoinDesk endpoints,
4//! you can check what endpoints are supported by checking the variants of the enum `CCAPIEndpoint` - it contains all
5//! supported endpoint URLs.
6//!
7//! For documentation on CoinDesk REST API endpoints visit CoinDesk online documentation:
8//! - API Documentation: <https://developers.coindesk.com/documentation/data-api/introduction>
9//! - Legacy API Documentation: <https://developers.coindesk.com/documentation/legacy/Price/SingleSymbolPriceEndpoint>
10//!
11//! **Disclaimer:** This crate is an unofficial CoinDesk REST API wrapper, the maintainers of the crate are independent developers.
12//! The developers of the crate do not accept any responsibility or liability for the accuracy, security, or completeness of the code,
13//! or the information provided within the crate.
14//!
15//! # Errors
16//!
17//! The REST API functions in the crate will error if the data received does not fit into the pre-defined schemas provided
18//! in the crate. If you encounter any errors, please open an issue on GitHub with the parameters that you have used (e.g., asset symbol,
19//! timestamp, limit, etc.). **Do not provide your API key or any personal data!**
20//!
21//! # Deprecated API Endpoints
22//!
23//! Some API endpoints have been deprecated by CoinDesk, who strongly recommend migrating to newer alternatives suggested in their API documentation.
24//!
25//! # Features
26//! - `debug`: If this feature is enabled, you can set `CCDATA_API_DEBUG` environment variable to `true`, which will print the response body
27//! for every request to the command line.
28//!
29//! # Examples
30//!
31//! To start making the REST API requests, define a data collection backend. This can be done by either directly passing an
32//! API key to the data collection backend, or by defining a `.env` file with an API key as an environment variable (Preferred
33//! method).
34//!
35//! ## Build Backend Explicitly Stating API Key (May expose API key)
36//!
37//! ```rust
38//! use ccdata_api::CCData;
39//!
40//! let mut backend: CCData = CCData::new();
41//!
42//! let api_key: String = String::from("xxxxxxx");
43//! backend.update_api_key(api_key);
44//!
45//! assert_eq!(backend.api_key().unwrap(), "xxxxxxx");
46//! ```
47//!
48//! ## Build Backend Using .env File (Preferred method)
49//!
50//! ```rust
51//! use ccdata_api::CCData;
52//!
53//! let mut backend: CCData = CCData::new();
54//! // Provide API key as the environment variable called API_KEY
55//! backend.build(&"API_KEY").unwrap();
56//!
57//! println!("{}", backend.api_key().unwrap());
58//! ```
59//!
60//! ## Making First API Call
61//!
62//! After the backend has been build, you can make API requests using the methods provided in the backend. For example, to
63//! get a daily spot OHLCV data for Bitcoin you can do the following (note that the calls use Rust's `async` functionality):
64//!
65//! ```rust
66//!
67//! use ccdata_api::{CCData, CCUnit, CCSpotMarket};
68//!
69//! #[tokio::main]
70//! async fn main() -> () {
71//!
72//! let mut backend: CCData = CCData::new();
73//! // Provide API key as the environment variable called API_KEY
74//! backend.build(&"API_KEY").unwrap();
75//!
76//! // Define the API parameters
77//! let market: CCSpotMarket = CCSpotMarket::KRAKEN;
78//! let limit: usize = 2000;
79//! let to_timestamp: Option<i64> = Some(1728860400);
80//!
81//! // Make the API call
82//! let ohlcv = backend.get_spot_ohlcv("BTC-USD", to_timestamp, Some(limit), market, CCUnit::Day).await.unwrap();
83//! assert_eq!(ohlcv.data.unwrap().len(), limit);
84//!
85//! }
86//! ```
87//!
88//! # General information
89//! If you would like to add a commit or an issue, please do so using the GitHub link to the project:
90//! - <https://github.com/rsadykhov/ccdata-api>
91
92
93// Re-Exports
94pub use self::backend::CCData;
95// Min-API Re-Exports
96pub use self::schemas::{CCMinResponse, CCMinWrapper, CCRateLimit, CCMaxCalls, CCCallsMade};
97pub use self::schemas::min_api::{CCAvailableCoinList, CCHistoricalDaily, CCBalanceDistribution, CCSupplyBand};
98// Data-API Re-Exports
99pub use self::schemas::{CCDataResponse, CCError, CCErrorOtherInfo};
100pub use self::schemas::data_api::indices_and_reference_rates::{CCIndicesMarket, CCIndicesOHLCV};
101pub use self::schemas::data_api::spot::{CCSpotMarket, CCSpotInstrumentStatus, CCSpotOHLCV, CCSpotInstrumentMetdata, CCSpotMarkets, CCSpotMarketsInstruments};
102pub use self::schemas::data_api::futures::{CCFuturesMarket, CCFuturesOHLCV, CCFuturesMarkets};
103pub use self::schemas::data_api::options::{CCOptionsMarket, CCOptionsOHLCV, CCOptionsMarkets};
104pub use self::schemas::data_api::derivatives_indices::{CCDerIndicesMarket, CCDerIndicesOHLCV, CCDerIndicesMarkets};
105pub use self::schemas::data_api::on_chain_dex::{CCOCDEXMarket, CCOCDEXOHLCV, CCOCDEXMarkets};
106pub use self::schemas::data_api::on_chain_core::{CCOCCoreETHBlock, CCOCCoreAssetByChain, CCOCCoreAssetByAddress, CCOCCoreSupply};
107pub use self::schemas::data_api::asset::{CCAssetMetadata, CCAssetEvent, CCAssetCodeRepoMetrics, CCAssetDiscord, CCAssetReddit, CCAssetTelegram, CCAssetTwitter};
108pub use self::schemas::data_api::news::{CCNewsStatus, CCNewsLang, CCNewsSourceID, CCNewsLatestArticle, CCNewsSourceType, CCNewsSource, CCNewsCategory};
109pub use self::schemas::data_api::overview::CCOverviewMktCapOHLCV;
110
111
112pub mod error;
113pub mod schemas;
114pub mod utils;
115pub mod backend;
116
117
118/// Unit of the interval between successive data points.
119pub enum CCUnit {
120 /// Daily data interval
121 Day,
122 /// Hourly data interval
123 Hour,
124 /// Minutely data interval
125 Minute,
126 /// Used for API endpoints that do not have a specified unit for data or where unit is unapplicable
127 NA,
128}
129
130
131/// All supported API endpoints.
132pub enum CCAPIEndpoint {
133 #[deprecated(since="1.0.6", note="Deprecated by CoinDesk")]
134 // Min-API
135 /// Min-API Endpoint
136 ///
137 /// Description: Returns a list of all coins for which CoinDesk currently gets the blockchain data
138 ///
139 /// URL: https://min-api.cryptocompare.com/data/blockchain/list
140 AvailableCoinList,
141 #[deprecated(since="1.0.6", note="Deprecated by CoinDesk")]
142 /// Min-API Endpoint
143 ///
144 /// Description: Retrieves the daily aggregated blockchain data for the requested coin
145 ///
146 /// URL: https://min-api.cryptocompare.com/data/blockchain/histo/day
147 HistoricalDaily,
148 #[deprecated(since="1.0.6", note="Deprecated by CoinDesk")]
149 /// Min-API Endpoint
150 ///
151 /// Description: Retrieves the balance distribution for a specified asset over a specified time range at a daily interval
152 ///
153 /// Note: Only data for BTC (Bitcoin) is currently available
154 ///
155 /// URL: https://min-api.cryptocompare.com/data/blockchain/balancedistribution/histo/day
156 BalanceDistribution,
157 // Data-API
158 // Indices & Reference Rates
159 /// Data-API Endpoint
160 ///
161 /// Description: Provides historical candlestick data for various indices
162 ///
163 /// URL: https://data-api.coindesk.com/index/cc/v1/historical
164 IndicesOHLCV,
165 // Spot
166 /// Data-API Endpoint
167 ///
168 /// Description: Provides candlestick data for specific cryptocurrency instruments across selected exchanges
169 ///
170 /// URL: https://data-api.coindesk.com/spot/v1/historical
171 SpotOHLCV,
172 /// Data-API Endpoint
173 ///
174 /// Description: Delivers vital metadata about financial instruments traded on specified exchanges, focusing solely on non-price related information
175 ///
176 /// URL: https://data-api.coindesk.com/spot/v1/latest/instrument/metadata
177 SpotInstrumentMetadata,
178 #[deprecated(since="1.0.6", note="Deprecated by CoinDesk")]
179 /// Data-API Endpoint
180 ///
181 /// Description: Provides comprehensive information about various cryptocurrency spot markets
182 ///
183 /// URL: https://data-api.coindesk.com/spot/v1/markets
184 SpotMarkets,
185 /// Data-API Endpoint
186 ///
187 /// Description: Retrieves a comprehensive dictionary of mapped instruments across one or more spot markets, filtered by a specified state or status
188 ///
189 /// URL: https://data-api.coindesk.com/spot/v1/markets/instruments
190 SpotMarketsInstruments,
191 // Futures
192 /// Data-API Endpoint
193 ///
194 /// Description: Provides aggregated candlestick data for specific futures instruments on designated exchanges
195 ///
196 /// URL: https://data-api.coindesk.com/futures/v1/historical
197 FuturesOHLCV,
198 #[deprecated(since="1.0.6", note="Deprecated by CoinDesk")]
199 /// Data-API Endpoint
200 ///
201 /// Description: Provides comprehensive information about various cryptocurrency futures markets
202 ///
203 /// URL: https://data-api.coindesk.com/futures/v1/markets
204 FuturesMarkets,
205 // Options
206 /// Data-API Endpoint
207 ///
208 /// Description: Provides historical OHLCV (open, high, low, close, volume) data for specified options instruments on a chosen exchange
209 ///
210 /// URL: https://data-api.coindesk.com/options/v1/historical
211 OptionsOHLCV,
212 #[deprecated(since="1.0.6", note="Deprecated by CoinDesk")]
213 /// Data-API Endpoint
214 ///
215 /// Description: Provides comprehensive information about the various options markets integrated by our platform
216 ///
217 /// URL: https://data-api.coindesk.com/options/v1/markets
218 OptionsMarkets,
219 // Derivatives Indices
220 /// Data-API Endpoint
221 ///
222 /// Description: Provides historical OHLC (open, high, low, close) data for specified index instruments on a selected market
223 ///
224 /// URL: https://data-api.coindesk.com/index/v1/historical
225 DerIndicesOHLCV,
226 #[deprecated(since="1.0.6", note="Deprecated by CoinDesk")]
227 /// Data-API Endpoint
228 ///
229 /// Description: Provides comprehensive information about various derivatives index markets
230 ///
231 /// URL: https://data-api.coindesk.com/index/v1/markets
232 DerIndicesMarkets,
233 // On-Chain DEX
234 /// Data-API Endpoint
235 ///
236 /// Description: Retrieves aggregated candlestick data for AMM swap transactions
237 ///
238 /// URL: https://data-api.coindesk.com/onchain/v1/amm/historical/swap
239 OCDEXOHLCV,
240 #[deprecated(since="1.0.6", note="Deprecated by CoinDesk")]
241 /// Data-API Endpoint
242 ///
243 /// Description: Provides comprehensive information about various decentralized exchange (DEX) markets within the blockchain ecosystem
244 ///
245 /// URL: https://data-api.coindesk.com/onchain/v1/amm/markets
246 OCDEXMarkets,
247 // On-Chain Core
248 /// Data-API Endpoint
249 ///
250 /// Description: Delivers exhaustive details on a specific Ethereum block in a meticulously processed format, complete with detailed explanations for each field
251 ///
252 /// URL: https://data-api.coindesk.com/onchain/v1/block/2
253 OCCoreETHBlocks,
254 /// Data-API Endpoint
255 ///
256 /// Description: Retrieves a comprehensive summary of chain asset information for a specified blockchain, identified by its chain symbol
257 ///
258 /// URL: https://data-api.coindesk.com/onchain/v3/summary/by/chain
259 OCCoreAssetsByChain,
260 /// Data-API Endpoint
261 ///
262 /// Description: Retrieves comprehensive asset information for a specific asset identified by its smart contract address and associated blockchain asset
263 ///
264 /// URL: https://data-api.coindesk.com/onchain/v2/data/by/address
265 OCCoreAssetByAddress,
266 /// Data-API Endpoint
267 ///
268 /// Description: Retrieves comprehensive historical supply data for various digital assets identified by either their CoinDesk asset ID or unique asset symbol
269 ///
270 /// URL: https://data-api.coindesk.com/onchain/v2/historical/supply/days
271 OCCoreSupply,
272 #[deprecated(since="1.0.6", note="Deprecated by CoinDesk")]
273 // Asset
274 /// Data-API Endpoint
275 ///
276 /// Description: Returns an object that provides detailed and comprehensive information about multiple cryptocurrency assets in response to a request
277 ///
278 /// URL: https://data-api.coindesk.com/asset/v1/metadata
279 AssetMetadata,
280 /// Data-API Endpoint
281 ///
282 /// Descriptions: Returns an object that provides detailed and comprehensive information about multiple cryptocurrency assets in response to a request
283 ///
284 /// URL: https://data-api.coindesk.com/asset/v2/metadata
285 AssetMetadataV2,
286 /// Data-API Endpoint
287 ///
288 /// Description: Retrieves an array of significant events related to digital assets, such as security incidents, rebrandings, blockchain forks, and other impactful developments
289 ///
290 /// URL: https://data-api.coindesk.com/asset/v1/events
291 AssetEvents,
292 /// Data-API Endpoint
293 ///
294 /// Description: Provides an in-depth, daily snapshot of a digital asset's code repositories
295 ///
296 /// URL: https://data-api.coindesk.com/asset/v1/historical/code-repository/days
297 AssetCodeRepo,
298 /// Data-API Endpoint
299 ///
300 /// Description: Aggregates detailed daily metrics from all Discord servers related to a specific digital asset, offering a multifaceted view into community engagement and the asset's standing within Discord communities
301 ///
302 /// URL: https://data-api.coindesk.com/asset/v1/historical/discord/days
303 AssetDiscord,
304 /// Data-API Endpoint
305 ///
306 /// Description: Aggregates key performance indicators from all the subreddits related to a specific digital asset, providing a comprehensive understanding of the asset's footprint on Reddit
307 ///
308 /// URL: https://data-api.coindesk.com/asset/v1/historical/reddit/days
309 AssetReddit,
310 /// Data-API Endpoint
311 ///
312 /// Description: Collates essential data points across all Telegram groups affiliated with a particular cryptocurrency asset
313 ///
314 /// URL: https://data-api.coindesk.com/asset/v1/historical/telegram/days
315 AssetTelegram,
316 /// Data-API Endpoint
317 ///
318 /// Description: Aggregates essential metrics from all X (Twitter) accounts associated with a specific cryptocurrency asset
319 ///
320 /// URL: https://data-api.coindesk.com/asset/v1/historical/twitter/days
321 AssetTwitter,
322 // News
323 /// Data-API Endpoint
324 ///
325 /// Description: Serves as the pulse of the crypto news landscape, providing users with instant access to the most recent articles across the industry
326 ///
327 /// URL: https://data-api.coindesk.com/news/v1/article/list
328 NewsLatestArticles,
329 /// Data-API Endpoint
330 ///
331 /// Description: Offers a comprehensive listing of all news sources available through CoinDesk API
332 ///
333 /// URL: https://data-api.coindesk.com/news/v1/source/list
334 NewsSources,
335 /// Data-API Endpoint
336 ///
337 /// Description: Provide a straightforward listing of all news categories available through CoinDesk API
338 ///
339 /// URL: https://data-api.coindesk.com/news/v1/category/list
340 NewsCategories,
341 // Overview
342 /// Data-API Endpoint
343 ///
344 /// Description: Presents a thorough historical daily overview of market capitalisation for digital assets that meet the volume and listing criteria
345 ///
346 /// URL: https://data-api.coindesk.com/overview/v1/historical/marketcap/all/assets/days
347 OverviewMktCapOHLCV,
348}
349
350impl CCAPIEndpoint {
351 fn resolve_url(&self) -> String {
352 match self {
353 // Min-API
354 Self::AvailableCoinList => String::from("https://min-api.cryptocompare.com/data/blockchain/list"),
355 Self::HistoricalDaily => String::from("https://min-api.cryptocompare.com/data/blockchain/histo/day"),
356 Self::BalanceDistribution => String::from("https://min-api.cryptocompare.com/data/blockchain/balancedistribution/histo/day"),
357 // Data-API
358 // Indices & Reference Rates
359 Self::IndicesOHLCV => String::from("https://data-api.coindesk.com/index/cc/v1/historical"),
360 // Spot
361 Self::SpotOHLCV => String::from("https://data-api.coindesk.com/spot/v1/historical"),
362 Self::SpotInstrumentMetadata => String::from("https://data-api.coindesk.com/spot/v1/latest/instrument/metadata"),
363 Self::SpotMarkets => String::from("https://data-api.coindesk.com/spot/v1/markets"),
364 Self::SpotMarketsInstruments => String::from("https://data-api.coindesk.com/spot/v1/markets/instruments"),
365 // Futures
366 Self::FuturesOHLCV => String::from("https://data-api.coindesk.com/futures/v1/historical"),
367 Self::FuturesMarkets => String::from("https://data-api.coindesk.com/futures/v1/markets"),
368 // Options
369 Self::OptionsOHLCV => String::from("https://data-api.coindesk.com/options/v1/historical"),
370 Self::OptionsMarkets => String::from("https://data-api.coindesk.com/options/v1/markets"),
371 // Derivatives Indices
372 Self::DerIndicesOHLCV => String::from("https://data-api.coindesk.com/index/v1/historical"),
373 Self::DerIndicesMarkets => String::from("https://data-api.coindesk.com/index/v1/markets"),
374 // On-Chain DEX
375 Self::OCDEXOHLCV => String::from("https://data-api.coindesk.com/onchain/v1/amm/historical/swap"),
376 Self::OCDEXMarkets => String::from("https://data-api.coindesk.com/onchain/v1/amm/markets"),
377 // On-Chain Core
378 Self::OCCoreETHBlocks => String::from("https://data-api.coindesk.com/onchain/v1/block/2"),
379 Self::OCCoreAssetsByChain => String::from("https://data-api.coindesk.com/onchain/v3/summary/by/chain"),
380 Self::OCCoreAssetByAddress => String::from("https://data-api.coindesk.com/onchain/v2/data/by/address"),
381 Self::OCCoreSupply => String::from("https://data-api.coindesk.com/onchain/v2/historical/supply/days"),
382 // Asset
383 Self::AssetMetadata => String::from("https://data-api.coindesk.com/asset/v1/metadata"),
384 Self::AssetMetadataV2 => String::from("https://data-api.coindesk.com/asset/v2/metadata"),
385 Self::AssetEvents => String::from("https://data-api.coindesk.com/asset/v1/events"),
386 Self::AssetCodeRepo => String::from("https://data-api.coindesk.com/asset/v1/historical/code-repository/days"),
387 Self::AssetDiscord => String::from("https://data-api.coindesk.com/asset/v1/historical/discord/days"),
388 Self::AssetReddit => String::from("https://data-api.coindesk.com/asset/v1/historical/reddit/days"),
389 Self::AssetTelegram => String::from("https://data-api.coindesk.com/asset/v1/historical/telegram/days"),
390 Self::AssetTwitter => String::from("https://data-api.coindesk.com/asset/v1/historical/twitter/days"),
391 // News
392 Self::NewsLatestArticles => String::from("https://data-api.coindesk.com/news/v1/article/list"),
393 Self::NewsSources => String::from("https://data-api.coindesk.com/news/v1/source/list"),
394 Self::NewsCategories => String::from("https://data-api.coindesk.com/news/v1/category/list"),
395 // Overview
396 Self::OverviewMktCapOHLCV => String::from("https://data-api.coindesk.com/overview/v1/historical/marketcap/all/assets/days"),
397 }
398 }
399
400 fn add_unit_to_url(&self, url: &mut String, unit: &CCUnit) -> () {
401 match self {
402 Self::IndicesOHLCV | Self::SpotOHLCV | Self::FuturesOHLCV |
403 Self::OptionsOHLCV | Self::DerIndicesOHLCV | Self::OCDEXOHLCV => {
404 match unit {
405 CCUnit::Day | CCUnit::NA => url.push_str(&"/days"),
406 CCUnit::Hour => url.push_str(&"/hours"),
407 CCUnit::Minute => url.push_str(&"/minutes"),
408 }
409 },
410 _ => (),
411 }
412 }
413
414 /// Produces URL for a given API endpoint.
415 ///
416 /// # Input
417 /// - `unit`: Unit of the interval between successive data points
418 pub fn url(&self, unit: &CCUnit) -> String {
419 let mut url: String = self.resolve_url();
420 self.add_unit_to_url(&mut url, unit);
421 url
422 }
423}
424
425
426#[cfg(test)]
427mod tests {
428
429 #[test]
430 fn unit_test_add_unit_to_url() -> () {
431 use crate::{CCUnit, CCAPIEndpoint};
432 let unit: CCUnit = CCUnit::Hour;
433 let api_endpoint: CCAPIEndpoint = CCAPIEndpoint::IndicesOHLCV;
434 assert_eq!(api_endpoint.url(&unit), String::from("https://data-api.coindesk.com/index/cc/v1/historical/hours"));
435 }
436}