diff options
author | 2022-08-17 02:22:06 -0700 | |
---|---|---|
committer | 2022-08-17 02:22:06 -0700 | |
commit | d37bdcd64d1dd951ae4125efa039062dcf4dd314 (patch) | |
tree | fab870cf4da2504b54ba877d4a3f51e376147b06 /rust/scraper/src | |
parent | 9f7722345941b571d284b490a4121aabc37d94f6 (diff) | |
download | touchpad-d37bdcd64d1dd951ae4125efa039062dcf4dd314.tar.gz touchpad-d37bdcd64d1dd951ae4125efa039062dcf4dd314.tar.zst touchpad-d37bdcd64d1dd951ae4125efa039062dcf4dd314.zip |
Adjusts TouchpadClient api and internals
Moves gender from only individual events to all events in proto schema.
Also adds is_relay boolean to event proto schema.
Adds url field to allow for dynamic base url adjustment and adds
new_with_url function to allow for TouchpadLiveClient with custom base
urls.
Diffstat (limited to 'rust/scraper/src')
-rw-r--r-- | rust/scraper/src/touchpad/mod.rs | 76 |
1 files changed, 41 insertions, 35 deletions
diff --git a/rust/scraper/src/touchpad/mod.rs b/rust/scraper/src/touchpad/mod.rs index 6d965eb..9b982c6 100644 --- a/rust/scraper/src/touchpad/mod.rs +++ b/rust/scraper/src/touchpad/mod.rs @@ -2,6 +2,7 @@ mod error; mod request_response; mod conversion; +use std::borrow::Cow; use futures::{future, TryFutureExt}; use proto::touchpad::common::v1; use reqwest::Client; @@ -18,43 +19,44 @@ use self::conversion::FromTouchpadLive; const BASE_URL: &'static str = "https://www.touchpadlive.com/rest/touchpadlive"; +/// A client to the TouchpadLive website api +/// +/// The client wraps a [reqwest::Client] to make the api calls. #[derive(Clone)] -pub struct TouchpadLiveClient { +pub struct TouchpadLiveClient<'a> { client: Client, + url: Cow<'a, str>, } -impl TouchpadLiveClient { +impl<'a> TouchpadLiveClient<'a> { pub fn new() -> Self { TouchpadLiveClient { client: Client::new(), + url: BASE_URL.into(), + } + } + + pub fn new_with_url(url: impl Into<Cow<'a, str>>) -> Self { + TouchpadLiveClient { + client: Client::new(), + url: url.into(), } } pub async fn meet_info(&self, id: u32) -> Result<v1::SwimMeet, TouchpadLiveError> { - let client1 = self.client.clone(); - let meet_info_handle = tokio::spawn(async move { - client1 - .get(format!("{}/meets/{}", BASE_URL, id)) - .send() - .await? - .json::<MeetInfoResponse>() - .await - }); - - let client2 = self.client.clone(); - let team_info_handle = tokio::spawn(async move { - client2 - .get(format!("{}/meets/{}/teams", BASE_URL, id)) - .send() - .await? - .json::<Vec<TeamInfoResponse>>() - .await - }); + let meet_info_handle = self.client + .get(format!("{}/meets/{}", &self.url, id)) + .send() + .await? + .json::<MeetInfoResponse>(); - let (resp_results, teams_result) = future::join(meet_info_handle, team_info_handle).await; + let team_info_handle = self.client + .get(format!("{}/meets/{}/teams", &self.url, id)) + .send() + .await? + .json::<Vec<TeamInfoResponse>>(); - let resp = resp_results??; - let teams = teams_result??; + let (resp, teams) = future::try_join(meet_info_handle, team_info_handle).await?; Ok(v1::SwimMeet { id, @@ -73,7 +75,7 @@ impl TouchpadLiveClient { } pub async fn events(&self, id: u32) -> Result<Vec<v1::Event>, TouchpadLiveError> { - let events = get_events(self.client.clone(), id).await?; + let events = get_events(self.client.clone(), &self.url, id).await?; events.into_iter() .map(|ev| Ok(v1::Event { @@ -81,11 +83,12 @@ impl TouchpadLiveClient { age_hi: ev.age_hi as u32, age_lo: ev.age_lo as u32, distance: ev.distance, - gender: v1::Gender::from_touchpad (ev.stroke.as_str()) as i32, + gender: v1::Gender::from_touchpad(ev.gender.as_str()) as i32, event: None, event_num: ev.event_number.parse()?, meet_id: id, stroke: v1::Stroke::from_touchpad(ev.stroke.as_str()) as i32, + is_relay: ev.relay, })) .collect() } @@ -94,7 +97,7 @@ impl TouchpadLiveClient { let (swimmers, swimmer_map, events) = { let swimmers = self .client - .get(format!("{}/meets/{}/participants", BASE_URL, id)) + .get(format!("{}/meets/{}/participants", &self.url, id)) .send() .await? .json::<Vec<ParticipantResponse>>() @@ -102,13 +105,13 @@ impl TouchpadLiveClient { let swimmer_map = self .client - .get(format!("{}/meets/{}/swimmerEventMap", BASE_URL, id)) + .get(format!("{}/meets/{}/swimmerEventMap", &self.url, id)) .send() .await? .json::<HashMap<u32, Vec<u32>>>() .map_err(|e| e.into()); - let events = get_events(self.client.clone(), id); + let events = get_events(self.client.clone(), &self.url, id); future::try_join3(swimmers, swimmer_map, events) } @@ -119,9 +122,9 @@ impl TouchpadLiveClient { pub async fn individual_event(&self, meet_id: u32, ev_id: u32) -> Result<v1::Event, TouchpadLiveError> { let (events, times) = { - let events = get_events(self.client.clone(), meet_id); + let events = get_events(self.client.clone(), &self.url, meet_id); - let event = get_event(self.client.clone(), "individual", meet_id, ev_id); + let event = get_event(self.client.clone(), "individual", &self.url, meet_id, ev_id); future::try_join(events, event) }.await?; @@ -135,18 +138,20 @@ impl TouchpadLiveClient { } } -async fn get_events(client: Client, id: u32) -> Result<Vec<EventsResponse>, TouchpadLiveError> { +/// Gets the events for a meet from TouchpadLive +async fn get_events(client: Client, base_url: &str, id: u32) -> Result<Vec<EventsResponse>, TouchpadLiveError> { Ok(client - .get(format!("{}/meets/{}/events", BASE_URL, id)) + .get(format!("{}/meets/{}/events", base_url, id)) .send() .await? .json() .await?) } -async fn get_event(client: Client, tp: &str, meet_id: u32, ev_id: u32) -> Result<Vec<EventTimeResponse>, TouchpadLiveError> { +/// Gets event timings given a meet_id, ev_id, and event type (tp) +async fn get_event(client: Client, base_url: &str, tp: &str, meet_id: u32, ev_id: u32) -> Result<Vec<EventTimeResponse>, TouchpadLiveError> { Ok(client - .get(format!("{}/meets/{}/{}/{}", BASE_URL, meet_id, tp, ev_id)) + .get(format!("{}/meets/{}/{}/{}", base_url, meet_id, tp, ev_id)) .send() .await? .json() @@ -220,6 +225,7 @@ fn create_individual_event_proto( id: ev_id, meet_id, stroke: v1::Stroke::from_touchpad(event.stroke.as_str()) as i32, + is_relay: event.relay, event: Some(v1::event::Event::Individual( v1::IndividualEvent { times: proto_times, |