From e78de73d83ee224899d1e2443d301e7dbcb30179 Mon Sep 17 00:00:00 2001 From: Jef Roosens Date: Thu, 8 Apr 2021 10:56:35 +0200 Subject: [PATCH] [#14] Added fancy loops to pickup_times & search --- src/ivago/controller/pickup_times.rs | 15 ++++++++------- src/ivago/controller/search.rs | 22 ++++++++-------------- 2 files changed, 16 insertions(+), 21 deletions(-) diff --git a/src/ivago/controller/pickup_times.rs b/src/ivago/controller/pickup_times.rs index 955e840..d2721f9 100644 --- a/src/ivago/controller/pickup_times.rs +++ b/src/ivago/controller/pickup_times.rs @@ -41,13 +41,14 @@ pub fn get_pickup_times( let mut output: Vec = Vec::new(); - for map in data.iter() { - output.push(PickupTime::new( - // TODO it's really not logical here that this would return an - // "InvalidArgument" error, it should just skip the item - BasicDate::try_from(map.get("date").unwrap().as_str())?, - map.get("label").unwrap().to_string(), - )) + for map in data + .iter() + .filter(|m| m.contains_key("date") && m.contains_key("label")) + { + // Because we filtered the maps in the loop, we can safely us unwrap here + if let Ok(date) = BasicDate::try_from(map.get("date").unwrap().as_str()) { + output.push(PickupTime::new(date, map.get("label").unwrap().to_string())) + } } Ok(output) diff --git a/src/ivago/controller/search.rs b/src/ivago/controller/search.rs index 8c84113..e66652d 100644 --- a/src/ivago/controller/search.rs +++ b/src/ivago/controller/search.rs @@ -13,23 +13,17 @@ const SEARCH_URL: &str = "https://www.ivago.be/nl/particulier/autocomplete/garba /// /// * `street` - name of the street /// * `city` - city the street is in -// TODO find out how to do this async pub fn search_streets(street_name: &str) -> Result, FejError> { let client = reqwest::Client::new(); let response = client.get(SEARCH_URL).query(&[("q", street_name)]).send()?; let data: Vec> = response.json()?; - let mut output: Vec = Vec::new(); - - // We iterate over every item and extract the needed data - for map in data.iter() { - if let Some(value) = map.get("value") { - match Street::try_from(value.as_str()) { - Ok(street) => output.push(street), - Err(_) => continue, - } - } - } - - Ok(output) + // This is pretty cool, filter_map first does get() on all the maps, and + // then filters out any None values + // Then, we do the same thing for streets + Ok(data + .iter() + .filter_map(|m| m.get("value")) + .filter_map(|v| Street::try_from(v.as_str()).ok()) + .collect()) }