diff --git a/CHANGELOG.md b/CHANGELOG.md
index a2085b91bc..b9826cf002 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## Unreleased
+
+### Changed
+
+- Upgrade to Rust edition 2024
+- Raise the minimum supported Rust version to `1.85`
+
## 6.4.0 (2024-11-11)
diff --git a/Cargo.lock b/Cargo.lock
index 32750f0399..3c340b645f 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -84,9 +84,9 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
[[package]]
name = "clap"
-version = "4.5.26"
+version = "4.5.30"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "a8eb5e908ef3a6efbe1ed62520fb7287959888c88485abe072543190ecc66783"
+checksum = "92b7b18d71fad5313a1e320fa9897994228ce274b60faa4d694fe0ea89cd9e6d"
dependencies = [
"clap_builder",
"clap_derive",
@@ -94,9 +94,9 @@ dependencies = [
[[package]]
name = "clap_builder"
-version = "4.5.26"
+version = "4.5.30"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "96b01801b5fc6a0a232407abc821660c9c6d25a1cafc0d4f85f29fb8d9afc121"
+checksum = "a35db2071778a7344791a4fb4f95308b5673d219dee3ae348b86642574ecc90c"
dependencies = [
"anstream",
"anstyle",
@@ -106,9 +106,9 @@ dependencies = [
[[package]]
name = "clap_derive"
-version = "4.5.24"
+version = "4.5.28"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "54b755194d6389280185988721fffba69495eed5ee9feeee9a599b53db80318c"
+checksum = "bf4ced95c6f4a675af3da73304b9ac4ed991640c36374e4b46795c49e17cf1ed"
dependencies = [
"heck",
"proc-macro2",
@@ -155,9 +155,9 @@ dependencies = [
[[package]]
name = "equivalent"
-version = "1.0.1"
+version = "1.0.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5"
+checksum = "877a4ace8713b0bcf2a4e7eec82529c029f1d0619886d18145fea96c3ffe5c0f"
[[package]]
name = "errno"
@@ -198,13 +198,14 @@ dependencies = [
[[package]]
name = "getrandom"
-version = "0.2.15"
+version = "0.3.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "c4567c8db10ae91089c99af84c68c38da3ec2f087c3f82960bcdbf3656b6f4d7"
+checksum = "43a49c392881ce6d5c3b8cb70f98717b7c07aabbdff06687b9030dbfbe2725f8"
dependencies = [
"cfg-if",
"libc",
- "wasi",
+ "wasi 0.13.3+wasi-0.2.2",
+ "windows-targets",
]
[[package]]
@@ -221,9 +222,9 @@ checksum = "2304e00983f87ffb38b55b444b5e3b60a884b5d30c0fca7d82fe33449bbe55ea"
[[package]]
name = "indexmap"
-version = "2.7.0"
+version = "2.7.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "62f822373a4fe84d4bb149bf54e584a7f4abec90e072ed49cda0edea5b95471f"
+checksum = "8c9c992b02b5b4c94ea26e32fe5bccb7aa7d9f390ab5c1221ff895bc7ea8b652"
dependencies = [
"equivalent",
"hashbrown",
@@ -334,7 +335,7 @@ checksum = "2886843bf800fba2e3377cff24abf6379b4c4d5c6681eaf9ea5b0d15090450bd"
dependencies = [
"libc",
"log",
- "wasi",
+ "wasi 0.11.0+wasi-snapshot-preview1",
"windows-sys 0.52.0",
]
@@ -365,9 +366,9 @@ checksum = "5e0826a989adedc2a244799e823aece04662b66609d96af8dff7ac6df9a8925d"
[[package]]
name = "once_cell"
-version = "1.20.2"
+version = "1.20.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "1261fe7e33c73b354eab43b1273a57c8f967d0391e80353e51f764ac02cf6775"
+checksum = "945462a4b81e43c4e3ba96bd7b49d834c6f61198356aa858733bc4acf3cbe62e"
[[package]]
name = "os_pipe"
@@ -431,9 +432,9 @@ dependencies = [
[[package]]
name = "rustix"
-version = "0.38.43"
+version = "0.38.44"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "a78891ee6bf2340288408954ac787aa063d8e8817e9f53abb37c695c6d834ef6"
+checksum = "fdb5bc1ae2baa591800df16c9ca78619bf65c0488b41b96ccec5d11220d8c154"
dependencies = [
"bitflags 2.8.0",
"errno",
@@ -470,9 +471,9 @@ dependencies = [
[[package]]
name = "ryu"
-version = "1.0.18"
+version = "1.0.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "f3cb5ba0dc43242ce17de99c180e96db90b235b8a9fdc9543c96d2209116bd9f"
+checksum = "6ea1a2d0a644769cc99faa24c3ad26b379b786fe7c36fd3c546254801650e6dd"
[[package]]
name = "same-file"
@@ -511,9 +512,9 @@ dependencies = [
[[package]]
name = "serde_json"
-version = "1.0.135"
+version = "1.0.138"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "2b0d7ba2887406110130a978386c4e1befb98c674b4fba677954e4db976630d9"
+checksum = "d434192e7da787e94a6ea7e9670b26a036d0ca41e0b7efb2676dd32bae872949"
dependencies = [
"itoa",
"memchr",
@@ -562,9 +563,9 @@ dependencies = [
[[package]]
name = "smallvec"
-version = "1.13.2"
+version = "1.14.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "3c5e1a9a646d36c3599cd173a41282daf47c44583ad367b8e6837255952e5c67"
+checksum = "7fcf8323ef1faaee30a44a340193b1ac6814fd9b7b4e88e9d4519a3e4abe1cfd"
[[package]]
name = "strsim"
@@ -574,9 +575,9 @@ checksum = "7da8b5736845d9f2fcb837ea5d9e2628564b3b043a70948a3f0b778838c5fb4f"
[[package]]
name = "syn"
-version = "2.0.96"
+version = "2.0.98"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "d5d0adab1ae378d7f53bdebc67a39f1f151407ef230f0ce2883572f5d8985c80"
+checksum = "36147f1a48ae0ec2b5b3bc5b537d267457555a10dc06f3dbc8cb11ba3006d3b1"
dependencies = [
"proc-macro2",
"quote",
@@ -585,9 +586,9 @@ dependencies = [
[[package]]
name = "tempfile"
-version = "3.15.0"
+version = "3.17.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "9a8a559c81686f576e8cd0290cd2a24a2a9ad80c98b3478856500fcbd7acd704"
+checksum = "22e5a0acb1f3f55f65cc4a866c361b2fb2a0ff6366785ae6fbb5f85df07ba230"
dependencies = [
"cfg-if",
"fastrand",
@@ -608,9 +609,9 @@ dependencies = [
[[package]]
name = "toml_edit"
-version = "0.22.22"
+version = "0.22.24"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "4ae48d6208a266e853d946088ed816055e556cc6028c5e8e2b84d9fa5dd7c7f5"
+checksum = "17b4795ff5edd201c7cd6dca065ae59972ce77d1b80fa0a84d94950ece7d1474"
dependencies = [
"indexmap",
"serde",
@@ -621,9 +622,9 @@ dependencies = [
[[package]]
name = "unicode-ident"
-version = "1.0.14"
+version = "1.0.16"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "adb9e6ca4f869e1180728b7950e35922a7fc6397f7b641499e8f3ef06e50dc83"
+checksum = "a210d160f08b701c8721ba1c726c11662f877ea6b7094007e1ca9a1041945034"
[[package]]
name = "utf8parse"
@@ -647,6 +648,15 @@ version = "0.11.0+wasi-snapshot-preview1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423"
+[[package]]
+name = "wasi"
+version = "0.13.3+wasi-0.2.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "26816d2e1a4a36a2940b96c5296ce403917633dff8f3440e9b236ed6f6bacad2"
+dependencies = [
+ "wit-bindgen-rt",
+]
+
[[package]]
name = "winapi"
version = "0.3.9"
@@ -762,9 +772,18 @@ checksum = "589f6da84c646204747d1270a2a5661ea66ed1cced2631d546fdfb155959f9ec"
[[package]]
name = "winnow"
-version = "0.6.24"
+version = "0.7.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "c8d71a593cc5c42ad7876e2c1fda56f314f3754c084128833e64f1345ff8a03a"
+checksum = "59690dea168f2198d1a3b0cac23b8063efcd11012f10ae4698f284808c8ef603"
dependencies = [
"memchr",
]
+
+[[package]]
+name = "wit-bindgen-rt"
+version = "0.33.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "3268f3d866458b787f390cf61f4bbb563b922d091359f9608842999eaee3943c"
+dependencies = [
+ "bitflags 2.8.0",
+]
diff --git a/Cargo.toml b/Cargo.toml
index c0eb1d126b..e9b29eca05 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -15,12 +15,12 @@ authors = [
]
repository = "https://github.com/rust-lang/rustlings"
license = "MIT"
-edition = "2021" # On Update: Update the edition of the `rustfmt` command that checks the solutions.
-rust-version = "1.80"
+edition = "2024" # On Update: Update the edition of the `rustfmt` command that checks the solutions.
+rust-version = "1.85"
[workspace.dependencies]
serde = { version = "1.0.217", features = ["derive"] }
-toml_edit = { version = "0.22.22", default-features = false, features = ["parse", "serde"] }
+toml_edit = { version = "0.22.24", default-features = false, features = ["parse", "serde"] }
[package]
name = "rustlings"
@@ -47,20 +47,20 @@ include = [
[dependencies]
anyhow = "1.0.95"
-clap = { version = "4.5.26", features = ["derive"] }
+clap = { version = "4.5.30", features = ["derive"] }
crossterm = { version = "0.28.1", default-features = false, features = ["windows", "events"] }
notify = "8.0.0"
os_pipe = "1.2.1"
rustlings-macros = { path = "rustlings-macros", version = "=6.4.0" }
-serde_json = "1.0.135"
+serde_json = "1.0.138"
serde.workspace = true
toml_edit.workspace = true
[target.'cfg(not(windows))'.dependencies]
-rustix = { version = "0.38.43", default-features = false, features = ["std", "stdio", "termios"] }
+rustix = { version = "0.38.44", default-features = false, features = ["std", "stdio", "termios"] }
[dev-dependencies]
-tempfile = "3.15.0"
+tempfile = "3.17.1"
[profile.release]
panic = "abort"
diff --git a/dev/Cargo.toml b/dev/Cargo.toml
index 29a557a019..ae380d1751 100644
--- a/dev/Cargo.toml
+++ b/dev/Cargo.toml
@@ -192,7 +192,7 @@ bin = [
[package]
name = "exercises"
-edition = "2021"
+edition = "2024"
# Don't publish the exercises on crates.io!
publish = false
diff --git a/release-hook.sh b/release-hook.sh
index 8da5636dea..db3d86eecd 100755
--- a/release-hook.sh
+++ b/release-hook.sh
@@ -13,4 +13,4 @@ cargo test --workspace --all-targets
cargo run -- dev check --require-solutions
# MSRV
-cargo +1.80 run -- dev check --require-solutions
+cargo +1.85 run -- dev check --require-solutions
diff --git a/solutions/13_error_handling/errors2.rs b/solutions/13_error_handling/errors2.rs
index 0597c8c9d9..f0e144e746 100644
--- a/solutions/13_error_handling/errors2.rs
+++ b/solutions/13_error_handling/errors2.rs
@@ -16,7 +16,7 @@
use std::num::ParseIntError;
-#[allow(unused_variables)]
+#[allow(unused_variables, clippy::question_mark)]
fn total_cost(item_quantity: &str) -> Result {
let processing_fee = 1;
let cost_per_item = 5;
diff --git a/src/app_state.rs b/src/app_state.rs
index 5979150faa..d1c45d4963 100644
--- a/src/app_state.rs
+++ b/src/app_state.rs
@@ -1,11 +1,11 @@
-use anyhow::{bail, Context, Error, Result};
-use crossterm::{cursor, terminal, QueueableCommand};
+use anyhow::{Context, Error, Result, bail};
+use crossterm::{QueueableCommand, cursor, terminal};
use std::{
collections::HashSet,
env,
fs::{File, OpenOptions},
io::{Read, Seek, StdoutLock, Write},
- path::{Path, MAIN_SEPARATOR_STR},
+ path::{MAIN_SEPARATOR_STR, Path},
process::{Command, Stdio},
sync::{
atomic::{AtomicUsize, Ordering::Relaxed},
@@ -427,32 +427,34 @@ impl AppState {
let next_exercise_ind = &next_exercise_ind;
let slf = &self;
thread::Builder::new()
- .spawn_scoped(s, move || loop {
- let exercise_ind = next_exercise_ind.fetch_add(1, Relaxed);
- let Some(exercise) = slf.exercises.get(exercise_ind) else {
- // No more exercises.
- break;
- };
-
- if exercise_progress_sender
- .send((exercise_ind, CheckProgress::Checking))
- .is_err()
- {
- break;
- };
-
- let success = exercise.run_exercise(None, &slf.cmd_runner);
- let progress = match success {
- Ok(true) => CheckProgress::Done,
- Ok(false) => CheckProgress::Pending,
- Err(_) => CheckProgress::None,
- };
-
- if exercise_progress_sender
- .send((exercise_ind, progress))
- .is_err()
- {
- break;
+ .spawn_scoped(s, move || {
+ loop {
+ let exercise_ind = next_exercise_ind.fetch_add(1, Relaxed);
+ let Some(exercise) = slf.exercises.get(exercise_ind) else {
+ // No more exercises.
+ break;
+ };
+
+ if exercise_progress_sender
+ .send((exercise_ind, CheckProgress::Checking))
+ .is_err()
+ {
+ break;
+ };
+
+ let success = exercise.run_exercise(None, &slf.cmd_runner);
+ let progress = match success {
+ Ok(true) => CheckProgress::Done,
+ Ok(false) => CheckProgress::Pending,
+ Err(_) => CheckProgress::None,
+ };
+
+ if exercise_progress_sender
+ .send((exercise_ind, progress))
+ .is_err()
+ {
+ break;
+ }
}
})
.context("Failed to spawn a thread to check all exercises")?;
diff --git a/src/cargo_toml.rs b/src/cargo_toml.rs
index 8d417ffa93..e966809f35 100644
--- a/src/cargo_toml.rs
+++ b/src/cargo_toml.rs
@@ -74,13 +74,13 @@ pub fn updated_cargo_toml(
let (bins_start_ind, bins_end_ind) = bins_start_end_ind(current_cargo_toml)?;
let mut updated_cargo_toml = Vec::with_capacity(BINS_BUFFER_CAPACITY);
- updated_cargo_toml.extend_from_slice(current_cargo_toml[..bins_start_ind].as_bytes());
+ updated_cargo_toml.extend_from_slice(¤t_cargo_toml.as_bytes()[..bins_start_ind]);
append_bins(
&mut updated_cargo_toml,
exercise_infos,
exercise_path_prefix,
);
- updated_cargo_toml.extend_from_slice(current_cargo_toml[bins_end_ind..].as_bytes());
+ updated_cargo_toml.extend_from_slice(¤t_cargo_toml.as_bytes()[bins_end_ind..]);
Ok(updated_cargo_toml)
}
diff --git a/src/cmd.rs b/src/cmd.rs
index 30f988a6de..551df8f0ae 100644
--- a/src/cmd.rs
+++ b/src/cmd.rs
@@ -1,4 +1,4 @@
-use anyhow::{bail, Context, Result};
+use anyhow::{Context, Result, bail};
use serde::Deserialize;
use std::{
io::Read,
diff --git a/src/dev.rs b/src/dev.rs
index 8af40d6943..354d77c4b1 100644
--- a/src/dev.rs
+++ b/src/dev.rs
@@ -1,4 +1,4 @@
-use anyhow::{bail, Context, Result};
+use anyhow::{Context, Result, bail};
use clap::Subcommand;
use std::path::PathBuf;
diff --git a/src/dev/check.rs b/src/dev/check.rs
index 956c2be2de..aacc2f440f 100644
--- a/src/dev/check.rs
+++ b/src/dev/check.rs
@@ -1,8 +1,8 @@
-use anyhow::{anyhow, bail, Context, Error, Result};
+use anyhow::{Context, Error, Result, anyhow, bail};
use std::{
cmp::Ordering,
collections::HashSet,
- fs::{self, read_dir, OpenOptions},
+ fs::{self, OpenOptions, read_dir},
io::{self, Read, Write},
path::{Path, PathBuf},
process::{Command, Stdio},
@@ -10,11 +10,11 @@ use std::{
};
use crate::{
- cargo_toml::{append_bins, bins_start_end_ind, BINS_BUFFER_CAPACITY},
+ CURRENT_FORMAT_VERSION,
+ cargo_toml::{BINS_BUFFER_CAPACITY, append_bins, bins_start_end_ind},
cmd::CmdRunner,
- exercise::{RunnableExercise, OUTPUT_CAPACITY},
+ exercise::{OUTPUT_CAPACITY, RunnableExercise},
info_file::{ExerciseInfo, InfoFile},
- CURRENT_FORMAT_VERSION,
};
const MAX_N_EXERCISES: usize = 999;
@@ -42,10 +42,14 @@ fn check_cargo_toml(
if old_bins != new_bins {
if cfg!(debug_assertions) {
- bail!("The file `dev/Cargo.toml` is outdated. Run `cargo run -- dev update` to update it. Then run `cargo run -- dev check` again");
+ bail!(
+ "The file `dev/Cargo.toml` is outdated. Run `cargo run -- dev update` to update it. Then run `cargo run -- dev check` again"
+ );
}
- bail!("The file `Cargo.toml` is outdated. Run `rustlings dev update` to update it. Then run `rustlings dev check` again");
+ bail!(
+ "The file `Cargo.toml` is outdated. Run `rustlings dev update` to update it. Then run `rustlings dev check` again"
+ );
}
Ok(())
@@ -63,7 +67,9 @@ fn check_info_file_exercises(info_file: &InfoFile) -> Result> {
bail!("Found an empty exercise name in `info.toml`");
}
if name.len() > MAX_EXERCISE_NAME_LEN {
- bail!("The length of the exercise name `{name}` is bigger than the maximum {MAX_EXERCISE_NAME_LEN}");
+ bail!(
+ "The length of the exercise name `{name}` is bigger than the maximum {MAX_EXERCISE_NAME_LEN}"
+ );
}
if let Some(c) = forbidden_char(name) {
bail!("Char `{c}` in the exercise name `{name}` is not allowed");
@@ -79,7 +85,9 @@ fn check_info_file_exercises(info_file: &InfoFile) -> Result> {
}
if exercise_info.hint.trim_ascii().is_empty() {
- bail!("The exercise `{name}` has an empty hint. Please provide a hint or at least tell the user why a hint isn't needed for this exercise");
+ bail!(
+ "The exercise `{name}` has an empty hint. Please provide a hint or at least tell the user why a hint isn't needed for this exercise"
+ );
}
if !names.insert(name) {
@@ -96,20 +104,28 @@ fn check_info_file_exercises(info_file: &InfoFile) -> Result> {
.with_context(|| format!("Failed to read the file {path}"))?;
if !file_buf.contains("fn main()") {
- bail!("The `main` function is missing in the file `{path}`.\nCreate at least an empty `main` function to avoid language server errors");
+ bail!(
+ "The `main` function is missing in the file `{path}`.\nCreate at least an empty `main` function to avoid language server errors"
+ );
}
if !file_buf.contains("// TODO") {
- bail!("Didn't find any `// TODO` comment in the file `{path}`.\nYou need to have at least one such comment to guide the user.");
+ bail!(
+ "Didn't find any `// TODO` comment in the file `{path}`.\nYou need to have at least one such comment to guide the user."
+ );
}
let contains_tests = file_buf.contains("#[test]\n");
if exercise_info.test {
if !contains_tests {
- bail!("The file `{path}` doesn't contain any tests. If you don't want to add tests to this exercise, set `test = false` for this exercise in the `info.toml` file");
+ bail!(
+ "The file `{path}` doesn't contain any tests. If you don't want to add tests to this exercise, set `test = false` for this exercise in the `info.toml` file"
+ );
}
} else if contains_tests {
- bail!("The file `{path}` contains tests annotated with `#[test]` but the exercise `{name}` has `test = false` in the `info.toml` file");
+ bail!(
+ "The file `{path}` contains tests annotated with `#[test]` but the exercise `{name}` has `test = false` in the `info.toml` file"
+ );
}
file_buf.clear();
@@ -125,7 +141,10 @@ fn check_info_file_exercises(info_file: &InfoFile) -> Result> {
// Only one level of directory nesting is allowed.
fn check_unexpected_files(dir: &str, allowed_rust_files: &HashSet) -> Result<()> {
let unexpected_file = |path: &Path| {
- anyhow!("Found the file `{}`. Only `README.md` and Rust files related to an exercise in `info.toml` are allowed in the `{dir}` directory", path.display())
+ anyhow!(
+ "Found the file `{}`. Only `README.md` and Rust files related to an exercise in `info.toml` are allowed in the `{dir}` directory",
+ path.display()
+ )
};
for entry in read_dir(dir).with_context(|| format!("Failed to open the `{dir}` directory"))? {
@@ -154,7 +173,10 @@ fn check_unexpected_files(dir: &str, allowed_rust_files: &HashSet) -> R
let path = entry.path();
if !entry.file_type().unwrap().is_file() {
- bail!("Found `{}` but expected only files. Only one level of exercise nesting is allowed", path.display());
+ bail!(
+ "Found `{}` but expected only files. Only one level of exercise nesting is allowed",
+ path.display()
+ );
}
let file_name = path.file_name().unwrap();
@@ -224,8 +246,12 @@ fn check_exercises_unsolved(
fn check_exercises(info_file: &'static InfoFile, cmd_runner: &'static CmdRunner) -> Result<()> {
match info_file.format_version.cmp(&CURRENT_FORMAT_VERSION) {
- Ordering::Less => bail!("`format_version` < {CURRENT_FORMAT_VERSION} (supported version)\nPlease migrate to the latest format version"),
- Ordering::Greater => bail!("`format_version` > {CURRENT_FORMAT_VERSION} (supported version)\nTry updating the Rustlings program"),
+ Ordering::Less => bail!(
+ "`format_version` < {CURRENT_FORMAT_VERSION} (supported version)\nPlease migrate to the latest format version"
+ ),
+ Ordering::Greater => bail!(
+ "`format_version` > {CURRENT_FORMAT_VERSION} (supported version)\nTry updating the Rustlings program"
+ ),
Ordering::Equal => (),
}
diff --git a/src/dev/new.rs b/src/dev/new.rs
index 154cd2247b..ba3517f5b8 100644
--- a/src/dev/new.rs
+++ b/src/dev/new.rs
@@ -1,4 +1,4 @@
-use anyhow::{bail, Context, Result};
+use anyhow::{Context, Result, bail};
use std::{
env::set_current_dir,
fs::{self, create_dir},
@@ -6,7 +6,7 @@ use std::{
process::Command,
};
-use crate::{init::RUST_ANALYZER_TOML, CURRENT_FORMAT_VERSION};
+use crate::{CURRENT_FORMAT_VERSION, init::RUST_ANALYZER_TOML};
// Create a directory relative to the current directory and print its path.
fn create_rel_dir(dir_name: &str, current_dir: &str) -> Result<()> {
@@ -55,7 +55,9 @@ pub fn new(path: &Path, no_git: bool) -> Result<()> {
write_rel_file(
"info.toml",
&dir_path_str,
- format!("{INFO_FILE_BEFORE_FORMAT_VERSION}{CURRENT_FORMAT_VERSION}{INFO_FILE_AFTER_FORMAT_VERSION}"),
+ format!(
+ "{INFO_FILE_BEFORE_FORMAT_VERSION}{CURRENT_FORMAT_VERSION}{INFO_FILE_AFTER_FORMAT_VERSION}"
+ ),
)?;
write_rel_file("Cargo.toml", &dir_path_str, CARGO_TOML)?;
@@ -130,7 +132,7 @@ bin = []
[package]
name = "exercises"
-edition = "2021"
+edition = "2024"
# Don't publish the exercises on crates.io!
publish = false
diff --git a/src/exercise.rs b/src/exercise.rs
index 849082847a..fdfbc4f6ea 100644
--- a/src/exercise.rs
+++ b/src/exercise.rs
@@ -1,13 +1,13 @@
use anyhow::Result;
use crossterm::{
- style::{Attribute, Color, ResetColor, SetAttribute, SetForegroundColor},
QueueableCommand,
+ style::{Attribute, Color, ResetColor, SetAttribute, SetForegroundColor},
};
use std::io::{self, StdoutLock, Write};
use crate::{
cmd::CmdRunner,
- term::{self, terminal_file_link, write_ansi, CountedWrite},
+ term::{self, CountedWrite, terminal_file_link, write_ansi},
};
/// The initial capacity of the output buffer.
diff --git a/src/info_file.rs b/src/info_file.rs
index fdc8f0f35c..ec61f8ad0b 100644
--- a/src/info_file.rs
+++ b/src/info_file.rs
@@ -1,4 +1,4 @@
-use anyhow::{bail, Context, Error, Result};
+use anyhow::{Context, Error, Result, bail};
use serde::Deserialize;
use std::{fs, io::ErrorKind};
diff --git a/src/init.rs b/src/init.rs
index ce49bb65fa..208425c2a3 100644
--- a/src/init.rs
+++ b/src/init.rs
@@ -1,7 +1,7 @@
-use anyhow::{bail, Context, Result};
+use anyhow::{Context, Result, bail};
use crossterm::{
- style::{Attribute, Color, ResetColor, SetAttribute, SetForegroundColor},
QueueableCommand,
+ style::{Attribute, Color, ResetColor, SetAttribute, SetForegroundColor},
};
use serde::Deserialize;
use std::{
@@ -57,7 +57,9 @@ pub fn init() -> Result<()> {
if !workspace_manifest_content.contains("[workspace]\n")
&& !workspace_manifest_content.contains("workspace.")
{
- bail!("The current directory is already part of a Cargo project.\nPlease initialize Rustlings in a different directory");
+ bail!(
+ "The current directory is already part of a Cargo project.\nPlease initialize Rustlings in a different directory"
+ );
}
stdout.write_all(b"This command will create the directory `rustlings/` as a member of this Cargo workspace.\nPress ENTER to continue ")?;
@@ -75,7 +77,9 @@ pub fn init() -> Result<()> {
.stdout(Stdio::null())
.status()?;
if !status.success() {
- bail!("Failed to initialize a new Cargo workspace member.\nPlease initialize Rustlings in a different directory");
+ bail!(
+ "Failed to initialize a new Cargo workspace member.\nPlease initialize Rustlings in a different directory"
+ );
}
stdout.write_all(b"The directory `rustlings` has been added to `workspace.members` in the `Cargo.toml` file of this Cargo workspace.\n")?;
diff --git a/src/list.rs b/src/list.rs
index 9f243a1724..a2eee9e16a 100644
--- a/src/list.rs
+++ b/src/list.rs
@@ -1,14 +1,13 @@
use anyhow::{Context, Result};
use crossterm::{
- cursor,
+ QueueableCommand, cursor,
event::{
self, DisableMouseCapture, EnableMouseCapture, Event, KeyCode, KeyEventKind, MouseEventKind,
},
terminal::{
- disable_raw_mode, enable_raw_mode, DisableLineWrap, EnableLineWrap, EnterAlternateScreen,
- LeaveAlternateScreen,
+ DisableLineWrap, EnableLineWrap, EnterAlternateScreen, LeaveAlternateScreen,
+ disable_raw_mode, enable_raw_mode,
},
- QueueableCommand,
};
use std::io::{self, StdoutLock, Write};
diff --git a/src/list/state.rs b/src/list/state.rs
index 0670fa46a8..ae65ec2be9 100644
--- a/src/list/state.rs
+++ b/src/list/state.rs
@@ -1,11 +1,11 @@
use anyhow::{Context, Result};
use crossterm::{
+ QueueableCommand,
cursor::{MoveTo, MoveToNextLine},
style::{
Attribute, Attributes, Color, ResetColor, SetAttribute, SetAttributes, SetForegroundColor,
},
terminal::{self, BeginSynchronizedUpdate, Clear, ClearType, EndSynchronizedUpdate},
- QueueableCommand,
};
use std::{
fmt::Write as _,
@@ -15,7 +15,7 @@ use std::{
use crate::{
app_state::AppState,
exercise::Exercise,
- term::{progress_bar, CountedWrite, MaxLenWriter},
+ term::{CountedWrite, MaxLenWriter, progress_bar},
};
use super::scroll_state::ScrollState;
diff --git a/src/main.rs b/src/main.rs
index eeb1883edd..6688e3e6f3 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -1,4 +1,4 @@
-use anyhow::{bail, Context, Result};
+use anyhow::{Context, Result, bail};
use app_state::StateFileStatus;
use clap::{Parser, Subcommand};
use std::{
diff --git a/src/run.rs b/src/run.rs
index ac8b26ad76..6f4f099b47 100644
--- a/src/run.rs
+++ b/src/run.rs
@@ -1,7 +1,7 @@
use anyhow::Result;
use crossterm::{
- style::{Color, ResetColor, SetForegroundColor},
QueueableCommand,
+ style::{Color, ResetColor, SetForegroundColor},
};
use std::{
io::{self, Write},
@@ -10,7 +10,7 @@ use std::{
use crate::{
app_state::{AppState, ExercisesProgress},
- exercise::{solution_link_line, RunnableExercise, OUTPUT_CAPACITY},
+ exercise::{OUTPUT_CAPACITY, RunnableExercise, solution_link_line},
};
pub fn run(app_state: &mut AppState) -> Result {
diff --git a/src/term.rs b/src/term.rs
index cb0a07ceaf..1e08c84f64 100644
--- a/src/term.rs
+++ b/src/term.rs
@@ -1,8 +1,8 @@
use crossterm::{
+ Command, QueueableCommand,
cursor::MoveTo,
style::{Attribute, Color, ResetColor, SetAttribute, SetForegroundColor},
terminal::{Clear, ClearType},
- Command, QueueableCommand,
};
use std::{
fmt, fs,
diff --git a/src/watch/notify_event.rs b/src/watch/notify_event.rs
index 2051e544bf..9c05f10dad 100644
--- a/src/watch/notify_event.rs
+++ b/src/watch/notify_event.rs
@@ -1,18 +1,18 @@
use anyhow::{Context, Result};
use notify::{
- event::{AccessKind, AccessMode, MetadataKind, ModifyKind, RenameMode},
Event, EventKind,
+ event::{AccessKind, AccessMode, MetadataKind, ModifyKind, RenameMode},
};
use std::{
sync::{
atomic::Ordering::Relaxed,
- mpsc::{sync_channel, RecvTimeoutError, Sender, SyncSender},
+ mpsc::{RecvTimeoutError, Sender, SyncSender, sync_channel},
},
thread,
time::Duration,
};
-use super::{WatchEvent, EXERCISE_RUNNING};
+use super::{EXERCISE_RUNNING, WatchEvent};
const DEBOUNCE_DURATION: Duration = Duration::from_millis(200);
diff --git a/src/watch/state.rs b/src/watch/state.rs
index 5263bc5788..2413becd28 100644
--- a/src/watch/state.rs
+++ b/src/watch/state.rs
@@ -1,24 +1,25 @@
use anyhow::{Context, Result};
use crossterm::{
+ QueueableCommand,
style::{
Attribute, Attributes, Color, ResetColor, SetAttribute, SetAttributes, SetForegroundColor,
},
- terminal, QueueableCommand,
+ terminal,
};
use std::{
io::{self, Read, StdoutLock, Write},
- sync::mpsc::{sync_channel, Sender, SyncSender},
+ sync::mpsc::{Sender, SyncSender, sync_channel},
thread,
};
use crate::{
app_state::{AppState, ExercisesProgress},
clear_terminal,
- exercise::{solution_link_line, RunnableExercise, OUTPUT_CAPACITY},
+ exercise::{OUTPUT_CAPACITY, RunnableExercise, solution_link_line},
term::progress_bar,
};
-use super::{terminal_event::terminal_event_handler, InputPauseGuard, WatchEvent};
+use super::{InputPauseGuard, WatchEvent, terminal_event::terminal_event_handler};
const HEADING_ATTRIBUTES: Attributes = Attributes::none()
.with(Attribute::Bold)
diff --git a/src/watch/terminal_event.rs b/src/watch/terminal_event.rs
index 48411db0f7..2400a3df54 100644
--- a/src/watch/terminal_event.rs
+++ b/src/watch/terminal_event.rs
@@ -4,7 +4,7 @@ use std::sync::{
mpsc::{Receiver, Sender},
};
-use super::{WatchEvent, EXERCISE_RUNNING};
+use super::{EXERCISE_RUNNING, WatchEvent};
pub enum InputEvent {
Next,
diff --git a/tests/test_exercises/dev/Cargo.toml b/tests/test_exercises/dev/Cargo.toml
index 01fe7c10d0..74dcc20ade 100644
--- a/tests/test_exercises/dev/Cargo.toml
+++ b/tests/test_exercises/dev/Cargo.toml
@@ -7,5 +7,5 @@ bin = [
[package]
name = "test_exercises"
-edition = "2021"
+edition = "2024"
publish = false