From bc5eacf367fefab414587ca34d6a9e9101ceab2a Mon Sep 17 00:00:00 2001 From: geekiot Date: Wed, 26 Nov 2025 20:42:59 +0500 Subject: [PATCH] Add: add base projects command --- src/cli.rs | 23 ++++++++++++ src/config/config.rs | 2 ++ src/lib.rs | 83 ++++++++++++++++++++++++++++++++++++++++++-- 3 files changed, 106 insertions(+), 2 deletions(-) diff --git a/src/cli.rs b/src/cli.rs index 05b3849..ca0701c 100644 --- a/src/cli.rs +++ b/src/cli.rs @@ -1,3 +1,5 @@ +use std::path::PathBuf; + use clap::{Args, Parser, Subcommand}; use crate::misc::{APP_DESCRIPTION, APP_NAME}; @@ -20,6 +22,9 @@ pub enum Commands { /// Pomodoro Timer Timer(PomodoroCommand), + + /// Work with user git projects + Project(ProjectsCommand), } #[derive(Args)] @@ -64,3 +69,21 @@ pub enum PomodoroAction { rest: Option, }, } + +#[derive(Args)] +pub struct ProjectsCommand { + #[command(subcommand)] + pub action: ProjectsAction, +} + +#[derive(Subcommand)] +pub enum ProjectsAction { + /// Add new user project + Add { path: PathBuf }, + + /// Remove user project + Remove { project_name: String }, + + /// List of all user projects + List, +} diff --git a/src/config/config.rs b/src/config/config.rs index ede3d78..d5fbb3f 100644 --- a/src/config/config.rs +++ b/src/config/config.rs @@ -6,6 +6,7 @@ pub struct Config { pub templates_dir: PathBuf, pub timer_concentrate_mins: u8, pub timer_rest_mins: u8, + pub projects: Vec, } impl Config { @@ -14,6 +15,7 @@ impl Config { templates_dir: templates_dir, timer_concentrate_mins: 45, timer_rest_mins: 15, + projects: Vec::new(), } } } diff --git a/src/lib.rs b/src/lib.rs index 1675ae8..1d6db62 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -6,9 +6,9 @@ mod templates; mod timer; use clap::Parser; -use std::process; +use std::{fs, process}; -use cli::{CLI, Commands, PomodoroAction, TemplateAction}; +use cli::{CLI, Commands, PomodoroAction, ProjectsAction, TemplateAction}; use config::{Config, load_config, save_config}; use templates::{list_templates, load_template}; use timer::run_timer; @@ -108,6 +108,85 @@ fn process_command(mut cfg: Config) { }; } }, + Some(Commands::Project(project_action)) => match project_action.action { + ProjectsAction::Add { path } => { + let path = match fs::canonicalize(path) { + Ok(p) => p, + Err(err) => { + eprintln!("Error:\n{}", err); + process::exit(1); + } + }; + + if let None = path.file_name() { + eprintln!("Error:\nproject folder/file empty name."); + process::exit(1); + } + + if cfg.projects.contains(&path) { + eprintln!("Project already added."); + process::exit(1); + } + + cfg.projects.push(path.clone()); + + match save_config(&cfg) { + Ok(_) => { + eprintln!("Successfully add path: {}", path.display()); + } + Err(err) => { + eprintln!("Get error while saving config:\n{}", err); + process::exit(1); + } + } + } + ProjectsAction::Remove { project_name } => { + let mut is_deleted = false; + + for (idx, project) in cfg.projects.iter().enumerate() { + match project.file_name() { + Some(name) => { + if String::from(name.to_str().unwrap()) == project_name { + cfg.projects.remove(idx); + is_deleted = true; + break; + } + } + None => eprintln!( + "Error: project folder/file empty name '{}'", + project.display() + ), + } + } + + if !is_deleted { + eprintln!("Can't find project with name '{}'", project_name); + process::exit(1); + } + + match save_config(&cfg) { + Ok(_) => { + eprintln!("Successfully remove project: {}", project_name); + } + Err(err) => { + eprintln!("Get error while saving config:\n{}", err); + process::exit(1); + } + } + } + ProjectsAction::List => { + eprintln!("Projects:"); + for project in cfg.projects { + match project.file_name() { + Some(name) => eprintln!("{}", name.display()), + None => eprintln!( + "Error: project folder/file empty name '{}'", + project.display() + ), + } + } + } + }, None => { eprintln!("No command provided. Use --help for usage."); process::exit(1);