1use pine_core::{Data, Ohlcv};
12
13mod static_provider;
14
15mod binance;
16mod kraken;
17mod yahoo;
18
19pub use binance::BinanceSource;
20pub use kraken::KrakenSource;
21pub use static_provider::{resample, StaticProvider};
22pub use yahoo::YahooSource;
23
24pub(crate) fn fetch(url: &str) -> Result<String, DataError> {
25 ureq::get(url)
28 .set("User-Agent", "pinecone/0.1")
29 .call()
30 .map_err(|source| DataError::Http {
31 url: url.to_string(),
32 message: source.to_string(),
33 })?
34 .into_string()
35 .map_err(|source| DataError::Http {
36 url: url.to_string(),
37 message: source.to_string(),
38 })
39}
40
41pub(crate) fn quoted(value: &serde_json::Value) -> Option<f64> {
43 match value {
44 serde_json::Value::String(text) => text.parse().ok(),
45 other => other.as_f64(),
46 }
47}
48
49pub fn synthetic(count: usize) -> Data {
50 Data::from_ohlcv((0..count).map(|i| {
51 let close = 100.0 + i as f64;
52 Ohlcv {
53 time: i as i64 * 60_000,
54 open: close - 1.0,
55 high: close + 1.0,
56 low: close - 2.0,
57 close,
58 volume: 1000.0,
59 }
60 }))
61}
62
63#[derive(Debug, thiserror::Error)]
64pub enum DataError {
65 #[error("{path}: {source}")]
68 Read {
69 path: String,
70 #[source]
71 source: ::csv::Error,
72 },
73
74 #[error("{url}: {message}")]
76 Http { url: String, message: String },
77
78 #[error("{provider}: {message}")]
81 Provider {
82 provider: &'static str,
83 message: String,
84 },
85}