use super::hh_mm_time_format; use chrono::{Duration, NaiveTime}; use serde::Deserialize; #[derive(Deserialize, Debug, Clone, Copy)] pub struct HourBlock { #[serde(with = "hh_mm_time_format")] pub hour: NaiveTime, pub state: u32, // reservations pub granularity: u32, pub person_count: u32, pub places_available: u32, pub places_bookable: u32, } #[derive(Deserialize, Debug)] pub struct Resource { pub resource_id: u32, pub resource_name: String, pub resource_type: u32, pub granularity: u32, pub time_slot_count: u32, pub static_time_slot: bool, // reservations_by_timeslot pub note_available: bool, pub note_required: bool, pub note_description: String, pub description: String, pub capacity: u32, pub site_timezone: String, pub user_name_required: bool, pub user_phone_required: bool, pub user_name_available: bool, pub user_phone_available: bool, // time_before_reservations_closed // min_places_per_reservation // max_places_per_reservation pub image_url: Option, // services pub slots_state: u32, pub hours: Vec, } impl Resource { pub fn condensed_hours(&self) -> Vec<(&HourBlock, Duration)> { let mut start_hour_opt: Option<&HourBlock> = None; let mut duration = Duration::seconds(0); let mut out: Vec<(&HourBlock, Duration)> = Default::default(); for hour in &self.hours { if let Some(start_hour) = start_hour_opt { if hour.state == start_hour.state { duration = duration + Duration::minutes(hour.granularity.into()); } else { out.push((start_hour, duration)); start_hour_opt = Some(hour); duration = Duration::minutes(hour.granularity.into()); } } else if hour.state == 1 { start_hour_opt = Some(hour); duration = Duration::minutes(hour.granularity.into()); } } if let Some(start_hour) = start_hour_opt { out.push((start_hour, duration)); } out } pub fn condensed_available_hours(&self) -> Vec<(&HourBlock, Duration)> { self.condensed_hours() .into_iter() .filter(|(hour, _)| hour.state == 1) .collect() } }