From c0c64590d081bd2aab0ca53006388c1d98db0fb4 Mon Sep 17 00:00:00 2001 From: dfayd0 <78728332+dfayd0@users.noreply.github.com> Date: Mon, 7 Jul 2025 22:08:41 +0200 Subject: [PATCH 1/3] feat(main): ask again for a start programming language --- src/main.rs | 17 +++++++++++++---- src/utils.rs | 22 ++++++++++++++++++++-- 2 files changed, 33 insertions(+), 6 deletions(-) diff --git a/src/main.rs b/src/main.rs index e7b22c8..4f76143 100644 --- a/src/main.rs +++ b/src/main.rs @@ -2,6 +2,7 @@ use clap::Parser; use leetcode_cli::{ utils::{ parse_programming_language, + prompt_for_language, spin_the_spinner, }, Cli, @@ -33,11 +34,19 @@ async fn main() -> Result<(), Box> { id, language, } => { - let default = &rcs.config.default_language.unwrap(); - let lang = match language { - Some(lang) => parse_programming_language(lang)?, - None => parse_programming_language(default)?, + let default_lang = &rcs + .config + .default_language + .unwrap_or("not found".to_owned()); + let mut lang = match language { + Some(lang) => parse_programming_language(lang), + None => parse_programming_language(default_lang), }; + while lang.is_err() { + lang = prompt_for_language() + .and_then(|lang| parse_programming_language(&lang)); + } + let lang = lang.unwrap(); let mut spin = spin_the_spinner("Starting problem setup..."); let start_problem = api_runner.start_problem(*id, lang).await; spin.stop(); diff --git a/src/utils.rs b/src/utils.rs index feb87da..249fb9f 100644 --- a/src/utils.rs +++ b/src/utils.rs @@ -34,7 +34,7 @@ pub fn write_to_file( pub fn parse_programming_language( lang: &str, -) -> Result { +) -> Result { match lang.to_ascii_lowercase().as_str() { "cpp" | "c++" => Ok(leetcoderustapi::ProgrammingLanguage::CPP), "java" => Ok(leetcoderustapi::ProgrammingLanguage::Java), @@ -62,7 +62,10 @@ pub fn parse_programming_language( "dart" => Ok(leetcoderustapi::ProgrammingLanguage::Dart), "pandas" => Ok(leetcoderustapi::ProgrammingLanguage::Pandas), "react" => Ok(leetcoderustapi::ProgrammingLanguage::React), - _ => Err(format!("Unsupported language: {}", lang)), + _ => Err(io::Error::new( + io::ErrorKind::InvalidInput, + format!("Unsupported language: {}", lang), + )), } } @@ -159,3 +162,18 @@ pub fn extension_programming_language( pub fn spin_the_spinner(message: &str) -> spinners::Spinner { spinners::Spinner::new(spinners::Spinners::Dots12, message.to_string()) } + +pub fn prompt_for_language() -> Result { + println!( + "Please enter a Leetcode programming language (cpp, rust, python, \ + ...):" + ); + let mut input = String::new(); + io::stdin().read_line(&mut input)?; + let trimmed = input.trim().to_string(); + if trimmed.is_empty() { + Err(io::Error::new(io::ErrorKind::InvalidInput, "No language entered")) + } else { + Ok(trimmed) + } +} From 7f216a2cc0fbc339bdbb3d818a911f9d805138c7 Mon Sep 17 00:00:00 2001 From: dfayd0 <78728332+dfayd0@users.noreply.github.com> Date: Sat, 12 Jul 2025 13:46:14 +0200 Subject: [PATCH 2/3] feat(start_problem): users are now prompted if programming language is unknown Signed-off-by: dfayd0 <78728332+dfayd0@users.noreply.github.com> --- src/leetcode_api_runner.rs | 29 ++++++++++++++++++++++++++++- src/main.rs | 13 +++++++++++-- src/utils.rs | 15 ++++++++++++--- 3 files changed, 51 insertions(+), 6 deletions(-) diff --git a/src/leetcode_api_runner.rs b/src/leetcode_api_runner.rs index a11e4cb..f0b4003 100644 --- a/src/leetcode_api_runner.rs +++ b/src/leetcode_api_runner.rs @@ -24,7 +24,14 @@ pub struct LeetcodeApiRunner { impl LeetcodeApiRunner { pub async fn new(rcs: &RuntimeConfigSetup) -> Self { - let api = UserApi::new(&rcs.config.leetcode_token).await.unwrap(); + let api = + UserApi::new(&rcs.config.leetcode_token) + .await + .expect(&format!( + "An error occurred while creating the API client. Check \ + your token in your configuration file: \n\n{}\n\n", + rcs.config_file.display() + )); LeetcodeApiRunner { rcs: rcs.clone(), api, @@ -46,6 +53,26 @@ impl LeetcodeApiRunner { Ok(format!("{} {}: {}\n{}", id, difficulty, title, description)) } + /// Fetches the problem name by its ID. + pub async fn get_problem_name(&self, id: u32) -> io::Result { + let pb = self.api.set_problem_by_id(id).await.unwrap(); + Ok(pb.description().unwrap().name.clone()) + } + + /// Fetches the available languages for a given problem ID. + pub async fn get_available_languages( + &self, id: &u32, + ) -> io::Result> { + let problem = self.api.set_problem_by_id(*id).await?; + + Ok(problem + .code_snippets() + .expect("No code snippets found.") + .iter() + .map(|snippet| snippet.langSlug.clone()) + .collect::>()) + } + pub async fn start_problem( &self, id: u32, language: ProgrammingLanguage, ) -> io::Result { diff --git a/src/main.rs b/src/main.rs index 4f76143..b923747 100644 --- a/src/main.rs +++ b/src/main.rs @@ -42,9 +42,18 @@ async fn main() -> Result<(), Box> { Some(lang) => parse_programming_language(lang), None => parse_programming_language(default_lang), }; + let mut spin = spin_the_spinner("Gathering problem info..."); + let problem_name = api_runner.get_problem_name(*id).await?; + let available_languages = + api_runner.get_available_languages(&id).await?; + spin.stop(); while lang.is_err() { - lang = prompt_for_language() - .and_then(|lang| parse_programming_language(&lang)); + lang = prompt_for_language( + id, + &problem_name, + &available_languages, + ) + .and_then(|lang| parse_programming_language(&lang)); } let lang = lang.unwrap(); let mut spin = spin_the_spinner("Starting problem setup..."); diff --git a/src/utils.rs b/src/utils.rs index 249fb9f..1cd08de 100644 --- a/src/utils.rs +++ b/src/utils.rs @@ -163,10 +163,19 @@ pub fn spin_the_spinner(message: &str) -> spinners::Spinner { spinners::Spinner::new(spinners::Spinners::Dots12, message.to_string()) } -pub fn prompt_for_language() -> Result { +pub fn prompt_for_language( + id: &u32, problem_name: &str, available_languages: &Vec, +) -> Result { println!( - "Please enter a Leetcode programming language (cpp, rust, python, \ - ...):" + "\nPlease enter a valid Leetcode programming language.\nHere is a \ + list of available languages for the problem {} - {}\n{}", + id, + problem_name, + available_languages + .iter() + .map(|l| l.to_string()) + .collect::>() + .join(", ") ); let mut input = String::new(); io::stdin().read_line(&mut input)?; From 96a34c5de4e0d6d602dd725aba3d4503dbf69c81 Mon Sep 17 00:00:00 2001 From: dfayd0 <78728332+dfayd0@users.noreply.github.com> Date: Sat, 12 Jul 2025 14:30:47 +0200 Subject: [PATCH 3/3] refactor: matching copilot PR comments Signed-off-by: dfayd0 <78728332+dfayd0@users.noreply.github.com> --- src/leetcode_api_runner.rs | 27 +++++++++++++++------------ src/main.rs | 9 +++++---- src/utils.rs | 2 +- 3 files changed, 21 insertions(+), 17 deletions(-) diff --git a/src/leetcode_api_runner.rs b/src/leetcode_api_runner.rs index f0b4003..4719915 100644 --- a/src/leetcode_api_runner.rs +++ b/src/leetcode_api_runner.rs @@ -23,19 +23,22 @@ pub struct LeetcodeApiRunner { } impl LeetcodeApiRunner { - pub async fn new(rcs: &RuntimeConfigSetup) -> Self { - let api = - UserApi::new(&rcs.config.leetcode_token) - .await - .expect(&format!( - "An error occurred while creating the API client. Check \ - your token in your configuration file: \n\n{}\n\n", - rcs.config_file.display() - )); - LeetcodeApiRunner { + pub async fn new(rcs: &RuntimeConfigSetup) -> Result { + Ok(LeetcodeApiRunner { rcs: rcs.clone(), - api, - } + api: UserApi::new(&rcs.config.leetcode_token).await.map_err( + |_| { + io::Error::new( + io::ErrorKind::NotConnected, + format!( + "An error occurred while creating the API client. \ + Check your token in your configuration file: {}", + rcs.config_file.display() + ), + ) + }, + )?, + }) } pub async fn get_problem_info(&self, id: u32) -> io::Result { diff --git a/src/main.rs b/src/main.rs index b923747..2d748ed 100644 --- a/src/main.rs +++ b/src/main.rs @@ -16,7 +16,7 @@ async fn main() -> Result<(), Box> { let cli = Cli::parse(); let mut rcs = RuntimeConfigSetup::new(); rcs.status()?; - let api_runner = LeetcodeApiRunner::new(&rcs).await; + let api_runner = LeetcodeApiRunner::new(&rcs).await?; match &cli.command { Commands::Info { @@ -34,13 +34,14 @@ async fn main() -> Result<(), Box> { id, language, } => { - let default_lang = &rcs + let default_lang = rcs .config .default_language - .unwrap_or("not found".to_owned()); + .clone() + .unwrap_or_else(|| "not found".to_string()); let mut lang = match language { Some(lang) => parse_programming_language(lang), - None => parse_programming_language(default_lang), + None => parse_programming_language(&default_lang), }; let mut spin = spin_the_spinner("Gathering problem info..."); let problem_name = api_runner.get_problem_name(*id).await?; diff --git a/src/utils.rs b/src/utils.rs index 1cd08de..25b1a10 100644 --- a/src/utils.rs +++ b/src/utils.rs @@ -164,7 +164,7 @@ pub fn spin_the_spinner(message: &str) -> spinners::Spinner { } pub fn prompt_for_language( - id: &u32, problem_name: &str, available_languages: &Vec, + id: &u32, problem_name: &str, available_languages: &[String], ) -> Result { println!( "\nPlease enter a valid Leetcode programming language.\nHere is a \