use std::time::Duration;
use serde::Deserialize;
use crate::error::{Result, SyncwebError};
use super::certs::ensure_provider_installed;
pub const POOL_HTTP_ENDPOINT: &str = "https://relays.syncthing.net/endpoint";
const POOL_USER_AGENT: &str = concat!("syncweb/", env!("CARGO_PKG_VERSION"));
pub async fn fetch_relay_pool(timeout: Duration) -> Result<Vec<String>> {
fetch_relay_pool_from(POOL_HTTP_ENDPOINT, timeout).await
}
async fn fetch_relay_pool_from(endpoint: &str, timeout: Duration) -> Result<Vec<String>> {
ensure_provider_installed();
let client = reqwest::Client::builder()
.timeout(timeout)
.user_agent(POOL_USER_AGENT)
.build()
.map_err(|error| SyncwebError::operation("relay pool client", error))?;
let response: PoolResponse = client
.get(endpoint)
.send()
.await
.map_err(|error| SyncwebError::operation("relay pool request", error))?
.error_for_status()
.map_err(|error| SyncwebError::operation("relay pool response status", error))?
.json()
.await
.map_err(|error| SyncwebError::operation("relay pool response body", error))?;
Ok(response.relays.into_iter().map(|relay| relay.url).collect())
}
#[derive(Deserialize)]
struct PoolResponse {
relays: Vec<PoolRelay>,
}
#[derive(Deserialize)]
struct PoolRelay {
url: String,
}