Skip to main content

things3_cloud/commands/
upcoming.rs

1use std::{io::Write, sync::Arc};
2
3use anyhow::Result;
4use clap::Args;
5use iocraft::prelude::*;
6
7use crate::{
8    app::Cli,
9    commands::{Command, DetailedArgs},
10    ui::{render_element_to_string, views::upcoming::UpcomingView},
11    wire::task::TaskStatus,
12};
13
14#[derive(Debug, Default, Args)]
15pub struct UpcomingArgs {
16    #[command(flatten)]
17    pub detailed: DetailedArgs,
18}
19
20impl Command for UpcomingArgs {
21    fn run_with_ctx(
22        &self,
23        cli: &Cli,
24        out: &mut dyn Write,
25        ctx: &mut dyn crate::cmd_ctx::CmdCtx,
26    ) -> Result<()> {
27        let store = Arc::new(cli.load_store()?);
28        let today = ctx.today();
29        let now_ts = today.timestamp();
30
31        let mut tasks = Vec::new();
32        for t in store.tasks(Some(TaskStatus::Incomplete), Some(false), None) {
33            if t.in_someday() {
34                continue;
35            }
36            let Some(start_date) = t.start_date else {
37                continue;
38            };
39            if start_date.timestamp() > now_ts {
40                tasks.push(t);
41            }
42        }
43        tasks.sort_by_key(|t| t.start_date);
44
45        let mut ui = element! {
46            ContextProvider(value: Context::owned(store.clone())) {
47                ContextProvider(value: Context::owned(today)) {
48                    UpcomingView(
49                        items: &tasks,
50                        detailed: self.detailed.detailed,
51                    )
52                }
53            }
54        };
55
56        let rendered = render_element_to_string(&mut ui, cli.no_color);
57        writeln!(out, "{}", rendered)?;
58        Ok(())
59    }
60}