2024-04-10 20:51:02 -04:00
|
|
|
use anyhow::{Context, Result};
|
2023-08-25 17:18:01 -04:00
|
|
|
use clap::{Parser, Subcommand};
|
2024-04-07 18:36:26 -04:00
|
|
|
use std::{path::Path, process::exit};
|
2019-01-09 14:33:43 -05:00
|
|
|
|
2024-04-10 20:51:02 -04:00
|
|
|
mod app_state;
|
2024-04-04 21:04:53 -04:00
|
|
|
mod consts;
|
2024-03-28 16:06:36 -04:00
|
|
|
mod embedded;
|
2019-04-11 16:41:24 -04:00
|
|
|
mod exercise;
|
2024-03-28 20:29:41 -04:00
|
|
|
mod init;
|
2024-04-06 21:03:37 -04:00
|
|
|
mod list;
|
2024-04-09 13:37:39 -04:00
|
|
|
mod progress_bar;
|
2019-01-09 14:33:43 -05:00
|
|
|
mod run;
|
2024-04-06 19:17:53 -04:00
|
|
|
mod watch;
|
2018-05-14 12:41:58 -04:00
|
|
|
|
2024-04-07 18:36:26 -04:00
|
|
|
use self::{
|
2024-04-10 20:51:02 -04:00
|
|
|
app_state::AppState,
|
2024-04-07 18:36:26 -04:00
|
|
|
consts::WELCOME,
|
2024-04-10 20:51:02 -04:00
|
|
|
exercise::InfoFile,
|
|
|
|
init::init,
|
2024-04-09 20:12:50 -04:00
|
|
|
list::list,
|
2024-04-07 18:36:26 -04:00
|
|
|
run::run,
|
2024-04-09 20:12:50 -04:00
|
|
|
watch::{watch, WatchExit},
|
2024-04-07 18:36:26 -04:00
|
|
|
};
|
2024-04-07 13:01:08 -04:00
|
|
|
|
feat: Replace clap with argh
I’ve been wanting to do this for a while, but always procrastinated on it. We’ve been using Clap since the 2.0 rewrite, but Clap is known to be a fairly heavy library. Since Rustlings is usually peoples’ first contact with a Rust compilation, I think it’s in our best interests that this complation is as fast as possible. In effect, replacing Clap with the smaller, structopt-style `argh` reduces the amount of crates needing to be compiled from 82 to 60.
I also think this makes the code way easier to read, we don’t need to use Clap’s methods anymore, but can switch over to using pure Rust methods, e.g., switches are booleans, options are Option<String>s or the like, and subcommands are just structs.
2021-04-20 06:46:49 -04:00
|
|
|
/// Rustlings is a collection of small exercises to get you used to writing and reading Rust code
|
2023-08-25 17:18:01 -04:00
|
|
|
#[derive(Parser)]
|
|
|
|
#[command(version)]
|
feat: Replace clap with argh
I’ve been wanting to do this for a while, but always procrastinated on it. We’ve been using Clap since the 2.0 rewrite, but Clap is known to be a fairly heavy library. Since Rustlings is usually peoples’ first contact with a Rust compilation, I think it’s in our best interests that this complation is as fast as possible. In effect, replacing Clap with the smaller, structopt-style `argh` reduces the amount of crates needing to be compiled from 82 to 60.
I also think this makes the code way easier to read, we don’t need to use Clap’s methods anymore, but can switch over to using pure Rust methods, e.g., switches are booleans, options are Option<String>s or the like, and subcommands are just structs.
2021-04-20 06:46:49 -04:00
|
|
|
struct Args {
|
2023-08-25 17:18:01 -04:00
|
|
|
#[command(subcommand)]
|
|
|
|
command: Option<Subcommands>,
|
feat: Replace clap with argh
I’ve been wanting to do this for a while, but always procrastinated on it. We’ve been using Clap since the 2.0 rewrite, but Clap is known to be a fairly heavy library. Since Rustlings is usually peoples’ first contact with a Rust compilation, I think it’s in our best interests that this complation is as fast as possible. In effect, replacing Clap with the smaller, structopt-style `argh` reduces the amount of crates needing to be compiled from 82 to 60.
I also think this makes the code way easier to read, we don’t need to use Clap’s methods anymore, but can switch over to using pure Rust methods, e.g., switches are booleans, options are Option<String>s or the like, and subcommands are just structs.
2021-04-20 06:46:49 -04:00
|
|
|
}
|
|
|
|
|
2023-08-25 17:18:01 -04:00
|
|
|
#[derive(Subcommand)]
|
feat: Replace clap with argh
I’ve been wanting to do this for a while, but always procrastinated on it. We’ve been using Clap since the 2.0 rewrite, but Clap is known to be a fairly heavy library. Since Rustlings is usually peoples’ first contact with a Rust compilation, I think it’s in our best interests that this complation is as fast as possible. In effect, replacing Clap with the smaller, structopt-style `argh` reduces the amount of crates needing to be compiled from 82 to 60.
I also think this makes the code way easier to read, we don’t need to use Clap’s methods anymore, but can switch over to using pure Rust methods, e.g., switches are booleans, options are Option<String>s or the like, and subcommands are just structs.
2021-04-20 06:46:49 -04:00
|
|
|
enum Subcommands {
|
2024-03-28 20:29:41 -04:00
|
|
|
/// Initialize Rustlings
|
|
|
|
Init,
|
2024-04-10 20:51:02 -04:00
|
|
|
/// Run a single exercise. Runs the next pending exercise if the exercise name is not specified.
|
2023-08-25 17:18:01 -04:00
|
|
|
Run {
|
|
|
|
/// The name of the exercise
|
2024-04-10 20:51:02 -04:00
|
|
|
name: Option<String>,
|
2023-08-25 17:18:01 -04:00
|
|
|
},
|
2024-03-28 17:11:16 -04:00
|
|
|
/// Reset a single exercise
|
2023-08-25 17:18:01 -04:00
|
|
|
Reset {
|
|
|
|
/// The name of the exercise
|
|
|
|
name: String,
|
|
|
|
},
|
|
|
|
/// Return a hint for the given exercise
|
|
|
|
Hint {
|
|
|
|
/// The name of the exercise
|
|
|
|
name: String,
|
|
|
|
},
|
feat: Replace clap with argh
I’ve been wanting to do this for a while, but always procrastinated on it. We’ve been using Clap since the 2.0 rewrite, but Clap is known to be a fairly heavy library. Since Rustlings is usually peoples’ first contact with a Rust compilation, I think it’s in our best interests that this complation is as fast as possible. In effect, replacing Clap with the smaller, structopt-style `argh` reduces the amount of crates needing to be compiled from 82 to 60.
I also think this makes the code way easier to read, we don’t need to use Clap’s methods anymore, but can switch over to using pure Rust methods, e.g., switches are booleans, options are Option<String>s or the like, and subcommands are just structs.
2021-04-20 06:46:49 -04:00
|
|
|
}
|
|
|
|
|
2024-03-24 22:46:56 -04:00
|
|
|
fn main() -> Result<()> {
|
2023-08-25 17:18:01 -04:00
|
|
|
let args = Args::parse();
|
feat: Replace clap with argh
I’ve been wanting to do this for a while, but always procrastinated on it. We’ve been using Clap since the 2.0 rewrite, but Clap is known to be a fairly heavy library. Since Rustlings is usually peoples’ first contact with a Rust compilation, I think it’s in our best interests that this complation is as fast as possible. In effect, replacing Clap with the smaller, structopt-style `argh` reduces the amount of crates needing to be compiled from 82 to 60.
I also think this makes the code way easier to read, we don’t need to use Clap’s methods anymore, but can switch over to using pure Rust methods, e.g., switches are booleans, options are Option<String>s or the like, and subcommands are just structs.
2021-04-20 06:46:49 -04:00
|
|
|
|
2024-03-31 12:25:54 -04:00
|
|
|
which::which("cargo").context(
|
|
|
|
"Failed to find `cargo`.
|
2024-03-31 10:55:33 -04:00
|
|
|
Did you already install Rust?
|
2024-03-31 12:25:54 -04:00
|
|
|
Try running `cargo --version` to diagnose the problem.",
|
|
|
|
)?;
|
2019-11-11 11:15:14 -05:00
|
|
|
|
2024-04-09 15:23:02 -04:00
|
|
|
let mut info_file = InfoFile::parse()?;
|
|
|
|
info_file.exercises.shrink_to_fit();
|
2024-04-10 20:51:02 -04:00
|
|
|
let exercises = info_file.exercises;
|
2019-04-11 16:41:24 -04:00
|
|
|
|
2024-03-28 20:29:41 -04:00
|
|
|
if matches!(args.command, Some(Subcommands::Init)) {
|
2024-04-10 20:51:02 -04:00
|
|
|
init(&exercises).context("Initialization failed")?;
|
2024-03-28 20:52:05 -04:00
|
|
|
println!(
|
|
|
|
"\nDone initialization!\n
|
|
|
|
Run `cd rustlings` to go into the generated directory.
|
|
|
|
Then run `rustlings` for further instructions on getting started."
|
|
|
|
);
|
2024-03-28 20:29:41 -04:00
|
|
|
return Ok(());
|
|
|
|
} else if !Path::new("exercises").is_dir() {
|
|
|
|
println!(
|
2024-04-06 19:17:53 -04:00
|
|
|
"
|
|
|
|
{WELCOME}
|
|
|
|
|
|
|
|
The `exercises` directory wasn't found in the current directory.
|
2024-03-28 20:52:05 -04:00
|
|
|
If you are just starting with Rustlings, run the command `rustlings init` to initialize it."
|
2024-03-28 20:29:41 -04:00
|
|
|
);
|
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
|
2024-04-10 20:51:02 -04:00
|
|
|
let mut app_state = AppState::new(exercises);
|
2024-04-06 19:17:53 -04:00
|
|
|
|
2024-04-04 21:04:53 -04:00
|
|
|
match args.command {
|
2024-04-11 10:54:27 -04:00
|
|
|
None => loop {
|
2024-04-10 20:51:02 -04:00
|
|
|
match watch(&mut app_state)? {
|
2024-04-09 20:12:50 -04:00
|
|
|
WatchExit::Shutdown => break,
|
|
|
|
// It is much easier to exit the watch mode, launch the list mode and then restart
|
|
|
|
// the watch mode instead of trying to pause the watch threads and correct the
|
|
|
|
// watch state.
|
2024-04-10 20:51:02 -04:00
|
|
|
WatchExit::List => list(&mut app_state)?,
|
2024-04-09 20:12:50 -04:00
|
|
|
}
|
|
|
|
},
|
2024-03-28 20:29:41 -04:00
|
|
|
// `Init` is handled above.
|
2024-04-04 21:04:53 -04:00
|
|
|
Some(Subcommands::Init) => (),
|
|
|
|
Some(Subcommands::Run { name }) => {
|
2024-04-10 20:51:02 -04:00
|
|
|
if let Some(name) = name {
|
|
|
|
app_state.set_current_exercise_by_name(&name)?;
|
|
|
|
}
|
|
|
|
run(&mut app_state)?;
|
feat: Replace clap with argh
I’ve been wanting to do this for a while, but always procrastinated on it. We’ve been using Clap since the 2.0 rewrite, but Clap is known to be a fairly heavy library. Since Rustlings is usually peoples’ first contact with a Rust compilation, I think it’s in our best interests that this complation is as fast as possible. In effect, replacing Clap with the smaller, structopt-style `argh` reduces the amount of crates needing to be compiled from 82 to 60.
I also think this makes the code way easier to read, we don’t need to use Clap’s methods anymore, but can switch over to using pure Rust methods, e.g., switches are booleans, options are Option<String>s or the like, and subcommands are just structs.
2021-04-20 06:46:49 -04:00
|
|
|
}
|
2024-04-04 21:04:53 -04:00
|
|
|
Some(Subcommands::Reset { name }) => {
|
2024-04-10 20:51:02 -04:00
|
|
|
app_state.set_current_exercise_by_name(&name)?;
|
|
|
|
app_state.set_pending(app_state.current_exercise_ind())?;
|
|
|
|
let exercise = app_state.current_exercise();
|
2024-04-07 16:43:59 -04:00
|
|
|
exercise.reset()?;
|
2024-04-07 19:33:11 -04:00
|
|
|
println!("The exercise {exercise} has been reset!");
|
2022-08-17 10:31:53 -04:00
|
|
|
}
|
2024-04-04 21:04:53 -04:00
|
|
|
Some(Subcommands::Hint { name }) => {
|
2024-04-10 20:51:02 -04:00
|
|
|
app_state.set_current_exercise_by_name(&name)?;
|
|
|
|
println!("{}", app_state.current_exercise().hint);
|
feat: Replace clap with argh
I’ve been wanting to do this for a while, but always procrastinated on it. We’ve been using Clap since the 2.0 rewrite, but Clap is known to be a fairly heavy library. Since Rustlings is usually peoples’ first contact with a Rust compilation, I think it’s in our best interests that this complation is as fast as possible. In effect, replacing Clap with the smaller, structopt-style `argh` reduces the amount of crates needing to be compiled from 82 to 60.
I also think this makes the code way easier to read, we don’t need to use Clap’s methods anymore, but can switch over to using pure Rust methods, e.g., switches are booleans, options are Option<String>s or the like, and subcommands are just structs.
2021-04-20 06:46:49 -04:00
|
|
|
}
|
2018-11-26 05:10:38 -05:00
|
|
|
}
|
2024-03-24 22:46:56 -04:00
|
|
|
|
|
|
|
Ok(())
|
2018-05-06 12:59:50 -04:00
|
|
|
}
|