diff --git a/src/cli/commands.rs b/src/cli/commands.rs index 58c1188..5b189da 100644 --- a/src/cli/commands.rs +++ b/src/cli/commands.rs @@ -41,16 +41,15 @@ impl<'a> CommandClient<'a> { } } - // TODO: allow setting week - pub(crate) async fn get_table(&self, week: &WeekNumber) -> anyhow::Result<()> { - let time_sheet = self.repository.lock().await.get_week(week).await?; + pub(crate) async fn get_table(&self, week: Option<&WeekNumber>) -> anyhow::Result<()> { + let time_sheet = self.repository.lock().await.get_time_sheet(week).await?; println!("{time_sheet}"); Ok(()) } - async fn get_json(&self, week: &WeekNumber) -> anyhow::Result<()> { - let time_sheet = self.repository.lock().await.get_week(week).await?; + async fn get_json(&self, week: Option<&WeekNumber>) -> anyhow::Result<()> { + let time_sheet = self.repository.lock().await.get_time_sheet(week).await?; let json = serde_json::to_string(&time_sheet).context("Failed to deserialize time sheet")?; @@ -59,9 +58,10 @@ impl<'a> CommandClient<'a> { } pub(crate) async fn get(&self, week: Option, format: Format) { + let week = week.map(WeekNumber::from); match format { - Format::Json => self.get_json(&week.into()).await.context("JSON"), - Format::Table => self.get_table(&week.into()).await.context("table"), + Format::Json => self.get_json(week.as_ref()).await.context("JSON"), + Format::Table => self.get_table(week.as_ref()).await.context("table"), } .unwrap_or_else(|err| { exit_with_error!("Failed to get time sheet as {}", error_stack_fmt(&err)); @@ -81,10 +81,12 @@ impl<'a> CommandClient<'a> { } let day = get_days(days); + let week = week.map(WeekNumber::from); + self.time_sheet_service .lock() .await - .set_time(hours, &day, &week.into(), job, task) + .set_time(hours, &day, week.as_ref(), job, task) .await .unwrap_or_else(|err| { if let SetTimeError::Unknown(err) = err { @@ -106,10 +108,11 @@ impl<'a> CommandClient<'a> { exit_with_error!("`--day` is set but no day was provided"); } + let week = week.map(WeekNumber::from); self.time_sheet_service .lock() .await - .clear(job, task, &get_days(days), &week.into()) + .clear(job, task, &get_days(days), week.as_ref()) .await .unwrap_or_else(|err| { if let SetTimeError::Unknown(err) = err { @@ -127,10 +130,12 @@ impl<'a> CommandClient<'a> { } pub(crate) async fn delete(&mut self, line_number: &LineNumber, week: Option) { + let week = week.map(WeekNumber::from); + self.repository .lock() .await - .delete_line(line_number, &week.into()) + .delete_line(line_number, week.as_ref()) .await .unwrap_or_else(|err| { let source = error_stack_fmt(&err); diff --git a/src/domain/time_sheet_service.rs b/src/domain/time_sheet_service.rs index f7041cd..310ad04 100644 --- a/src/domain/time_sheet_service.rs +++ b/src/domain/time_sheet_service.rs @@ -37,7 +37,7 @@ impl TimeSheetService<'_> { job: &str, task: &str, days: &Days, - week: &WeekNumber, + week: Option<&WeekNumber>, ) -> Result<(), SetTimeError> { self.set_time(0.0, days, week, job, task).await } @@ -47,7 +47,7 @@ impl TimeSheetService<'_> { &mut self, hours: f32, days: &Days, - week: &WeekNumber, + week: Option<&WeekNumber>, job: &str, task: &str, ) -> Result<(), SetTimeError> { diff --git a/src/infrastructure/repositories/time_sheet_repository.rs b/src/infrastructure/repositories/time_sheet_repository.rs index a2b4c25..4614d56 100644 --- a/src/infrastructure/repositories/time_sheet_repository.rs +++ b/src/infrastructure/repositories/time_sheet_repository.rs @@ -68,6 +68,11 @@ impl TimeSheetRepository<'_> { } async fn get_time_registration(&mut self) -> Result { + // Caching + if let Some(time_registration) = &self.time_registration { + return Ok(time_registration.clone()); + } + let container_instance = self.get_container_instance().await?; let (time_registration, concurrency_control) = self .client @@ -95,13 +100,13 @@ impl TimeSheetRepository<'_> { } /// Gets and caches time sheet - pub(crate) async fn get_time_sheet(&mut self) -> Result { - if let Some(time_registration) = &self.time_registration { - return Ok(time_registration.clone().into()); + pub(crate) async fn get_time_sheet(&mut self, week: Option<&WeekNumber>) -> Result { + if let Some(week) = week { + return self.get_week(week).await.context("Failed to get week"); } + // Fall back to today's week let time_registration = self.get_time_registration().await?; - Ok(time_registration.into()) } @@ -132,12 +137,13 @@ impl TimeSheetRepository<'_> { &mut self, hours: f32, days: &Days, - week: &WeekNumber, + week: Option<&WeekNumber>, job: &str, task: &str, ) -> Result<(), AddLineError> { + info!("Getting time sheet"); let time_sheet = self - .get_time_sheet() + .get_time_sheet(week) .await .context("Failed to get time sheet")?; @@ -151,6 +157,7 @@ impl TimeSheetRepository<'_> { let days: HashSet<_> = days.iter().map(|&d| d as u8).collect(); + info!("Setting time"); let concurrency_control = self .client .set_time(hours, &days, line_number, &container_instance) @@ -222,26 +229,21 @@ impl TimeSheetRepository<'_> { Ok(time_registration.into()) } - async fn get_number_of_lines(&mut self) -> Result { - let time_sheet = self.get_time_sheet().await?; - Ok(time_sheet.lines.len() as u8) - } - pub(crate) async fn delete_line( &mut self, line_number: &LineNumber, - week: &WeekNumber, + week: Option<&WeekNumber>, ) -> Result<()> { // We need to get the time sheet before we can modify it - let _ = self - .get_time_sheet() + let time_sheet = self + .get_time_sheet(week) .await .context("Failed to get time sheet")?; let line_number = match line_number { LineNumber::Number(line_number) => *line_number, LineNumber::Last => { - let last_line_number = self.get_number_of_lines().await?; + let last_line_number = time_sheet.lines.len() as u8; info!("Using line number {last_line_number} as last line number"); last_line_number } @@ -261,8 +263,8 @@ impl TimeSheetRepository<'_> { Ok(()) } - pub(crate) async fn get_week(&mut self, week: &WeekNumber) -> Result { - // TODO: only call `set_time` if week isn't today's week + async fn get_week(&mut self, week: &WeekNumber) -> Result { + // We have to get the time registration before we can set a week let _ = self.get_time_registration().await?; let container_instance = self @@ -270,7 +272,6 @@ impl TimeSheetRepository<'_> { .await .context("Failed to get container instance")?; - // TODO: calculate date from week number let year = Local::now().date_naive().year(); let date = week .first_day(year)