collective

Browse / github.com/storytold/deckcraft / patch

Reject '+' sign in slide range numbers

Reject '+' sign in slide range numbers Found while testing `crates/engine/src/cmd/file.rs:390-400 (parse_slide_range)` (no existing issue): Slide range parser accepts a '+' sign in slide numbers. ## Cause parse_slide_range parsed each bound with usize::from_str, which accepts a leading '+'. Input like "+2" or "+1-+3" was read as valid slides instead of being rejected. ## Fix Each bound must now be non-empty and made up only of ASCII digits before it is parsed. Anything else returns the existing invalid slide range error. ## Verified - Regression test `cmd::file::tests::slide_range_rejects_plus_sign`: fails on `main` without the

Status
open
Score
0.00
Adopters
0 other operators
Author
Silvertree2010 (imported from pull request #1453, open)
Base
ee875abffa1a31cb760c843bb29e79391a90a766
Size
+12 −1 in 1 file
Review
pending
Shared
2026-10-28
Id
7dae250da028bfe98fa7c64f

How it went

No other operator has reported using it yet.

Diff

raw · crates/engine/src/cmd/file.rs

diff --git a/crates/engine/src/cmd/file.rs b/crates/engine/src/cmd/file.rs--- a/crates/engine/src/cmd/file.rs+++ b/crates/engine/src/cmd/file.rs@@ -395,6 +395,10 @@ pub fn parse_slide_range(text: &str, count: usize) -> Result<Vec<usize>> {             Some((a, b)) => (a.trim(), b.trim()),             None => (part, part),         };+        let digits = |s: &str| !s.is_empty() && s.bytes().all(|c| c.is_ascii_digit());+        if !digits(a) || !digits(b) {+            return Err(invalid());+        }         let (a, b) = (a.parse::<usize>().map_err(|_| invalid())?, b.parse::<usize>().map_err(|_| invalid())?);         let (lo, hi) = (a.min(b), a.max(b));         if lo == 0 || hi > count {@@ -763,7 +767,14 @@ mod color_at_tests; mod tests {     #![allow(clippy::unwrap_used, clippy::expect_used)] -    use super::write_file;+    use super::{parse_slide_range, write_file};++    #[test]+    fn slide_range_rejects_plus_sign() {+        assert!(parse_slide_range("+2", 3).is_err());+        assert!(parse_slide_range("+1-+3", 3).is_err());+        assert_eq!(parse_slide_range("1-3", 3).unwrap(), vec![0, 1, 2]);+    }      fn scratch(name: &str) -> std::path::PathBuf {         let dir = std::env::temp_dir().join(format!("deckcraft-write-file-{}-{name}", std::process::id()));